Solucionado (ver solução)
Solucionado
(ver solução)
3
respostas

Atributo nulo no banco

O caminho da capa do livro não está ficando salvo no banco, porém a imagem está salvando na pasta casadocodigo/livros como no curso , o que poder ser? Segue as classes relativas a isso:

package br.com.casadocodigo.beans;

import java.io.IOException;
import java.util.List;

import javax.enterprise.context.RequestScoped;
import javax.faces.application.FacesMessage;
import javax.faces.context.FacesContext;
import javax.inject.Inject;
import javax.inject.Named;
import javax.servlet.http.Part;

import br.com.casadocodigo.dao.AutorDao;
import br.com.casadocodigo.dao.LivroDao;
import br.com.casadocodigo.infra.FileSaver;
import br.com.casadocodigo.models.Autor;
import br.com.casadocodigo.models.Livro;

@Named
@RequestScoped
public class AdminLivrosBean {

    private Livro livro = new Livro();

    @Inject
    private LivroDao dao;

    @Inject
    private AutorDao AutorDao;

    @Inject
    private FacesContext context;

    private Part capaLivro;


    public String salvar() throws IOException {

        dao.salvar(livro);

        FileSaver fileSaver = new FileSaver();
        livro.setCapaPath(fileSaver.write(capaLivro, "livros"));


        context.getExternalContext().getFlash().setKeepMessages(true);        
        context.addMessage(null,new FacesMessage("Livro cadastrado com sucesso!"));

        return "/livros/lista?faces-redirect=true";
    }

    public List<Autor> getAutores() {
        return AutorDao.listar();
    }

    public Livro getLivro() {
        return livro;
    }

    public void setLivro(Livro livro) {
        this.livro = livro;
    }

    public Part getCapaLivro() {
        return capaLivro;
    }

    public void setCapaLivro(Part capaLivro) {
        this.capaLivro = capaLivro;
    }


}
package br.com.casadocodigo.models;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Lob;
import javax.persistence.ManyToMany;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.validation.constraints.DecimalMin;
import javax.validation.constraints.Min;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;

import org.hibernate.validator.constraints.Length;
import org.hibernate.validator.constraints.NotBlank;

@Entity
public class Livro {

    @Id @GeneratedValue(strategy=GenerationType.IDENTITY)
    private Integer id;

    @NotBlank
    private String titulo;

    @Lob
    @NotBlank
    @Length(min=10)
    private String descricao;

    @DecimalMin("20")
    private BigDecimal preco;

    @Min(50)
    private Integer numeroPaginas;

    @ManyToMany
    @Size(min=1)
    @NotNull
    private List<Autor> autores = new ArrayList<>();

    @Temporal(TemporalType.DATE)
    private Calendar dataPublicacao;

    private String capaPath;    

    public String getTitulo() {
        return titulo;
    }

    public void setTitulo(String titulo) {
        this.titulo = titulo;
    }

    public String getDescricao() {
        return descricao;
    }

    public void setDescricao(String descricao) {
        this.descricao = descricao;
    }

    public Integer getNumeroPaginas() {
        return numeroPaginas;
    }

    public void setNumeroPaginas(Integer numeroPaginas) {
        this.numeroPaginas = numeroPaginas;
    }

    public BigDecimal getPreco() {
        return preco;
    }

    public void setPreco(BigDecimal preco) {
        this.preco = preco;
    }

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public List<Autor> getAutores() {
        return autores;
    }

    public void setAutores(List<Autor> autores) {
        this.autores = autores;
    }

    @Override
    public String toString() {
        return "Livro [id=" + id + ", titulo=" + titulo + ", descricao=" + descricao + ", numeroPaginas="
                + numeroPaginas + ", preco=" + preco + ", autores=" + autores + "]";
    }

    public Calendar getDataPublicacao() {
        return dataPublicacao;
    }

    public void setDataPublicacao(Calendar dataPublicacao) {
        this.dataPublicacao = dataPublicacao;
    }

    public String getCapaPath() {
        return capaPath;
    }

    public void setCapaPath(String capaPath) {
        this.capaPath = capaPath;
    }


}
package br.com.casadocodigo.infra;

import java.io.IOException;

import javax.servlet.http.Part;

public class FileSaver {

    private static final String SERVER_PATH = "/casadocodigo";

    public String write(Part arquivo, String path) {
        String relativePath = path + "/" + arquivo.getSubmittedFileName();
        try {
            arquivo.write(SERVER_PATH + "/" + relativePath);

            return relativePath;
        } catch(IOException ex) {
            throw new RuntimeException(ex);
        }
    }

    public static String getServerPath() {
        return SERVER_PATH;
    }
}
3 respostas

Faltou o formulário

<?xml version="1.0" encoding="ISO-8859-1" ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
    xmlns:h="http://xmlns.jcp.org/jsf/html"
    xmlns:f="http://xmlns.jcp.org/jsf/core">

<h:body>
    <h:form enctype="multipart/form-data">
        <div>
            <h:outputLabel value="Título:" />
            <h:inputText value="#{adminLivrosBean.livro.titulo}" required="true"
                id="titulo" />
            <h:message for="titulo" />
        </div>
        <div>
            <h:outputLabel value="Descrição:" />
            <h:inputTextarea rows="4" cols="20"
                value="#{adminLivrosBean.livro.descricao}" required="true"
                id="descricao" />
            <h:message for="descricao" />
        </div>
        <div>
            <h:outputLabel value="Número de Páginas:" />
            <h:inputText value="#{adminLivrosBean.livro.numeroPaginas}"
                required="true" id="numeroPaginas" />
            <h:message for="numeroPaginas" />
        </div>
        <div>
            <h:outputLabel value="Preço:" />
            <h:inputText value="#{adminLivrosBean.livro.preco}" required="true"
                id="preco" />
            <h:message for="preco" />
        </div>
        <div>
            <h:outputLabel value="Autores:" />
            <h:selectManyListbox value="#{adminLivrosBean.livro.autores}"
                converter="autorConverter" id="autores">
                <f:selectItems value="#{adminLivrosBean.autores}" var="autor"
                    itemValue="#{autor}" itemLabel="#{autor.nome}" />
            </h:selectManyListbox>
            <h:message for="autores" />
        </div>

        <div>
            <h:outputLabel value="Data de publicação:" />
            <h:inputText value="#{adminLivrosBean.livro.dataPublicacao}"
                required="true" id="data" />
            <h:message for="data" />
        </div>
        <div>
            <h:outputLabel value="Capa do Livro" />
            <h:inputFile value="#{adminLivrosBean.capaLivro}" id="capaLivro" />
            <h:message for="capaLivro" />
        </div>

        <h:commandButton value="Cadastrar" action="#{adminLivrosBean.salvar}" />

    </h:form>
</h:body>

</html>
solução!

Tudo bem, Patrick?

Tenta primeiro setar o path da capa e depois salvar? No seu AdminLivrosBean, no método salvar() ficaria assim:

public void salvar() {
    FileSaver fileSaver = new FileSaver();
    String capaPath = fileSaver.write(capaLivro, "livros");
    livro.setCapaPath(capaPath);
    // depois que seta a capa, salva
    dao.salvar(livro);

    // restante do código
}

Avisa se deu certo?

Um abraço.

Era isso mesmo, valeu pela ajuda.

Quer mergulhar em tecnologia e aprendizagem?

Receba a newsletter que o nosso CEO escreve pessoalmente, com insights do mercado de trabalho, ciência e desenvolvimento de software