Solucionado (ver solução)
Solucionado
(ver solução)
1
resposta

[Dúvida] PostgreSQL não refletiu automaticamente novos itens do Enum

Boa tarde, Colegas e Instrutores

Durante testes dos exercícios do Screematch" aqui do curso, decidi incluir mais algumas enumerações de Categoria, mas as novas possibilidades não atualizaram automaticamente nas "constraints" da tabela séries.

Na primeira execução da aplicação, a tabela foi criada correta e automaticamente com essa definição:

CONSTRAINT series_genero_check CHECK (genero::text = ANY (ARRAY['ACAO'::character varying, 'COMEDIA'::character varying, 'DRAMA'::character varying, 'CRIME'::character varying, 'TERROR'::character varying, 'MISTERIO'::character varying, 'FANTASIA'::character varying, 'ROMANCE'::character varying]::text[]))

Na execução seguinte, escolhi uma série cujo genêro não se encaixa nas opções de Categoria: após inserir os itens "Aventura" e "Ficção", o Enum passou a funcionar, mas passou a dar erro no SQL:

2025-07-03T16:05:48.886-03:00  WARN 17528 --- [           main] o.h.engine.jdbc.spi.SqlExceptionHelper   : SQL Error: 0, SQLState: 23514
2025-07-03T16:05:48.886-03:00 ERROR 17528 --- [           main] o.h.engine.jdbc.spi.SqlExceptionHelper   : ERRO: a nova linha da relação "series" viola a restrição de verificação **"series_genero_check"**

Para fins didáticos, eu consigo resolver fazendo o DROP TABLE da tabela "série" pelo próprio pgAdmin, "forçando" que ela seja recriada quando executar novamente a aplicação: infelizmente, nessa opção os dados são perdidos.

Existe alguma ação que a aplicação "force" essa alteração de estrutura no banco de dados? Ou alterações como esta só são possíveis diretamente no PostgreSQL?

Vou transcrever abaixo como está meu arquivo de propriedades:

spring.datasource.url=jdbc:postgresql://${DB_HOST}/${DB_NAME}
spring.datasource.username=${DB_USER}
spring.datasource.password=${DB_PASSWORD}
spring.datasource.driver-class-name=org.postgresql.Driver
hibernate.dialect=org.hibernate.dialect.PostgreSQLDialect
spring.jpa.hibernate.ddl-auto=update

Obrigado.

1 resposta
solução!

Olá! Tudo bem?

Quando você adiciona novos valores a um enum, o Spring Data JPA, por padrão, não atualiza automaticamente as constraints do banco de dados. Isso ocorre porque o spring.jpa.hibernate.ddl-auto=update não cobre alterações em constraints de enum.

Para resolver isso sem perder dados, você pode seguir algumas abordagens:

  1. Alterar a Constraint Manualmente: Você pode alterar a constraint diretamente no PostgreSQL usando um comando SQL. Aqui está um exemplo de como você pode fazer isso:

    ALTER TABLE series DROP CONSTRAINT series_genero_check;
    ALTER TABLE series ADD CONSTRAINT series_genero_check CHECK (genero::text = ANY (ARRAY['ACAO', 'COMEDIA', 'DRAMA', 'CRIME', 'TERROR', 'MISTERIO', 'FANTASIA', 'ROMANCE', 'AVENTURA', 'FICCAO']::text[]));
    

    Isso remove a constraint antiga e adiciona uma nova com os valores atualizados.

  2. Usar Migrations: Outra abordagem mais robusta seria usar uma ferramenta de migração de banco de dados, como Flyway ou Liquibase. Essas ferramentas permitem que você gerencie alterações no esquema do banco de dados de forma controlada e versionada. Você pode criar um script de migração para atualizar a constraint.

  3. Script SQL no Startup: Se você preferir, pode executar um script SQL no início da aplicação para alterar a constraint. Isso pode ser feito programaticamente ao iniciar a aplicação, garantindo que a constraint esteja sempre atualizada.

Essas abordagens ajudam a manter a integridade dos dados sem a necessidade de recriar tabelas e perder informações.

Espero ter ajudado e bons estudos!

Caso este post tenha lhe ajudado, por favor, marcar como solucionado ✓.