OK - I'll be blunt. I can't see the value in this. If you really want it though, this is what you'll have to do.
Firstly, create a table org_max_post (org_id, post_id)
. Populate it when you add a new organisation (I'd use a database trigger).
Then, when adding a new post you will need to:
BEGIN
a transaction
SELECT FOR UPDATE
that organisation's row to lock it
- Increment the
post_id
by one, update the row.
- Use that value to create your post.
COMMIT
the transaction to complete your updates and release locks.
You want all of this to happen within a single transaction of course, and with a lock on the relevant row in org_max_post. You want to make sure that a new post_id gets allocated to one and only one post and also that if the post fails to commit that you don't waste post_id's.
If you want to get clever and reduce the SQL in your application code you can do one of:
- Wrap the hole lot above in a custom insert_post() function.
- Insert via a view that lacks the post_id and provides it via a rule/trigger.
- Add a trigger that overwrites whatever is provided in the post_id column with a correctly updated value.
Deleting a post obviously doesn't affect your org_max_post
table, so won't break your numbering.
Prevent any updates to the posts at the database level with a trigger. Check for any changes in the OLD vs NEW post_id
and throw an exception if there is one.
Then delete your existing redundant id column in your posts table and use (org_id,post_id) as your primary key. If you're going to this trouble you might as well use it as your pkey.
Oh - and post_num
or post_index
is probably better than post_id
since it's not an identifier.
I've no idea how much of this will play nicely with rails I'm afraid - the last time I looked at it, the database handling was ridiculously primitive.