我试图将异步值绑定到我的Aurelia模板之一,显然我得到的是[object Promise]
作为回报。
我找到了这篇文章http://www.sobell.net/aurelia-async-bindings/,它很好地解释了如何使用绑定行为解决这个问题,它看起来像这样:
// http://www.sobell.net/aurelia-async-bindings/
export class asyncBindingBehavior {
bind (binding, source) {
binding.originalUpdateTarget = binding.updateTarget;
binding.updateTarget = a => {
if (typeof a.then === 'function') {
binding.originalUpdateTarget('...');
a.then(d => {
binding.originalUpdateTarget(d);
});
}
else {
binding.originalUpdateTarget(a);
}
};
}
unbind (binding) {
binding.updateTarget = binding.originalUpdateTarget;
binding.originalUpdateTarget = null;
}
}
当promise用字符串或其他非对象类型的变量解析时,这可以完美地工作。
但是如果我的promise解析为一个对象呢?我该如何访问对象内部需要的属性呢?
因为如果我在模板中做:${object.property & async}
,那么它将失败,因为object.property
不是一个承诺-只有object
是。
我添加了一点hack,允许我指定一个属性作为async
的参数,像这样:${object & async:'property'}
,并更新了我的绑定行为:
// http://www.sobell.net/aurelia-async-bindings/
export class asyncBindingBehavior {
bind (binding, source, property) {
binding.originalUpdateTarget = binding.updateTarget;
binding.updateTarget = a => {
if (typeof a.then === 'function') {
binding.originalUpdateTarget('...');
a.then(d => {
if (property) {
binding.originalUpdateTarget(d[property]);
}
else {
binding.originalUpdateTarget(d);
}
});
}
else {
binding.originalUpdateTarget(a);
}
};
}
unbind (binding) {
binding.updateTarget = binding.originalUpdateTarget;
binding.originalUpdateTarget = null;
}
}
但这对我来说感觉很像一个黑客,它也不允许我访问任何更深的属性,如object.parent.child
。
我也在GitHub上发现了这个(相当老的)问题:https://github.com/aurelia/templating/issues/81他们使用getValue
方法。我从来没有听说过这种方法,尝试使用它失败了,所以我不确定它是如何工作的…
任何想法?
您可以通过指定一个函数作为第三个参数来避开这个难题,从而提供比简单的属性提取更多的灵活性。
你可以这样写:
export class asyncBindingBehavior {
bind (binding, source, transformer="default") {
binding.originalUpdateTarget = binding.updateTarget;
binding.updateTarget = a => {
if (typeof a.then === 'function') {
binding.originalUpdateTarget('...');
a.then(d => binding.originalUpdateTarget(transformFunctions[transformer](d)));
} else {
binding.originalUpdateTarget(a);
}
};
}
unbind (binding) {
binding.updateTarget = binding.originalUpdateTarget;
binding.originalUpdateTarget = null;
}
}
transformFunctions
查找是必要的(?),因为Aurelia绑定被指定为HTML-ebbedded或模板指令(即所有参数必须是String)。除非Aurelia提供了一种更好的方式来"传递函数"(值转换器?),否则您应该这样写:
export var transformFunctions = {
default: (d) => d,
transform1: (d) => d.someProperty,
transform2: (d) => d.someProperty.someOtherProperty,
transform3: someFunction,
transform4: someOtherFunction.bind(null, someData);
}
当然,你可以给函数起个更好的名字