mercredi 6 mai 2015

Nested object doesn't exposed with Gson

I'm developing a web application with JPA and I need to return some database queries results as Json objects. I'm using Google Gson class for this. I have two related classes: Medico and Usuario. Medico contains an instance of Usuario. However I had added the annotation @Expose in the nested Usuario object, this attribute is not rendered when the final json is generated by my web service. How can I expose the inner Usuario object correctly?

Below is part of Medico class code:

@Entity
@Table(name = "medico")
@XmlRootElement

  public class Medico implements Serializable {

    @Size(max = 15)
    @Column(name = "duracao_consulta", length = 15)
    private String duracaoConsulta;
    @OneToMany(cascade = CascadeType.ALL, mappedBy = "medico", fetch = FetchType.LAZY)
    private Collection<Descansosemanal> descansosemanalCollection;
    @JoinTable(name = "medico_secretario", joinColumns = {
    @JoinColumn(name = "medico_id", referencedColumnName = "id")}, inverseJoinColumns = {
    @JoinColumn(name = "secretario_id", referencedColumnName = "id")})
    @ManyToMany(fetch = FetchType.LAZY)
    private Collection<Usuario> secretarioCollection;
    @Column(name = "valor_consulta", precision = 17, scale = 17)
    private Double valorConsulta;
    private static final long serialVersionUID = 1L;
    @Expose
    @Id
    @Basic(optional = false)
    @Column(name = "id", nullable = false)
    @SequenceGenerator(name = "medico_Generator", sequenceName = "Medico_id_seq", allocationSize = 1)
   @GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "medico_Generator")
    private Integer id;

    @Expose
    @Basic(optional = false)
    @NotNull
    @Size(min = 1, max = 150)
    @Column(name = "crm", nullable = false, length = 150)
    private String crm;

    @ManyToMany(mappedBy = "medicoCollection", fetch = FetchType.LAZY)
    private Collection<Convenio> convenioCollection;
    @OneToMany(mappedBy = "medico", fetch = FetchType.LAZY)
    private Collection<Horarios> horariosCollection;

    @Expose
    @JoinColumn(name = "usuario_id", referencedColumnName = "id", nullable = false)
    @ManyToOne(optional = false, fetch = FetchType.LAZY)
    private Usuario usuario;
    @Expose
    @JoinColumn(name = "especialidade_id", referencedColumnName = "id", nullable = false)
    @ManyToOne(optional = false, fetch = FetchType.LAZY)
    private Especialidade especialidade;
    @OneToMany(mappedBy = "medico", fetch = FetchType.LAZY)
    private Collection<Historico> historicoCollection;
    @OneToMany(cascade = CascadeType.ALL, mappedBy = "medico", fetch = FetchType.LAZY)

...
 }

Part of the Usuario class code:

   @Entity
   @Table(name = "usuario", uniqueConstraints = {
   @UniqueConstraint(columnNames = {"email"})})
   @XmlRootElement

   public class Usuario implements Serializable {

private static final long serialVersionUID = 1L;
@Expose
@Id
@Basic(optional = false)
@Column(name = "id", nullable = false)
@SequenceGenerator(name = "usr_Generator", sequenceName = "usuario_id_seq", allocationSize = 1)
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "usr_Generator")
private Integer id;
@Expose
@Basic(optional = false)
@NotNull
@Size(min = 1, max = 250)
@Column(name = "nome", nullable = false, length = 250)
private String nome;
@Expose
@Size(max = 20)
@Column(name = "cpf", length = 20)
private String cpf;

@Expose
@Basic(optional = false)
@NotNull
@Size(min = 1, max = 50)
@Column(name = "senha", nullable = false, length = 50)
private String senha;

@Expose
@Size(max = 20)
@Column(name = "telefone", length = 20)
private String telefone;

@Expose
@Size(max = 20)
@Column(name = "celular", length = 20)
private String celular;

@Expose
@Size(max = 250)
@Column(name = "logradouro", length = 250)
private String logradouro;

@Expose
@Size(max = 10)
@Column(name = "numero_endereco", length = 10)
private String numeroEndereco;

@Expose
@Size(max = 150)
@Column(name = "bairro", length = 150)
private String bairro;

@Expose
@Size(max = 150)
@Column(name = "cidade", length = 150)
private String cidade;

@Expose
@Size(max = 2)
@Column(name = "estado", length = 2)
private String estado;

@Expose
@Basic(optional = false)
@NotNull
@Column(name = "nascimento", nullable = false)
@Temporal(TemporalType.DATE)
private Date nascimento;
// @Max(value=?)  @Min(value=?)//if you know range of your decimal fields consider using these annotations to enforce field validation
@Expose
@Column(name = "latitude", precision = 17, scale = 17)
private Double latitude;
@Expose
@Column(name = "longitude", precision = 17, scale = 17)
private Double longitude;
@Expose
@Column(name = "active")
private Boolean active;
@Expose
@Basic(optional = false)
@NotNull
@Size(min = 1, max = 100)
@Column(name = "email", nullable = false, length = 100)
private String email;

@Expose
@Size(max = 150)
@Column(name = "foto", length = 150)
private String foto;

@Expose
@Column(name = "data_adesao")
@Temporal(TemporalType.DATE)
private Date dataAdesao;

@Expose
@OneToOne(cascade = CascadeType.ALL, mappedBy = "usuario", fetch = FetchType.LAZY)
private Grupo grupo;

@Expose
@JoinColumn(name = "categoria_id", referencedColumnName = "id")
@ManyToOne(fetch = FetchType.LAZY)
private Categoria categoria;

@OneToMany(mappedBy = "remetente", fetch = FetchType.LAZY)
private Collection<Mensagem> mensagemCollection;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "destinatario", fetch = FetchType.LAZY)
private Collection<Mensagem> mensagemCollection1;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "usuario", fetch = FetchType.LAZY)
private Collection<Funcionario> funcionarioCollection;
@OneToMany(mappedBy = "usuario", fetch = FetchType.LAZY)
private Collection<Pagamentos> pagamentosCollection;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "usuario", fetch = FetchType.LAZY)
private Collection<Medico> medicoCollection;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "usuario", fetch = FetchType.LAZY)
private Collection<Historico> historicoCollection;
@OneToMany(mappedBy = "usuario", fetch = FetchType.LAZY)
private Collection<Agendamento> agendamentoCollection;

...
}

Finally, the method that generates a Json list of Medico objects:

   @GET
   @Path("listar")
   @Produces("application/json; charset=ISO-8859-1")

   public String lista() {

    String json = "";

     Gson gson = new GsonBuilder().excludeFieldsWithoutExposeAnnotation ().create();
    json = gson.toJson(MedicoFachada.listar());
    return json;
 }

The excerpt medicoFachada.listar()) returns a result of a select in the database, table Medico, and it is working fine. The final Json result, however, doesn't include the nested Usuario object:

[{"id":33,"crm":"xxx"},{"id":15,"crm":"xxx"},{"id":16,"crm":"xxx"},{"id":17,"crm":"xxx"},{"id":19,"crm":"xxx"},{"id":20,"crm":"xxx"},{"id":21,"crm":"xxx"},{"id":22,"crm":"xxx"},{"id":23,"crm":"xxx"},{"id":24,"crm":"xxx"},{"id":25,"crm":"xxx"},{"id":27,"crm":"xxx"},{"id":28,"crm":"xxx"},{"id":29,"crm":"xxx"},{"id":30,"crm":"xxx"},{"id":14,"crm":"xxxxx"},{"id":31,"crm":"xxx"},{"id":32,"crm":"xxx"},{"id":36,"crm":"xxx"},{"id":37,"crm":"abc123"},{"id":38,"crm":"abc123"},{"id":39,"crm":"asd"},{"id":40,"crm":",mn,jkj"},{"id":41,"crm":"asas"},{"id":42,"crm":"jl"},{"id":43,"crm":"asa"},{"id":44,"crm":"jhkj"},{"id":50,"crm":"sdf"},{"id":51,"crm":"asd"},{"id":52,"crm":"165464"},{"id":53,"crm":"asdasd"},{"id":54,"crm":"asdasd"},{"id":55,"crm":"ssdf"},{"id":56,"crm":"123"}]




Aucun commentaire:

Enregistrer un commentaire