vaadin / flow-components

Java counterpart of Vaadin Web Components
100 stars 66 forks source link

PolymerTemplate: referencing to a field via `@Id` clears value given in the template #839

Open mvysny opened 4 years ago

mvysny commented 4 years ago

Vaadin 14.0.7. I have a polymer template with <vaadin-text-field id="username" name="username" value="foo"></vaadin-text-field>. When I navigate to the page the text field is properly pre-filled with foo.

However, as soon as I add

    @Id("username")
    TextField usernameField;

to my Java class, the text field becomes empty on the page. Sounds like a bug to me, but perhaps it's an after-effect of client+server fighting for control?

mvysny commented 4 years ago

skeleton-starter-flow.zip

mvysny commented 4 years ago

If this is intended, this should definitely be documented at https://vaadin.com/docs/v14/flow/polymer-templates/tutorial-template-components.html

The documentation currently mentions that, quoting:

neither its hierarchical structure nor attributes/properties are available on the server side via API. The injected Div instance doesn’t have any server side child even though there is the anchor a element available on the client side.

However, this behaviour is more than just stuff not being accessible on server-side. This behaviour is destructive since it overrides any settings in the polymer template, for no apparent reason.

joheriks commented 4 years ago

I would say this is a bug, as value works inconsistently with e.g. placeholder and label properties: when initialized in the template, the latter two are not cleared by @Id("username") in the server side components. (In either case the server side state is of course not synchronized automatically)

denis-anisimov commented 3 years ago

This is kind of a bug in TextFiled.

This is a generic issue for ANY component which is based on web component. When someone develops a component which has value it's quite common to set some default value. Usually it's an empty string "" (TextField case) or null.

The default value is set by default. It means that there is an explicitly set value from the server side which overrides any value set from the client side.

This is exactly the case with TextField here and overall : common case. It happens because nobody thought that a component can be used being mapped via @Id (and that's quite natural: why should I consider a potential case which is not forced anyhow and I'm not even aware of?).

This is still an issue even when the template is parsed on the server side and attribute/property value is set based on template content: even though the value is set during @Id mapping it's overriden by thew default "" value in the TextField constructor.

I've gone through all the Vaadin components and fixed the constructor behavior to consider value template property which can be already set by @Id mapping when the constructor is invoked.

But this is done for the master branch only: https://github.com/vaadin/flow-components/blob/master/vaadin-text-field-flow-parent/vaadin-text-field-flow/src/main/java/com/vaadin/flow/component/textfield/TextField.java#L66

The same should be done for 14.x versions and other versions as well.

But this is a component issue.

denis-anisimov commented 3 years ago

Just in case I want to repeat: this is not just TextField issue. All the components are affected. And all of them are fixed in the master .