public string Render(dynamic dmodel) { try { var xmodel = new Scriban.Runtime.ScriptObject(); xmodel.Import(new { model = dmodel }, renamer: member => member.Name); var xfn = new Scriban.Runtime.ScriptObject();; xfn.Import(typeof(HlidacStatu.Lib.Render.ScribanT.Functions) , renamer: member => member.Name); var context = new Scriban.TemplateContext { MemberRenamer = member => member.Name, LoopLimit = 65000 }; context.PushCulture(System.Globalization.CultureInfo.CurrentCulture); context.PushGlobal(xmodel); context.PushGlobal(xfn); var scriptObjGlobalVariables = new ScriptObject(); foreach (var kv in this.globalVariables) { scriptObjGlobalVariables[kv.Key] = kv.Value; } context.PushGlobal(scriptObjGlobalVariables); var res = xTemplate.Render(context); return(res); } catch (Exception e) { HlidacStatu.Util.Consts.Logger.Error($"ScribanT render error\nTemplate {this.template}\n\n" + Newtonsoft.Json.JsonConvert.SerializeObject(dmodel) , e); throw; } }
public void Regression_336() { var so = new Scriban.Runtime.ScriptObject(); so.SetValue("X", "TEST", false); var evaluated = Template.Parse("{{X}}").Evaluate(new TemplateContext(so)); //important - test type since ScriptArray can be cast to string implicitly Assert.AreEqual(typeof(string), evaluated.GetType()); Assert.AreEqual("TEST", evaluated); }
public string Render(DataSet ds, dynamic dmodel, string qs = "", IReadOnlyDictionary <string, IReadOnlyCollection <string> > highlightingData = null) { string template = GetTemplateHeader(ds.DatasetId, qs) + this.body; var xTemp = Scriban.Template.Parse(template); if (xTemp.HasErrors) { throw new System.ApplicationException(xTemp .Messages .Select(m => m.ToString()) .Aggregate((f, s) => f + "\n" + s) ); } var xmodel = new Scriban.Runtime.ScriptObject(); xmodel.Import(new { model = dmodel }, renamer: member => member.Name); var xfn = new Scriban.Runtime.ScriptObject();; xfn.Import(typeof(HlidacStatu.Lib.Data.External.DataSets.Registration.Template.Functions) , renamer: member => member.Name); var context = new Scriban.TemplateContext { MemberRenamer = member => member.Name }; context.PushCulture(System.Globalization.CultureInfo.CurrentCulture); context.PushGlobal(xmodel); context.PushGlobal(xfn); var scriptObjGlobalVariables = new ScriptObject(); // Notice: MyObject is not imported but accessible through // the variable myobject scriptObjGlobalVariables["highlightingData"] = highlightingData; context.PushGlobal(scriptObjGlobalVariables); var res = xTemp.Render(context); return(res); }
public string Render(DataSet ds, dynamic dmodel) { string template = "{{func fn_DatasetItemUrl" + "\n" + $" ret ('https://www.hlidacstatu.cz/data/Detail/{ds.DatasetId}/' + $0)" + "\n" + "end}}"; template = template + "\n\n" + this.body; var xTemp = Scriban.Template.Parse(template); if (xTemp.HasErrors) { throw new System.ApplicationException(xTemp .Messages .Select(m => m.ToString()) .Aggregate((f, s) => f + "\n" + s) ); } var xmodel = new Scriban.Runtime.ScriptObject(); xmodel.Import(new { model = dmodel }, renamer: member => member.Name); var xfn = new Scriban.Runtime.ScriptObject();; xfn.Import(typeof(HlidacStatu.Lib.Data.External.DataSets.Registration.Template.Functions) , renamer: member => member.Name); var context = new Scriban.TemplateContext { MemberRenamer = member => member.Name }; context.PushCulture(System.Globalization.CultureInfo.CurrentCulture); context.PushGlobal(xmodel); context.PushGlobal(xfn); var res = xTemp.Render(context); return(res); }
/// <summary> /// Imports the specified object. /// </summary> /// <param name="obj">The object.</param> /// <param name="flags">The import flags.</param> /// <param name="filter">A filter applied on each member</param> /// <param name="renamer">The member renamer.</param> /// <exception cref="System.ArgumentOutOfRangeException"></exception> public static void Import(this IScriptObject script, object obj, ScriptMemberImportFlags flags, FilterMemberDelegate filter = null, IMemberRenamer renamer = null) { if (obj == null) { return; } if (!ScriptObject.IsImportable(obj)) { throw new ArgumentOutOfRangeException(nameof(obj), $"Unsupported object type [{obj.GetType()}]. Expecting plain class or struct"); } var typeInfo = (obj as Type ?? obj.GetType()).GetTypeInfo(); bool useStatic = false; bool useInstance = false; bool useMethodInstance = false; if (obj is Type) { useStatic = true; obj = null; } else { useInstance = true; useMethodInstance = (flags & ScriptMemberImportFlags.MethodInstance) != 0; } renamer = renamer ?? StandardMemberRenamer.Default; if ((flags & ScriptMemberImportFlags.Field) != 0) { foreach (var field in typeInfo.GetDeclaredFields()) { if (!field.IsPublic) { continue; } if (filter != null && !filter(field.Name)) { continue; } var keep = field.GetCustomAttribute <ScriptMemberIgnoreAttribute>() == null; if (keep && ((field.IsStatic && useStatic) || useInstance)) { var newFieldName = renamer.GetName(field.Name); if (String.IsNullOrEmpty(newFieldName)) { newFieldName = field.Name; } // If field is init only or literal, it cannot be set back so we mark it as read-only script.SetValue(newFieldName, field.GetValue(obj), field.IsInitOnly || field.IsLiteral); } } } if ((flags & ScriptMemberImportFlags.Property) != 0) { foreach (var property in typeInfo.GetDeclaredProperties()) { if (!property.CanRead || !property.GetGetMethod().IsPublic) { continue; } if (filter != null && !filter(property.Name)) { continue; } var keep = property.GetCustomAttribute <ScriptMemberIgnoreAttribute>() == null; if (keep && (((property.GetGetMethod().IsStatic&& useStatic) || useInstance))) { var newPropertyName = renamer.GetName(property.Name); if (String.IsNullOrEmpty(newPropertyName)) { newPropertyName = property.Name; } script.SetValue(newPropertyName, property.GetValue(obj), property.GetSetMethod() == null || !property.GetSetMethod().IsPublic); } } } if ((flags & ScriptMemberImportFlags.Method) != 0 && (useStatic || useMethodInstance)) { foreach (var method in typeInfo.GetDeclaredMethods()) { if (filter != null && !filter(method.Name)) { continue; } var keep = method.GetCustomAttribute <ScriptMemberIgnoreAttribute>() == null; if (keep && method.IsPublic && ((useMethodInstance && !method.IsStatic) || (useStatic && method.IsStatic)) && !method.IsSpecialName) { var newMethodName = renamer.GetName(method.Name); if (String.IsNullOrEmpty(newMethodName)) { newMethodName = method.Name; } script.SetValue(newMethodName, new ObjectFunctionWrapper(obj, method), true); } } } }
/// <summary> /// Imports the specified object. /// </summary> /// <param name="script">The script object to import into</param> /// <param name="obj">The object.</param> /// <param name="flags">The import flags.</param> /// <param name="filter">A filter applied on each member</param> /// <param name="renamer">The member renamer.</param> /// <exception cref="System.ArgumentOutOfRangeException"></exception> public static void Import(this IScriptObject script, object obj, ScriptMemberImportFlags flags, MemberFilterDelegate filter = null, MemberRenamerDelegate renamer = null) { if (obj == null) { return; } if (!ScriptObject.IsImportable(obj)) { throw new ArgumentOutOfRangeException(nameof(obj), $"Unsupported object type `{obj.GetType()}`. Expecting plain class or struct"); } var typeInfo = (obj as Type ?? obj.GetType()).GetTypeInfo(); bool useStatic = false; bool useInstance = false; bool useMethodInstance = false; if (obj is Type) { useStatic = true; obj = null; } else { useInstance = true; useMethodInstance = (flags & ScriptMemberImportFlags.MethodInstance) != 0; } renamer = renamer ?? StandardMemberRenamer.Default; while (typeInfo != null) { if ((flags & ScriptMemberImportFlags.Field) != 0) { foreach (var field in typeInfo.GetDeclaredFields()) { if (!field.IsPublic) { continue; } if (filter != null && !filter(field)) { continue; } var keep = field.GetCustomAttribute <ScriptMemberIgnoreAttribute>() == null; if (keep && ((field.IsStatic && useStatic) || useInstance)) { var newFieldName = renamer(field); if (String.IsNullOrEmpty(newFieldName)) { newFieldName = field.Name; } // If field is init only or literal, it cannot be set back so we mark it as read-only script.SetValue(null, new SourceSpan(), newFieldName, field.GetValue(obj), field.IsInitOnly || field.IsLiteral); } } } if ((flags & ScriptMemberImportFlags.Property) != 0) { foreach (var property in typeInfo.GetDeclaredProperties()) { if (!property.CanRead || !property.GetGetMethod().IsPublic) { continue; } if (filter != null && !filter(property)) { continue; } var keep = property.GetCustomAttribute <ScriptMemberIgnoreAttribute>() == null; if (keep && (((property.GetGetMethod().IsStatic&& useStatic) || useInstance))) { var newPropertyName = renamer(property); if (String.IsNullOrEmpty(newPropertyName)) { newPropertyName = property.Name; } // Initially, we were setting readonly depending on the precense of a set method, but this is not compatible with liquid implems, so we remove readonly restriction //script.SetValue(null, new SourceSpan(), newPropertyName, property.GetValue(obj), property.GetSetMethod() == null || !property.GetSetMethod().IsPublic); script.SetValue(null, new SourceSpan(), newPropertyName, property.GetValue(obj), false); } } } if ((flags & ScriptMemberImportFlags.Method) != 0 && (useStatic || useMethodInstance)) { foreach (var method in typeInfo.GetDeclaredMethods()) { if (filter != null && !filter(method)) { continue; } var keep = method.GetCustomAttribute <ScriptMemberIgnoreAttribute>() == null; if (keep && method.IsPublic && ((useMethodInstance && !method.IsStatic) || (useStatic && method.IsStatic)) && !method.IsSpecialName) { var newMethodName = renamer(method); if (String.IsNullOrEmpty(newMethodName)) { newMethodName = method.Name; } script.SetValue(null, new SourceSpan(), newMethodName, DynamicCustomFunction.Create(obj, method), true); } } } if (typeInfo.BaseType == typeof(object)) { break; } typeInfo = typeInfo.BaseType.GetTypeInfo(); } }