public JavaScriptExpressionWriter(Dictionary <Type, IJavaScriptGenerator> writers, TextWriter output, EvaluationContext baseContext) { Json = new JavaScriptSerializer(); Output = output; Writers = writers; BaseContext = baseContext; _checker = new JavaScriptExpressionChecker(writers); }
/// <summary> /// Generates JavaScript functions to evaluate patterns client side /// </summary> /// <param name="manager">The text manager to extract texts from.</param> /// <param name="clientClassName">The client name of the generated object. (The script will be var clientClassName = ...)</param> /// <param name="output">The generated javascript will be written to this generator.</param> /// <param name="language">The language for the generated texts (if different from current language).</param> /// <param name="defaultNamespace">The default namespace for texts. (Set this to your assembly's namespace in plugins)</param> /// <param name="filter">Specify this to only include a subset of the TextManager's texts.</param> /// <param name="includeScriptTags">Wraps the generated script in <script> blocks if <c>true</c>.</param> public void WriteScript(TextManager manager, string clientClassName, TextWriter output, LanguageInfo language = null, string defaultNamespace = null, Func <string, string, bool> filter = null, bool includeScriptTags = true) { language = language ?? manager.GetCurrentLanguage(); defaultNamespace = defaultNamespace ?? manager.DefaultNamespace; filter = filter ?? ((ns, key) => true); if (includeScriptTags) { output.Write("<script type='text/javascript'>/*<![CDATA[*/"); } var foundationNamespace = manager.GetNamespace(typeof(TextManager).Assembly); Func <string, string, bool> foundationTextFilter = (ns, key) => ns == foundationNamespace && _foundationTextKeyMatcher.IsMatch(key); var texts = manager.CurrentEntries .SelectMany(ns => ns.Value .Where(key => foundationTextFilter(ns.Key, key.Key) || filter(ns.Key, key.Key)) .Select(key => new { Namespace = ns.Key, Key = key.Key, CacheEntry = manager.GetTextEntry(ns.Key, key.Key, language, true) })).Where(x => x.CacheEntry != null).ToList(); var json = new JavaScriptSerializer(); output.Write("var "); output.Write(clientClassName); output.Write("=new Umbraco.Framework.Localization.TextManager("); output.Write(json.Serialize(defaultNamespace)); output.Write(","); output.Write(GetClientCultureInfoSpecification(json, (CultureInfo)language.Culture)); //Namespace keys output.Write(",{"); var namespaceKeys = new Dictionary <string, string>(); int i = 0; foreach (var ns in texts.Select(x => x.Namespace).Distinct()) { var key = "" + i; namespaceKeys.Add(ns, key); if (i++ > 0) { output.Write(","); } output.Write(json.Serialize(ns)); output.Write(":"); output.Write(json.Serialize(key)); } output.Write("}"); output.Write(","); output.Write(json.Serialize(manager.FallbackNamespaces.ToArray())); //Texts (function takes: manager, applySwitch, defaultFormattedValue, htmlEncode, applyFormat, getValue, reflectionParameter output.Write(",function(m,sw,dv,e,af,val,rp,sf) {"); //Write prerequisite code //Prerequisites for used writers var checker = new JavaScriptExpressionChecker(Writers); var usedWriters = new HashSet <IJavaScriptGenerator>(); foreach (var text in texts) { var exprWriters = checker.CheckExpression(text.CacheEntry.Evaluator.Expression).UsedWriters; foreach (var writer in exprWriters) { usedWriters.Add(writer); } } foreach (var writer in usedWriters) { writer.WritePrerequisites(output); } bool first = true; output.Write("return {"); //Write texts foreach (var text in texts) { if (first) { first = false; } else { output.Write(",\n"); } output.Write(json.Serialize(namespaceKeys[text.Namespace] + text.Key)); output.Write(":"); //TODO: Maybe it should be put somewhere if the text is a fallback text //bool fallback = text.CacheEntry.Text.Language != language.Key; Write(text.Namespace, text.Key, language, text.CacheEntry.Evaluator.Expression, output, clientClassName); } output.Write("};"); output.Write("});"); if (includeScriptTags) { output.Write("//]]></script>"); } }