Duvida Erro de Chave primaria duplicada

6 respostas
T

Boa noite pessoal.
Estou com uma duvida em relação a chave primaria. De acordo com os bancos de dados a chave nao pode ser duplicada, ou seja, nao poderia haver 2 entradas com o mesmo valor.
E entao vem minha duvida. Eu queria que quando a pessoa inserisse ou editasse um valor que ja existisse no banco aparecesse a msg falando pro usuario que a chave ja existe e nao poderia ser inserida.
Entretando nao sei como fazer... apenas aparece o erro no java. alguem poderia me dar uma força?

segue o codigo no qual me refiro.

public void actionPerformed(ActionEvent e) {
			if(e.getSource()==Atualizar)
			{
				try
		    	{  
				
					   
					Connection con = DriverManager.getConnection("jdbc:mysql://localhost/prol","root", "");
					 Statement st = con.createStatement();
					 st.executeUpdate("	update computador set nome ='"+txNome.getText()+"'where nome='"+NomeParam+"'");
					 st.executeUpdate("	update computador set usuario ='"+txUsuario.getText()+"'where nome='"+NomeParam+"'");
					 st.executeUpdate("	update computador set configuracao ='"+txConfig.getText()+"'where nome='"+NomeParam+"'");
					 st.executeUpdate("	update computador set setor ='"+txSetor.getText()+"'where nome='"+NomeParam+"'");
					 st.executeUpdate("	update computador set proprietario ='"+Proprietario+"'where nome='"+NomeParam+"'");
					 st.executeUpdate("	update computador set observacao ='"+txObservacao.getText()+"'where nome='"+NomeParam+"'");

						
					modelo.setValueAt(txNome.getText(), row, 0);
					modelo.setValueAt(txUsuario.getText(), row, 1);
					modelo.setValueAt(txConfig.getText(), row, 2);
					modelo.setValueAt(txSetor.getText(), row, 3);
					modelo.setValueAt(Proprietario, row, 4);
					modelo.setValueAt(txObservacao.getText(), row, 5);
					
				con.close();
			}
			  
	        catch (SQLException sqlex)
	        { 
	        
	           System.out.println("erro sql "+ sqlex);
	           sqlex.printStackTrace();  
			}

Eu fechando a conexao dentro do try, tem algum problema? pq teoricamente estou criando dentro do try tbm, não?

valeu.

6 Respostas

dreampeppers99

Uma consulta antes já resolve, e não é tão custosa já que é baseada num campo indexado.

if (chaveExistente(entidade.chave)){ throw new ChaveJaExistenteException("Chave existente ..."); } else { salveRegistro(entidade); }
Outra forma seria tratar a exceção (que varia de banco a banco, acho que tem um código [o JDBC4 veio pra resolver isso] que é comum… mess around)

T

hum… entendi… pq o que é ruim, é que eu coloquei um joptionpane falando “Dados atualizado com sucesso” ou “Dados inseridos” e atras do programa aparece o erro no java falando que a chave primaria ja existe. portanto o usuario pensa que foi inserido ou atualizado os valores mas na verdade nao aconteceu nada…

jks1903

tarlix, só uma pergunta.

Por que tantos updates?

Não é possível simplificar e fazer um só?

drsmachado
Algumas dicas:

1 - Para evitar tais problemas, mantenha a chave primária como auto increment (mysql), sequenciada (oracle ou postgres) ou identada (sqlserver) e permita que somente o background do sistema gerencie isto (afinal, não vejo isto como responsabilidade do usuário e sim do programa). Você até pode mostrar o código ao usuário, após a inserção, mas apenas como informação, não como responsabilidade do mesmo gerenciar (caso ele tenha que inserir ou atualizar 500 itens, ele dará conta de lembrar todos?);

2 - Separe as coisas, você está fazendo acesso ao banco diretamente da tela, isso é uma péssima prática de programação.

3 - Não use STATEMENT. Prefira o PreparedStatement, cuja sintaxe torna a operação menos vulnerável e mais limpa, embora  utilizar mais linhas de programação;

4 - O excesso de chamadas ao update tornará tua aplicação lenta, tudo isto pode ser resolvido com um único update, tendo em vista que se trata da mesma tabela.

5 - Evite colocar as mensagens de erro sql para o usuário, dificilmente ele irá compreendê-las (pense num erro como Column count does not match). Prefira apenas mostrar Erro ao salvar / atualizar e grave um log para consultar e verificar o erro;
T

Como eu poderia fazer esse update em uma unica chamada?

Pq tipo, cada update é uma coluna diferente, e como eu nao sei qual coluna o usuario editou, se editaria todas as colunas eu fiz o update assim… poderia me falar como posso corrigir este erro?

drsmachado, coloquei IP como uma chave primaria até pq nao é possivel ter 2 computadores(impressoras) com o mesmo IP, por isso nao usei o auto_increment.

drsmachado

tarlix:
Como eu poderia fazer esse update em uma unica chamada?

Pq tipo, cada update é uma coluna diferente, e como eu nao sei qual coluna o usuario editou, se editaria todas as colunas eu fiz o update assim… poderia me falar como posso corrigir este erro?

Camarada, o custo do update será quase o mesmo, visto que o banco deleta e depois grava a linha referida no where.
Se você for estudar, um dia, um framework como o hibernate, verá que ele age assim, independente do número de colunas, ele atualiza todas elas, mesmo que o usuário tenha atualizado apenas uma, em uma tabela de 100 colunas.
Algo assim…

st.executeUpdate(" update computador set nome ='"+txNome.getText()+"'where nome='"+NomeParam+"',
				 set usuario ='"+txUsuario.getText()+"'where nome='"+NomeParam+"',
				 set configuracao ='"+txConfig.getText()+"'where nome='"+NomeParam+"',
				 set setor ='"+txSetor.getText()+"'where nome='"+NomeParam+"',
				 set proprietario ='"+Proprietario+"'where nome='"+NomeParam+"',
				 set observacao ='"+txObservacao.getText()+"'where nome='"+NomeParam+"'");
Criado 13 de julho de 2011
Ultima resposta 14 de jul. de 2011
Respostas 6
Participantes 4