How to take the value bound to a selectOneRadio and assign it to an attribute in a bean

Asked

Viewed 1,762 times

4

I request help to implement a method/way to take the value bound to a selectOneRadio (which is an Enum) and assign it to an attribute within a Bean.

After obtaining the value linked to selectOneRadio, I will pass it as a parameter to a method called newPessoa and so instantiate an attribute of type Person located in a class Client.

I am studying and in parallel developing a Java EE application using JSF, Primefaces and JPA. The main focus of learning is the use of Inheritance with JPA (hence the heritage of Java) and also Composition. I have chosen to use the JOINED inheritance strategy because I believe that in this way the tables in the database are more standardised. Therefore, I implemented 4 classes:

Person (abstract) Personal physique (inherits from Person) Personal (inherits from Person) Client (has a Person attribute since it can be either Personal or Personal)

At first I defined in the class Person an attribute type DEOP, which is an Enum composed by FISICA and JURIDICA, where the idea is: to link the values of this Enum to a "p:selectOneRadio" so that depending on the type that is selected (FISICO or JURIDICO) instantiate the Person object as Personal or Personal.

For this, I also implemented a class (using the Design Patterns Creation Factory Method) Personal factoty. This class has the newPessoa method that takes as a parameter a Personal type and depending on the type (FISICA or JURIDICA) a type of person is instantiated.

Below is the image of a class diagram to demonstrate the scenario of the relationship between the cited classes. Below are also the codes referring to the implementation of the classes.

PS: After completing this part of the implementation, I want to develop a way so that once the page is reinderized, the FISICA option is already selected, like this will be the default type of person, and there will also be a form for each type of person, If FISICA is selected, there will be fields of CPF, RG, etc., if it is JURIDICAL, there will be the fields CNPJ, Insc. State, etc., that is, the form will be dynamic.

Thanks in advance.

inserir a descrição da imagem aqui

Person

@Entity
@Table(name = "PESSOAS")
@Inheritance(strategy = InheritanceType.JOINED)
@DiscriminatorColumn(name = "PESS_TIPO")
public abstract class Pessoa implements Serializable {

private static final long serialVersionUID = 1L;

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "PESS_CODIGO", nullable = false)
private Integer codigo;

@Enumerated(EnumType.STRING)
@Column(name = "PESS_TIPO_DE_PESSOA")
private PessoaType tipoDePessoa;

@Column(name = "PESS_NOME", length = 100, nullable = false)
private String nome;

@Column(name = "PESS_FONE", length = 20, nullable = false)
private String telefone;

@OneToOne(mappedBy = "pessoa")
private Endereco endereco;

@Column(name = "PESS_OBSERVACAO", length = 255, nullable = true)
private String observacao;

@Column(name = "PESS_STATUS", length = 1, nullable = false)
private Boolean status;

@Temporal(TemporalType.TIMESTAMP)
@Column(name = "PESS_DATA_CADASTRO", nullable = false)
private Date dataCadastro;

@Version
@Column(name = "PESS_DATA_ALTERACAO", nullable = false)
private Timestamp dataAlteracao;

protected Pessoa() {

}
// Gets e Sets

Pessoa Física

@Entity
@Table(name = "PESSOA_FISICA")
@DiscriminatorValue(value = "PF")
@PrimaryKeyJoinColumn(name = "PESS_CODIGO")
public class PessoaFisica extends Pessoa implements Serializable {

private static final long serialVersionUID = 1L;

@Column(name = "PESF_CPF", length = 14, nullable = false)
private String cpf;

@Column(name = "PESF_RG", length = 14, nullable = false)
private String rg;

@Column(name = "PESF_ORGAO_EMISSOR_RG", length = 20, nullable = false)
private String orgaoEmissorRg;

@Column(name = "PESF_EMAIL", length = 65, nullable = true)
private String email;

@Column(name = "PESF_CELULAR", length = 14, nullable = true)
private String celular;

@Lob
@Column(name = "PESF_FOTO", nullable = true)
private byte[] foto;

@Temporal(TemporalType.DATE)
@Column(name = "PESF_DATA_NASCIMENTO", nullable = false)
private Date dataNascimento;

@Enumerated(EnumType.STRING)
@Column(name = "PESF_SEXO", nullable = false)
private SexoType sexo;

@OneToMany(mappedBy = "cliente")
private List<PedidoVenda> pedidos;

public PessoaFisica() {

}

Juridical Person

@Entity
@Table(name = "PESSOA_JURIDICA")
@DiscriminatorValue(value = "PJ")
@PrimaryKeyJoinColumn(name = "PESS_CODIGO")
public class PessoaJuridica extends Pessoa implements Serializable {

private static final long serialVersionUID = 1L;

@Column(name = "PESJ_NOME_FANTASIA", length = 100, nullable = false)
private String nomeFantasia;

@Column(name = "PESJ_CNPJ", length = 14, nullable = false)
private String cnpj;

@Column(name = "PESJ_INSCRICAO_ESTADUAL", length = 15, nullable = false)
private String inscricaoEstadual;

@Temporal(TemporalType.DATE)
@Column(name = "PESJ_VALIDADE_INSCRICAO_ESTADUAL", nullable = false)
private Date validadeInscricaoEstadual;

@Column(name = "PESJ_INSCRICAO_MUNICIPAL", length = 15, nullable = true)
private String inscricaoMunicipal;

@Column(name = "PESJ_HOME_PAGE", length = 100, nullable = true)
private String homePage;

@Column(name = "PESJ_FAX", length = 15, nullable = true)
private String fax;

public PessoaJuridica() {

}

Factory class to instantiate a person according to the type passed by parameter.

public class PessoaFactory {
public static Pessoa newPessoa(PessoaType tipo) {
    if (tipo == PessoaType.FISICA) {
        return new PessoaFisica();
    } else if (tipo == PessoaType.JURIDICA) {
        return new PessoaJuridica();
    } else {
        return null;
    }
}
}

Bean

@Named(value = "clienteBean")
@SessionScoped
public class ClienteBean extends Bean {

private static final long serialVersionUID = 1L;

@Inject
private ClienteService clienteService;

private Cliente cliente;

private Pessoa pessoa;

private Cliente clienteSelecionado;

private List<Cliente> clientes;

public void instanciarPessoa(ValueChangeEvent event) {

    HtmlSelectOneRadio radio = (HtmlSelectOneRadio) event.getComponent();
    PessoaType tipo = (PessoaType) radio.getValue();

    System.out.println(tipo);
}

public List<PessoaType> getTiposDePessoa() {
    return Arrays.asList(PessoaType.values());
}

public List<Cliente> getClientes() {
    try {
        if (clientes == null) {
            clientes = clienteService.listarTodosClientes();
        }
        return clientes;
    } catch (Exception e) {
        handleException(e);
        return null;
    }
}

public String novoCliente() {
    cliente = new Cliente();
    return redirect(Outcome.CADASTRO_CLIENTE);
}
}

Part of the XHTML file

<h:panelGrid columns="3">
    <h:outputLabel value="Tipo de Pessoa" for="tipoPessoa" />
        <p:selectOneRadio 
            id="tipoPessoa" 
            value="#{clienteBean.pessoa.tipoDePessoa}" 
            valueChangeListener="#{clienteBean.instanciarPessoa}">
            <f:selectItems 
                value="#{clienteBean.tiposDePessoa}" 
                var="tipoDePessoa" 
                itemValue="tipoDePessoa"
                itemLabel="#{tipoDePessoa.descricao}">
            </f:selectItems>
        </p:selectOneRadio>
</h:panelGrid>

1 answer

1

Assuming that you already have your Managerbean to control the registration system, I will assume that the name of your Bean is Personal Registrationbean, in it you must have a get method as follows:

 //
 private Pessoa pessoa;
 //Pega o tipo de pessoa que foi selecionada
 public Pessoa getPessoa() {
    return pessoa;
 }
 //Pega os valores de pessoas para exibir na página
 public TipoPessoa[] getTiposPessoas() {
    return TipoPessoa.values();
 }

On the registration page you should reference the method as below.

        <p:panelGrid columns="2" id="grid">
            <p:outputLabel value="Tipo" for="tipo" />
            <p:selectOneRadio id="tipo" 
                    value="#{CadastroPessoaBean.pessoa.tipoDePessoa}">
                    <f:selectItems value="#CadastroPessoaBean.tiposPessoas}"
                    var="tipoPessoa" itemValue="#{tipoPessoa}" 
                    itemLabel="#{tipoPessoa.descricao}" />
            </p:selectOneRadio>
        </p:panelGrid>

Enum:

public enum TipoPessoa {

  FISICA("Fisica"), 
  JURIDICA("Juridica");

  private String descricao;

  TipoPessoa(String descricao) {
      this.descricao = descricao;
  }

  public String getDescricao() {
      return descricao;
  }
}

Editing...

Now that you’ve picked up the amount, you must pass it to your Factory Method.

Something like that...

public abstract class PessoaFactory{

    protected abstract TipoPessoaInterface newPessoa();
//Aqui vai criar o tipo de pessoa
    public void criacao(Pessoa tipo) {
        newPessoa().criar(tipo);
    }
}

Inteface of your Factorymethod

public interface TipoPessoaInterface {
    public Pessoa criar(Pessoa tipo);
}

How you are using the Factorymethod has to have the classes that will be responsible for creating the object. Then you take this object created in the Client class to finish your registration.

  • Hi @Luiz the implementation suggestions you reported are very similar to the ones I had already created, except for the implementation of the Personal Factory class, because I created something simpler (due to lack of knowledge). I could not understand the last part of your answer regarding the classes responsible for creating the object and then take this object created in the Client class to finish the registration. Could you help me a little more? The difficulty is in taking the selected value in selectOneRadio and moving to the Personal classfactory, I think I should use a Valuechangeevent.

  • You can use the event to decide which fields should be filled in, in a single form. If the person marks Physics there you can enable the fields CPF and RG and leave Hidden the Legal fields. Then you would have only one Backbean to control this Person and Typodeperson record.. .

  • In your table Client would have a column of id_person for you to reference. And in the table Pessoa is already referencing the type by @Column(name = "PESS_TIPO_DE_PESSOA"). By the standard of the Factory Method you would have to have an object creation class for each type, I find it a little complicated, but it is quite interesting in case you have the possibility to add more types of people in your system, in addition to Legal and Physical, if never changed, then it would not be necessary.

  • 1

    That’s right @Luiz, in my Client class there is a Pessoa attribute (@Joincolumn(name = "PESS_CODIGO", nullable = false)) In the Personal classfactory the newPessoa method looks like this: 'public class Pessoafactory { public Static Pessoa newPessoa(Personal type) { if (type == Personal type.FISICA) { Return new Personal(); } Else if (type == Persontype.JURIDICA) { Return new Personjuridical(); } Else { Return null; } } }

  • What I had tried to implement in my Bean to get the selected value in selectOneRadio was a method like this: (sorry, I couldn’t put the formatted code) public void instancePessoa(Valuechangeevent Event) { htmlselectoneradio radio = (Htmlselectoneradio) Event.getComponent(); Personal type = (Personal type) radio.getValue(); System.out.println(type); } but it is not working to get the value, would know to inform me which class to use @Luiz, besides Htmlselectoneradio?

Browser other questions tagged

You are not signed in. Login or sign up in order to post.