diff --git a/app/assets/javascripts/discourse/widgets/header-contents.js.es6 b/app/assets/javascripts/discourse/widgets/header-contents.js.es6
index 819178b6ac0..e998053ff43 100644
--- a/app/assets/javascripts/discourse/widgets/header-contents.js.es6
+++ b/app/assets/javascripts/discourse/widgets/header-contents.js.es6
@@ -4,10 +4,10 @@ import hbs from 'discourse/widgets/hbs-compiler';
createWidget('header-contents', {
tagName: 'div.contents.clearfix',
template: hbs`
- {{attach widget="home-logo"}}
+ {{attach widget="home-logo" attrs=attrs}}
{{yield}}
{{#if attrs.topic}}
- {{attach widget="header-topic-info"}}
+ {{attach widget="header-topic-info" attrs=attrs}}
{{/if}}
`,
});
diff --git a/lib/javascripts/widget-hbs-compiler.js.es6 b/lib/javascripts/widget-hbs-compiler.js.es6
index 3f96a64eaaf..07d418ff2ba 100644
--- a/lib/javascripts/widget-hbs-compiler.js.es6
+++ b/lib/javascripts/widget-hbs-compiler.js.es6
@@ -1,20 +1,45 @@
function resolve(path) {
if (path.indexOf('settings') === 0) {
return `this.${path}`;
- } else if (path.indexOf('parentState') === 0) {
- return `attrs._${path}`;
}
-
return path;
}
+function sexp(value) {
+ if (value.path.original === "hash") {
+
+ let result = [];
+
+ value.hash.pairs.forEach(p => {
+ result.push(`"${p.key}": ${p.value.original}`);
+ });
+
+ return `{ ${result.join(", ")} }`;
+ }
+}
+
+function argValue(arg) {
+ let value = arg.value;
+ if (value.type === "SubExpression") {
+ return sexp(arg.value);
+ } else if (value.type === "PathExpression") {
+ return value.original;
+ }
+}
+
function mustacheValue(node, state) {
let path = node.path.original;
switch(path) {
case 'attach':
- const widgetName = node.hash.pairs.find(p => p.key === "widget").value.value;
- return `this.attach("${widgetName}", state ? $.extend({}, attrs, { _parentState: state }) : attrs)`;
+ let widgetName = node.hash.pairs.find(p => p.key === "widget").value.value;
+
+ let attrs = node.hash.pairs.find(p => p.key === "attrs");
+ if (attrs) {
+ return `this.attach("${widgetName}", ${argValue(attrs)})`;
+ }
+ return `this.attach("${widgetName}", attrs)`;
+
break;
case 'yield':
return `this.attrs.contents()`;
diff --git a/script/test_hbs_compiler.rb b/script/test_hbs_compiler.rb
new file mode 100644
index 00000000000..1b846615dcd
--- /dev/null
+++ b/script/test_hbs_compiler.rb
@@ -0,0 +1,28 @@
+template = <<~HBS
+ {{attach widget="widget-name" attrs=attrs}}
+ {{#if state.category}}
+ {{attach widget="category-display" attrs=(hash category=state.category)}}
+ {{/if}}
+HBS
+
+ctx = MiniRacer::Context.new(timeout: 15000)
+ctx.eval("var self = this; #{File.read("#{Rails.root}/vendor/assets/javascripts/babel.js")}")
+ctx.eval(File.read(Ember::Source.bundled_path_for('ember-template-compiler.js')))
+ctx.eval("module = {}; exports = {};");
+ctx.attach("rails.logger.info", proc { |err| puts(err.to_s) })
+ctx.attach("rails.logger.error", proc { |err| puts(err.to_s) })
+ctx.eval <