Polymer: Support for property getter/setters, including those with a defined default value

Created on 18 Sep 2015  路  6Comments  路  Source: Polymer/polymer

We have a number of cases where a component wants to expose a property whose value is managed by a separate object (which is not a DOM element). The most natural way to implement this is to define a property getter/setter that proxies requests to the other object. It's not clear from the docs whether something like this is supported.

First question: is there some official way of defining a getter/setter like this today?

As it turns out, one can get most of the way there by defining a property in both the properties block _and_ defining a getter/setter with the same name. See http://jsbin.com/yonara/edit. The key bit:

    get foo() { ... },
    set foo(value) { ... },

    properties: {
      foo: String
    }

This works mostly as expected, with one issue: if the proxied object defines a default value for the property, an initial value for the property cannot be set on a component instance in a markup attribute. In the demo, the attempt to set the foo attribute fails:

<test-element foo="bar"></test-element>

If the proxied object is modified to remove the property's default value ("Hello"), then the above markup works.

Digging in a bit, when Polymer is applying attributes to properties, _applyConfig() gets the value of the foo property and inspects to see if the value is defined. It appears that it wants to avoid stomping on values that have already been set since the component was created. However, since the proxied object already defines an initial value for the foo property ("Hello"), _applyConfig will conclude that the property has been set, and fail to apply the attribute as expected.

Second question: any suggestions for working around this?

Most helpful comment

@gaurav21r @azakus I thinking of you because now I'm developing an element with a property that should accept only url string...and a filter applied by a setter would be the perfect solution for this kind of property behavior...I know exists other workarounds...but they still remain workarounds!

All 6 comments

This would go a long way towards replacing the expression filters and to/from model functionality that was dropped in the move to Polymer 1.0.

+1

Polymer team any updates on this? There seems to be no valid replacement for get() in Polymer 1.0

I can see observer as a possible replacement for set()

The real issue here is that when using getters and setters, there is no way to declare the dependencies of those functions to the observation and databinding system.

You may not need it for this case (you do if you share Thing with any other element or function), but the risk of confusion is very high if users start making getter/setter backed properties that will not update as they expect.

Instead we provide computed properties for the getter use case, and observers for the setter use case.

@azakus Sorry for the late response. Doesn't computedProperties make the property read only ? I also felt computed / observers is the best solution to this problem. Unfortunately they can't be used together while getters setters can!

From the docs:

The value is interpreted as a method name and argument list. The method is invoked to calculate the value whenever any of the argument values changes. Computed properties are always read-only. See Computed properties for more information.

@gaurav21r @azakus I thinking of you because now I'm developing an element with a property that should accept only url string...and a filter applied by a setter would be the perfect solution for this kind of property behavior...I know exists other workarounds...but they still remain workarounds!

In ES6 it is idiomatic to provide getters or static getters for constants, e.g.,

static get DEFAULT_NAME { return 'constant'; }  // static getter
get DEFAULT_NAME { return 'constant'; }  // regular getter

and reference it in several places in the JS. Naturally, one would also want to use this from the template:

<span>[[DEFAULT_NAME]]</span>

The lack of this feature in Polymer is related to this issue.

Was this page helpful?
0 / 5 - 0 ratings