Symfony3 Dynamically Modify Forms with events

I did not notice a field or a property called 'select_provincia' in neither your entity, nor the main form, so I will try guessing, that it probably should be called simply 'provincia', as that is the name for both the property in municipality entity and in the form subscriber for municipality. Also in AddMunicipioField.php you should change this code:

if ($provincia instanceof DbProvincia) {
   $qb->where('idMunicipio.provincia = :provincia')
      >setParameter('provincia', $provincia);
} 

to this:

if ($provincia instanceof DbProvincia) {
   $qb->where('idMunicipio.provincia = :provincia')
      >setParameter('provincia', $provincia->getId());
} 

since when querying you will be comparing provincia to the ID of province.

Further more, make sure you have implemented the __toString() method in the municipality entity, so that symfony would know how to convert that object to a string in order to show it in the select list.

Hope this helps :)


Seeing that you have added new information i will update my answer:

Firstly, In the AddMunicipioField.php you still have basically the same error: the array key is going to be called the same way you name your field, in this case not 'provincia_input', but 'provincia'. You can see the data that was posted to you by calling "dump($data); die;" just before you check if the array key exists (check for a key name "provincia", as you can see the name matches what you have specified when adding the field to the form (AddProvinciaField.php):

$form -> add('provincia', EntityType::class

Another thing I have noticed in the first js snippet you have posted is that in this part of code:

$(".provincia-input").change(function(){
    var data = { idMunicipio: $(this).val() };
    $.ajax({
        type: 'POST',
        url: $form.attr('action'),
        data: data,
        success: function(data) {
            for (var i=0, total = data.length; i < total; i++) {
                $('.municipio-input').append('<option value="' + data[i].id + '">' + data[i].municipio + '</option>');
            }
        }
    });
});

you are taking the input from $(".provincia-input") and sending it as a value for a field called "idMunicipio", which in you situation I don't think makes any sense.


Lastly, I will discus the errors that were made in the last piece of the JS you've posted:

  $(document).ready(function () {
    $('.provincia-input').change(function () {       
        var $form = $(this).closest('form');
        var data = $('.provincia-input').serialize();
        $.ajax({
            url: $form.attr('action'),
            type: 'POST',
            data: data,
            success: function (data) {
                $('.municipio-input').replaceWith($(html).find('.municipio-input'));
            }
        });
    });
  });

First of all, class names are not supposed to be used for identifying the fields that you are using. By definition they are supposed to be used multiple time in the document and describe only style, which might lead to some unexpected behaviour as your codebase grows. Please assign proper ID values to the inputs that you are going to be querying and especially replacing so that you could identify them correctly.

Secondly, please refer to the JS code posted in the official Symfony tutorial by following this link. As you can see the proper way to post data back to the server is not by sending a lone property like you are trying to do in this line:

var data = $('.provincia-input').serialize();

but rather by sending the property as a part of the forms data. So as in the tutorial I've posted, please first create an empty data object:

var data = {};

then add the province value to it:

data[$(this).attr('name')] = $(this).val();

Thirdly, this part of code is clearly incorrect:

success: function (data) {
        $('.municipio-input').replaceWith($(html).find('.municipio-input'));
}

As you can see the html variable is undefined in that part of code. This of course is because the variable that you are supposed to be using in this case is called data (the response that you have gotten from the server). So please change it to this:

success: function (data) {
        $('.municipio-input').replaceWith($(data).find('.municipio-input'));
}

Lastly, if you are still learning SF and web programming, I would like to suggest taking the bottom up approach to advance your programming knowledge instead, since this case is pretty complex and issues that prevented your code from working still require deeper understanding of the technologies you are using. I would personally suggest reading up on HTML attribute usage, Symfony form handling, read up on what data is available to you during each Symfony form event and maybe try using the dumper component of symfony more to debug your code, since var_dump is really a very inefficient way to debug SF code (would have solved many problems for you).