Why does Postgres generate an already used PK value?

PostgreSQL will not try to insert duplicate values on its own, it is you (your application, ORM included) who does.

It can be either a sequence feeding the values to the PK set to the wrong position and the table already containing the value equal to its nextval() - or simply that your application does the wrong thing. The first one is easy to fix:

SELECT setval('your_sequence_name', (SELECT max(id) FROM your_table));

The second one means debugging.

Django (or any other popular framework) doesn't reset sequences on its own - otherwise we would have similar questions every other day.


You are most likely tying to insert a row in a table for which the serial column sequence value is not updated.

Consider following column in your table which is primary key defined by Django ORM for postgres

id serial NOT NULL

Whose default value is set to

nextval('table_name_id_seq'::regclass)

The sequence is only evaluated when the id field is set as blank. But that is problem if there are already entries into the table.

Question is why didn't those earlier entries trigger sequence update? That is because the id value were explicitly provided for all the earlier entries.

In my case those initial entries were loaded from fixtures through migrations.

This issue can also get tricky via custom entries with random PK value.

Say for eg. There are 10 entries into your table. You make an explicit entry with PK=15. The next four inserts through code would work perfectly fine but the 5th one would raise an exception.

DETAIL: Key (id)=(15) already exists.

I ended up here with very same error, which was occurring rarely, and was hard to track, because I was looking for it not where I should.

Fault was JS repetition which was doing the POST to the server twice! So sometimes it is worth to have a look not only on your django (or any other web framework) views and forms but also what happens on very front side.