When giving transition rollback, reset id to the last id actually inserted

Asked

Viewed 91 times

0

I want to avoid having jumps in the auto increment of id, in case there’s a mistake and I make it rollback in my transaction. And at the same time I want to make sure that no mistake happens if I change the auto-increment, in case of simultaneous accesses and etc.

Exp:

inserir a descrição da imagem aqui

The best option would be something like this?:

ALTER TABLE sales_order AUTO_INCREMENT =(SELECT MAX(id_sales_order)+1 FROM sales_order)

I wanted to take advantage of the tip and see if there are better practices to save data in a database

I know that from the moment we talk about best practices, the chance of my question being negative and closed is great, but I wanted a suggestion from more experienced users, if possible.

My commented structure:

$id = $_POST["id"];
//Abro a conexão
$db = new PDO('ok');
//Inicio da transação
$db->beginTransaction();
//Seto para pegar qualquer erro de sql
$db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$db->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);

try {
    $sql = "INSERT INTO sales_order (total_price) VALUES ($id,0)";
    $stmt = $db->prepare($sql);
    $stmt->execute();
    //Pego o último id inserido
    $lastId = $db->lastInsertId();
    //Gero um hash com esse id utilizando a biblioteca
    $hash_id = generate_hash_id($lastId);
    $sql = "UPDATE sales_order SET hashed_id ='".$hash_id."' WHERE id_sales_order = ".$lastId;
    $stmt = $db->prepare($sql);
    $stmt->execute();
} catch (PDOException $e) {
    if ($e != ""){
        //Seto erro 500 no header da resposta
        header($_SERVER["SERVER_PROTOCOL"]." 500 Internal Server Error");
        //Salvo em um arquivo .txt o log do erro com a data e hora
        date_default_timezone_set( 'America/Sao_Paulo' );
        $filename = 'log-errors.log';
        file_put_contents( $filename, '[START]'.PHP_EOL.date( 'r' ).PHP_EOL.$e.PHP_EOL.'[END]'.PHP_EOL, FILE_APPEND );
        //Realizo rollBack de todas alterações feitas na transação
        $db->rollBack();
        die();
    }
}
//Dou um commit em todas alterações feitas na transação
$db->commit();
echo '{"status":200}';

Library source: Hashids

All

  • 2

    Not directly solving your problem, but just to warn: normally an application should not depend on the existence of continuous Ids. The goal of autonumbering is not this. If you want to implement a sequential control, you need another mechanism, or auxiliary table. Auto-generated ids are for bank integrity and consistency, not application-client business rules.

  • Rs will take this into account @

  • This issue of the id skipping on each transition not made has always been a touch of mine, if it is not possible or not practicable, is as tip same

  • 2

    Your alter table solution works, only you may have competition issues. You would need to make a general lock to not happen to have 2 alter with wrong dice. Also, if it is open transaction, it will be a wicked roll. Unless you centralize the management of Ids in a single process (for example, a PHP running in the background with exclusivity in this reorganization). I can’t see a simple and "automatic way".

  • 1

    Another thing you can do is wait for the transaction to work, and save a sequential ID in an independent column, but you need to be aware that parallel processes don’t get the same number. How do you do in this case if you delete the record 10 when you are in the 89?

  • The proposed idea is that no record should ever be deleted, something that could fit the question, taking into account what you said (when deleting a record), is when (never, possibly and probably, but taking into account what happens) ids pop on the last possible option, it would come back and pay for every available id. I know that in Oracle there is a way to do this management, in the other company that I worked dba had applied this rule

  • Recycling is a very simple way to leave no hole, but there is unfolding: if they need to be in the order of release (usually when there can be no hole, it is usually necessary to keep the sequence too). Another simple way is in this part of the program, use full lock anyway, so you only have one transaction at a time. It doesn’t even need autonumbering, only a MAX( column ) + 1 - only there it has to be a system that does not depend on parallelism in the inserts (it is feasible in systems of little competition in the Insert)

  • In the modeling, were created fields of "created in" and "changed in" in each table, so for control of order of release I think the solution of keeping the holes would not be a problem, my doubt now as it would be set to use them when the sequential ids run out

Show 3 more comments
No answers

Browser other questions tagged

You are not signed in. Login or sign up in order to post.