8000 Missing an entry on setting default values in Symfony Forms · Issue #2871 · symfony/symfony-docs · GitHub
[go: up one dir, main page]

Skip to content

Missing an entry on setting default values in Symfony Forms #2871

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
luebbert42 opened this issue Aug 1, 2013 · 32 comments
Closed

Missing an entry on setting default values in Symfony Forms #2871

luebbert42 opened this issue Aug 1, 2013 · 32 comments
Labels
actionable Clear and specific issues ready for anyone to take them. Form good first issue Ideal for your first contribution! (some Symfony experience may be required) hasPR A Pull Request has already been submitted for this issue.

Comments

@luebbert42
Copy link
Contributor

Could we have an example how to set default values to a form element using form classes?

There are some answers on Stackoverflow (the question has 18.000 views!), but I am not sure about the answer quality (yet, trying to get it running ;-)):

http://stackoverflow.com/questions/7913086/how-to-set-default-value-for-form-field-in-symfony2

@wouterj
Copy link
Member
wouterj commented Dec 4, 2013

There is already a data document in the reference of the Form type.

Some other type references should include this under "Inherit options", to make it clear. I propose at least:

  • text
  • number
  • url

This can be easily done by adding a line to the table at the top of each reference:

+-------------+-------------------------------------------------------------------+
| Rendered as | ``input url`` field                                               |
+-------------+-------------------------------------------------------------------+
| Options     | - `default_protocol`_                                             |
+-------------+-------------------------------------------------------------------+
| Inherited   | - `max_length`_                                                   |
| options     | - `required`_                                                     |
|             | - `data`_                                                         |
|             | ...                                                               |
+-------------+-------------------------------------------------------------------+

And then in the "Inherit data" section, an include should be placed:

Inherited Options
-----------------

These options inherit from the :doc:`form </reference/forms/types/form>` type:

.. include:: /reference/forms/types/options/data.rst.inc

Related issue: #2360

@luebbert42
Copy link
Contributor Author

There is another interesting answer on Stackoverflow covering a few options - does it make sense to include those in the documentation?
http://stackoverflow.com/questions/17986481/set-default- 8000 values-using-form-classes-in-symfony-2

@mtrojanowski
Copy link
Contributor

I added the data option to the first three types mentioned by Wouter. Created the pull request just to make sure it's going the right direction. I will add the option to the other files as well.

As for the discussions on Stack Overflow I'm not sure if we need any more information in the documentation about the default values.

@mtrojanowski
Copy link
Contributor

It's now complete with data option added to all of the types where it is meaningful. I skipped the types: file, submit, password, reset, button, search.

@xabbuh
Copy link
Member
xabbuh commented Dec 15, 2013

@luebbert42 which additional options do you mean?

Copy link
Contributor Author

I am not sure we are talking about the same thing: from my experience "data" sets a value ALWAYS, not only when the form element has no value yet.

Let's say you want to create a form "Add a new address" to your application. For some reason in 99% of the use cases the city is "Amsterdam". For convenience you want to preset the city atttribute to "Amsterdam", but the user can change it for the rare case his address is not in Amsterdam, but in Utrecht. . When he edits this special address later on, the form should show "Utrecht" of course, not Amsterdam. My original request was to document this case. 😄

@wouterj
Copy link
Member
wouterj commented Dec 15, 2013

@luebbert42 then you should just use 'Amsterdam' as a default of your project

@mtrojanowski
Copy link
Contributor

Agreed. I think the topic of default values in the fields is not tightly connected to the documentation of the form types themselves. I mean you can specify the default value in different places depending on what your form represents (is it connected to an entity, a contact form, etc.).

Still @luebbert42 I don't quite understand what do you mean by "sets the value always". You create a form and the defaults will be populated with what you have in the data option. When you bind the form to the request the values will be changed, right? Isn't it what the default value should do?

Sticking to your example. If this is some kind of address you will be editing afterwards it means that you're persisting it. Thus you probably have some kind of Address entity. In this entity you can set a default value for the city. When you create your form for a new address and pass the new "empty" entity to the form it will use the default value of the city field, and there's actually no need to use the data option on the FormType.

@luebbert42
Copy link
Contributor Author

@wouterj excactly - where in the manual do I find the information how to do that for the different form elements?

@luebbert42
Copy link
Contributor Author

@mtrojanowski have to try that with the current version - when I had the question 5 months ago it did not work that way OR I did it wrong (probably the latter) ;-)

@wouterj
Copy link
Member
wouterj commented Dec 15, 2013

@luebbert42 it's the same for each form type, it's just using the object:

class Address
{
    protected $city = 'Amsterdam';
    protected $country = 'Nederland';

    // ... getters/setters
}

$address = new Address();
$form = $this->createFormBuilder($address)
    ->add('city', 'text')
    ->add('country', 'text')
    ->getForm();

Now, when rendering the form it has the defaults 'Amsterdam' and 'Nederland'. When changing this to 'Utrecht' and submitting the form (and you persist the object). The next time you generate the edit form, you use:

$address = $objectManager->find(...);
$form = $this->createFormBuilder($address)
    ->add('city', 'text')
    ->add('country', 'text')
    ->getForm();

And now the defaults are 'Utrecht' and 'Nederland'.

@luebbert42
Copy link
Contributor Author

@wouterj Yes, that's an option for text field. How would you do that with elements displayed as checkbox or radiobuttons?

I would have expected that setting the data attr in the form builder class handles default values correctly for all elements. This is not the case. I tried it with a fresh 2.4 project. Using the "data" attributes for default values is still not working (or I am still doing it wrong ;-))

I have uploaded a tar.gz of the complete demo app directory if you want to try it out, too:
www.another-showroom.com/demo.tar.gz

The code is all generated by the Symfony console tool but a few characters in src/Acme/DemoBundle/Form/AddressType.php

Access the CRUD thingy through:
http://yourtestdomain/app_dev.php/address/

@wouterj
Copy link
Member
wouterj commented Dec 15, 2013

With checkbox or radiobuttons, you don't use a string value but a boolean value:

class User
{
    protected $admin = false;
}

@luebbert42
Copy link
Contributor Author

does it make sense to have that in the manual or cookbook?

@wouterj
Copy link
Member
wouterj commented Dec 15, 2013

I've now said a couple of things:

  1. The form uses the data from the object you binded to the form
  2. Checkbox and radiobutton types use booleans

We documented (1) in the book article and (2) in the reference articles of checkbox and radiobutton. So we already documented everything :)

@luebbert42
Copy link
Contributor Author

I totally agree with 1. This is very well explained and easy to understand as a beginner.

Which paragraph are you refering to for "2"? (sorry for being such a pain in the ass, we can also close the issue and I'll shut up :-))

@wouterj
Copy link
Member
wouterj commented Dec 15, 2013

Creates a single input checkbox. This should always be used for a field that has a Boolean value: if the box is checked, the field will be set to true, if the box is unchecked, the value will be set to false.

First paragraph :)

(sorry for being such a pain in the ass, we can also close the issue and I'll shut up :-))

no, the PR is not yet merged so we can't close this one :) And I think it only improves the docs when we can have discussions like this with people reading our docs

@luebbert42
Copy link
Contributor Author

let me summarize in return what I know about setting default values in the sense of

    <input type='x' value='DEFAULT_VALUE_CAN_BE_OVER_WRITTEN_BY_USER'>

now in Symfony:

  1. You cannot do it in the form class.
    This does not work:
    0. create one form class used for "create entity and edit entity"
    1. set data = "foo" for a form element
    2. create new entity by using form, "foo" is displayed to the user
    3. user changes "foo" to "bar"
    4. entity with "bar" is saved to the database
    5. entity is displayed again with the form (by binding the entity to the form as usual)
    6. "foo" is shown to the user, not bar
    Solution: use two different form classes or use and some if-then-else-construction to fill the entity only with "foo" if not empty.
  2. You must set default values it in the entity class with class variables.

From my opinion this is still not obvious from the documentation.

@mtrojanowski
Copy link
Contributor

In the book article @wouterj mentioned it explicitly states that the form takes the values for fields from the entity passed to it. There's also this section. Which shows you how can you pass defaults to the form when using forms without a related entity class. Maybe we can have a short article somewhere (cookbook?) about the different aspects of default values and where can we set them. Or maybe a note field in the book will be sufficient. I think additional explanation is not needed here but if you believe the topic is still not clear maybe it's worth adding something.

@luebbert42
Copy link
Contributor Author

Hm, we are going around in circles...

"In the book article @wouterj mentioned it explicitly states that the form takes the values for fields from the entity passed to it."

Do we agree that defining a "data" attribute in the form class will always overwrite values passed from the entity?

@wouterj
Copy link
Member
wouterj commented Dec 15, 2013

Do we agree that defining a "data" attribute in the form class will always overwrite values passed from the entity?

Yes :)

@mtrojanowski
Copy link
Contributor

I read the discussion once again carefully and I think we somehow started to talk about slightly different things, or else - the proposed PR indeed is not exactly about what @luebbert42 originally meant.

So here's my view on the topic.

  1. The PR proposed by me (Added "data" option to the "Inherited options" table. #3333) adds the data option to the Inherited options table of the form types which make use of the data. I think we can agree that it is not wrong and it adds some information to the documentation (I only have to fix the order of the data paragraphs in lists under the tables).
  2. The fix proposed by the PR does not contribute much to a better understanding of where the default values for forms in Symfony come from (or where can be set). My proposition (which I will add shortly to the PR) is to add a short section in the book chapter on forms which will explain this. The chapter will explain that for forms connected to an entity it's best that the form takes defaults form the entity itself, and that for other forms the defaults can be passed as an array when creating the form object. It will also add that most of the form types can accept a data option which will override the value for the form field (so should be used carefully for entity forms).

Although I believe that all these can be found in different parts of the form's documentation and reference, having such a separate chapter will make it easier for people to find this particular piece of information (and will make it possible to share links directly to this chapter).

What do you think?

@wouterj
Copy link
Member
wouterj commented Dec 17, 2013

Thank you for the summary @mtrojanowski

This should not be placed in the book chapter, as that's already full of things that don't belong there :) It would either be (a) a new cookbook article ("Where are default values comming from?") or (b) a note added to the data option. I think (b) is the best option, as we already have information about this topic and we shouldn't duplicate ourselves to much by creating yet another article about this.

The note will look like:

.. note::

    The default values for Forms are based on the values of the properties of
    the entity. The ``data`` option overrides this default value.

@mtrojanowski
Copy link
Contributor

👍

My idea for the section in the book chapter was to have it clearly stand out from the other info ("Hey! Looking for the way to set the default values for the form? Have a look here!"), which would also allow people to directly link to the topic. The discussion on SO shows that people are still confused with this issue.

I like your solution. Unless there is more people who want that as a separate chapter we can stick to that note. Maybe I would just add something about values taken from an array (defaults do not have to come from an entity). Something like:

.. note::

    The default values for Form fields are taken directly from the entity 
    or the array passed to the form (if the form is not tied to an entity). 
    The ``data`` option overrides this default value.

@wouterj
Copy link
Member
wouterj commented Dec 17, 2013

we can also make it generic by saying "from the resource tied to the form".

Btw, don't forget to indent the note content with 4 spaces 😉

@xabbuh
Copy link
Member
xabbuh commented Dec 17, 2013

👍 for some generic wording. Though I prefer something like [...] are taken directly from the underlying data structure (e.g. an entity or an array). [...]

@luebbert42
Copy link
Contributor Author

can we add "class variables"?

[...] are taken directly from the underlying data structure (e.g. an entity's class variables or an array). [...]

@mtrojanowski
Copy link
Contributor

@xabbuh 👍

@luebbert42 I'm not sure about the class variables. If we were to be so specific then we should also use array fields instead of the array. I think it's a bit too much detailed. There's also a pretty nice error message when you want to use a form field which is not reflected in the entity (Sf tells you that you should have a public property a getter or isser). I'm sure people will be able to figure it out once they come to this stage :)

@mtrojanowski
Copy link
Contributor

I updated #3333 please have a look.

@weaverryan
Copy link
Member

Thanks everyone! If you still see something incomplete (now that I've merged #3333), let me know!

Cheers!

Sorry, something went wrong.

@Raghav9888
Copy link

@weaverryan Can you tell me when we Use inheritance

  1. abstract class AbstractEntity ( #[ORM\MappedSuperclass])
  2. class LoginUser
    (
    #[ORM\Entity(repositoryClass: LoginUserRepository::class)]
    #[ORM\InheritanceType("SINGLE_TABLE")]
    #[ORM\DiscriminatorColumn(name:"discr", type:"string")]
    #[ORM\DiscriminatorMap(['loginUser'=>LoginUser::class,"loginUserDetails"=>LoginUserDetails::class])]
    )
    3)class LoginUserDetails extends LoginUser

how to create form ?

@wouterj
Copy link
Member
wouterj commented Sep 21, 2022

Hi @Raghav9888! Please use one of the support channels to ask support question: https://symfony.com/support

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
actionable Clear and specific issues ready for anyone to take them. Form good first issue Ideal for your first contribution! (some Symfony experience may be required) hasPR A Pull Request has already been submitted for this issue.
Projects
None yet
Development

No branches or pull requests

6 participants
0