/** * Specialization of filterHtmlAttributes for Incremental DOM that can handle * attribute functions gracefully. In any other situation, this delegates to * the regular escaping directive. */ // tslint:disable-next-line:no-any function filterHtmlAttributes(value: any) { if (isIdomFunctionType(value, SanitizedContentKind.ATTRIBUTES) || isAttribute(value)) { return value; } return soy.$$filterHtmlAttributes(value); }
/** * Prints an expression whose type is not statically known to be of type * "attributes". The expression is tested at runtime and evaluated depending * on what type it is. For example, if a string is printed in a context * that expects attributes, the string is evaluated dynamically to compute * attributes. */ function printDynamicAttr( incrementaldom: IncrementalDomRenderer, expr: SanitizedHtmlAttribute|string|boolean|IdomFunction) { if (goog.isFunction(expr) && (expr as IdomFunction).contentKind === SanitizedContentKind.ATTRIBUTES) { // tslint:disable-next-line:no-any (expr as any as LetFunction)(incrementaldom); return; } const attributes = splitAttributes(expr.toString()); const isExprAttribute = isAttribute(expr); for (const attribute of attributes) { const attrName = isExprAttribute ? attribute[0] : soy.$$filterHtmlAttributes(attribute[0]); if (attrName === 'zSoyz') { incrementaldom.attr(attrName, ''); } else { incrementaldom.attr(String(attrName), String(attribute[1])); } } }
/** * Calls an expression in case of a function or outputs it as text content. */ function callDynamicAttributes<A, B>( incrementaldom: IncrementalDomRenderer, // tslint:disable-next-line:no-any expr: Template<A, B>, data: A, ij: B) { // tslint:disable-next-line:no-any Attaching arbitrary attributes to function. const type = (expr as any as IdomFunction).contentKind; if (type === SanitizedContentKind.ATTRIBUTES) { (expr as IdomTemplate<A, B>)(incrementaldom, data, ij); } else { let val: string|SanitizedHtmlAttribute; if (type === SanitizedContentKind.HTML) { // This effectively negates the value of splitting a string. However, // This can be removed if Soy decides to treat attribute printing // and attribute names differently. val = soy.$$filterHtmlAttributes(htmlToString( () => (expr as IdomTemplate<A, B>)(defaultIdomRenderer, data, ij))); } else { val = (expr as SoyTemplate<A, B>)(data, ij) as SanitizedHtmlAttribute; } printDynamicAttr(incrementaldom, val); } }