emberjs / ember.js

Ember.js - A JavaScript framework for creating ambitious web applications
https://emberjs.com
MIT License
22.46k stars 4.21k forks source link

Computed property in model obfuscates view #9293

Closed gonvaled closed 10 years ago

gonvaled commented 10 years ago

I have been refactoring the use of views (because of a deprecation warning). This is the change I have made:

-            {{view SettingsApp.PhoneWithFlagView phoneNumberBinding="locator"}}
+            {{view "phoneWithFlag" phoneNumberBinding="locator"}}

Which for most views has been working fine, but for this particular case is failing with a very strange message:

Uncaught Error: Assertion Failed: You are looking for a i> +34 93X XX XX XX view in the < namespace, but the namespace could not be found

It turns out I have a computed property with a somewhat similar name:

    phoneWithFlag: function () {
        return SettingsApp.helpers.phoneWithFlag(this.get('locator'));
    }.property('locator'),

And that property is being picked up during the template rendering as the view name. I have tried removing the quotes:

{{view phoneWithFlag phoneNumberBinding="locator"}}

But no luck.

You could say that the problem is in my code, because I have a view called PhoneWithFlagView and a property with the name phoneWithFlag. But I would not agree, because the names are different enough: one has the suffix View and starts with uppercase (as is accepted practice in ember?) and the property starts with lowercase (which is also accepted practice?)

To solve this problem I have just (without any real justification but to workaround these ember quirks) renamed the property phoneWithFlagProp, which is maybe the safe way to go for properties. This seems to work.

gonvaled commented 10 years ago

I have verified that this issue is not only related to computed properties, but to all model properties.

workmanw commented 10 years ago

This is pretty intriguing. I tried to make a JSBin to test out this issue, but wasn't able to. Any chance you could make this bin simulate the problem: http://emberjs.jsbin.com/cuhukudicake/4/edit

endash commented 10 years ago

I get your frustration gonvaled, and in this case the transparency in some of the "Ember magic" might seem particularly arbitrary. What you're seeing here is a conversion from using globals/symbols to refer to classes, to using lookups on an injected container, with your new code referring to a class which is actually registered on the container as "view:phoneWithFlag." A big effort has been made to attempt to move all similar class lookups (itemController, itemView on a collection, etc) to use the container, in ways that are semantically appropriate. {{#each itemController="phoneWithTag"}} will resolve to controller:phoneWithTag, and {{view "phoneWithTag"}}will resolve to view:phoneWithTag.

This design decision is further a consequence of es6ification, where modules don't necessarily have names at all, in the usual sense. In such an app, for instance using ember-cli, what you think of as "PhoneWithTag" is just a module exported by one file and imported by another, in the case of an ember-cli app it's imported and then registered on the container, with a name based on the directory it is in and the file name, without ever needing to define a name for itself.

NB This was a reply to a postscript on the issue that has since been removed

endash commented 10 years ago

I concur with @workmanw I can't replicate without removing the quotes entirely. Could you include the initial debug information (ember and handlebars version #s) spit out in the console?

rwjblue commented 10 years ago