none
Asp.Net MVC + Model Binder + Checkbox = bug ? RRS feed

  • Pergunta

  •       Estou com um problema quanto ao ModelBind.
          Estava usando o MVC 1 e no feriadão migrei para 2, preview 2 (o problema é o mesmo em ambas versões).

          Em uma mesma tela tenho duas listagens: a de usuários e a de regras. Posso selecionar vários usuários e várias regras e dar o Post (ambas listagens são apenas checkbox).

          O problema é que o ModelBinder funciona apenas se o primeiro item (indice 0) de cada listagem (usuário e regra) estiver selecionado.


    Exemplo:
    Vamos considerar os seguintes dados
    USUARIO:
    User0
    User1
    User2
    User3

    REGRAS:
    Regra0
    Regra1
    Regra2
    Regra3
    Regra4

    Os dados são exibidos nesta ordem e por uma questão de praticidade, no exemplo, o número que consta seria o índice.
    Se eu selecionar User0 e Regra0, o ModelBind será preenchido .... se eu selecionar qualquer outro usuário que não o 0 ou qualquer regra que não a 0, a propriedade respectiva ficará nula.


    Minha classe do ModelBinder tem 2 propriedades:
    IList<Usuario> Usuarios
    IList<Regra> Regras

    Na interface, os checkbox tem os seguintes nomes (names):
    Usuarios[x].Codigo
    Regras[x].Codigo
    OBS: Os checkbox tinham as propriedades id e name idênticos, daí mudei o id trocando o "." por "_" e deu na mesma. Também já tentei colocar o campo com nome índice, conforme vi em um exemplo na internet e não funcionou.


    Alguém já teve este problema ???

    Abraços
    terça-feira, 13 de outubro de 2009 22:36

Respostas

  • Ricardo,

    Para checkbox usar a tecnica de indexadores no name do input não irá funcionar.

    Para que um checkbox seja considerado parte de um "Grupo" todos devem conter o mesmo name, veja o exemplo:

    <input id="usuario1" type="checkbox" name="usuariosIds" value="1" /><label for="usuario1">Usuario 1</label>
    <input id="usuario2" type="checkbox" name="usuariosIds" value="2" /><label for="usuario2">Usuario 2</label>
    <input id="usuario3" type="checkbox" name="usuariosIds" value="3" /><label for="usuario3">Usuario 3</label>
    <input id="usuario4" type="checkbox" name="usuariosIds" value="4" /><label for="usuario4">Usuario 4</label>
    .
    .
    .
    O mesmo vale para os checkbox de regras:

    <input id="regra1" type="checkbox" name="regrasIds" value="1" /><label for="regra1">Regra 1</label>
    <input id="regra2" type="checkbox" name="regrasIds" value="2" /><label for="regra2">Regra 2</label>
    .
    .
    .
    

    E o seu controller deve estar preparado para receber um array de ids de usuarios e regras:

    public ActionResult RelacionarRegrasUsuarios(int[] usuariosIds, int[] regrasIds)
    {
    //código para relacionar os usuarios com as regras.
    //se voce estiver usando Entity sei como fazer isto.
    }
    Assim os itens selecionados nos checks viram nos arrays, a partir daí fazemos o código de relacionamento.
    Nos relacionamentos n para n que geralmente fazemos o uso do input checkbox não há outra saída a não ser trabalhar com as chaves das tabelas.

    Espero poder ajudado-lo. Qualquer dúvida favor entrar em contato.

    Douglas Aguiar
    MCAD, MCT
    quarta-feira, 14 de outubro de 2009 00:45

Todas as Respostas

  • Ricardo,

    Para checkbox usar a tecnica de indexadores no name do input não irá funcionar.

    Para que um checkbox seja considerado parte de um "Grupo" todos devem conter o mesmo name, veja o exemplo:

    <input id="usuario1" type="checkbox" name="usuariosIds" value="1" /><label for="usuario1">Usuario 1</label>
    <input id="usuario2" type="checkbox" name="usuariosIds" value="2" /><label for="usuario2">Usuario 2</label>
    <input id="usuario3" type="checkbox" name="usuariosIds" value="3" /><label for="usuario3">Usuario 3</label>
    <input id="usuario4" type="checkbox" name="usuariosIds" value="4" /><label for="usuario4">Usuario 4</label>
    .
    .
    .
    O mesmo vale para os checkbox de regras:

    <input id="regra1" type="checkbox" name="regrasIds" value="1" /><label for="regra1">Regra 1</label>
    <input id="regra2" type="checkbox" name="regrasIds" value="2" /><label for="regra2">Regra 2</label>
    .
    .
    .
    

    E o seu controller deve estar preparado para receber um array de ids de usuarios e regras:

    public ActionResult RelacionarRegrasUsuarios(int[] usuariosIds, int[] regrasIds)
    {
    //código para relacionar os usuarios com as regras.
    //se voce estiver usando Entity sei como fazer isto.
    }
    Assim os itens selecionados nos checks viram nos arrays, a partir daí fazemos o código de relacionamento.
    Nos relacionamentos n para n que geralmente fazemos o uso do input checkbox não há outra saída a não ser trabalhar com as chaves das tabelas.

    Espero poder ajudado-lo. Qualquer dúvida favor entrar em contato.

    Douglas Aguiar
    MCAD, MCT
    quarta-feira, 14 de outubro de 2009 00:45
  • Douglas,

    Realmente assim funciona.

    Obrigado

    quarta-feira, 14 de outubro de 2009 01:37