Ottieni il valore AUTO_INCREMENT corrente per qualsiasi tabella


294

Come posso ottenere l'attuale valore AUTO_INCREMENT per una tabella in MySQL?


31
Questa domanda non è necessariamente un duplicato. La domanda collegata richiede il conteggio delle righe e la risposta accettata riceve SOLO il conteggio delle righe, NON AUTO_INCREMENT, che è una domanda completamente diversa.
methai,

Risposte:


569

Puoi ottenere tutti i dati della tabella usando questa query:

SHOW TABLE STATUS FROM `DatabaseName` WHERE `name` LIKE 'TableName' ;

È possibile ottenere esattamente queste informazioni utilizzando questa query:

SELECT `AUTO_INCREMENT`
FROM  INFORMATION_SCHEMA.TABLES
WHERE TABLE_SCHEMA = 'DatabaseName'
AND   TABLE_NAME   = 'TableName';

34
Può anche utilizzare al DATABASE()posto del nome del database esplicito.
M. Suleiman,

22
Nota: DATABASE () è NULL se non è stato emesso un comando USE DATABASE
methai

5
C'è una ragione per cui non puoi SELECT MAX(id) FROM table_name?
Brian

43
cosa succede se hai eliminato l'ultimo record? max non ti fornirà l'attuale auto_increment
peterpeterson

3
Questo dà l'ultimo valore AUTO_INCREMENT nella tabella o quale sarà il valore successivo?
Sidx,

18

Credo che tu stia cercando la funzione LAST_INSERT_ID () di MySQL . Se nella riga di comando, esegui semplicemente quanto segue:

LAST_INSERT_ID();

È inoltre possibile ottenere questo valore tramite una query SELECT:

SELECT LAST_INSERT_ID();

3
Non è la migliore idea aggiungerne uno e aspettarsi, sarà l'ID della riga successiva. Nel frattempo un'altra transazione potrebbe inserire una nuova riga e useresti l'ID sbagliato giusto?
agim

Hai ragione. Immagino che dipenda dall'ambiente in cui ti trovi. Se si tratta di un ambiente di test controllato, molto probabilmente potresti aggiungerne uno ed essere al sicuro. La migliore risposta è stata fornita da Methai.
jvdub,

2
Qual è la risposta migliore, dipende da cosa vuoi ottenere. Se si inserisce una nuova riga e si desidera conoscere l'ID creato, la risposta è la risposta migliore, poiché LAST_INSERT_ID () è sicuro per le transazioni e garantisce che si ottenga l'ID per l'oggetto creato. Ho votato a favore della tua risposta, ma eliminerei la parte con "aggiungine una ..."
agim

25
LAST_INSERT_ID () è per connessione. Ciò significa che se un altro processo inserisce tre righe aggiuntive dopo di te, la tua chiamata LAST_INSERT_ID () sarà diversa dalla loro. Questa domanda richiede l'attuale AUTO_INC val sulla tabella stessa.
methai,

2
Se l'ultima istruzione INSERT ha inserito più di una riga, questo ti darà la risposta sbagliata. Documentazione MySQL (enfasi aggiunta): "LAST_INSERT_ID () restituisce un valore a 64 bit che rappresenta il primo valore generato automaticamente inserito correttamente per una colonna AUTO_INCREMENT come risultato dell'istruzione INSERT eseguita più di recente." Intuitivo! dev.mysql.com/doc/refman/5.6/en/…
Charlie

15

Se vuoi solo conoscere il numero, anziché ottenerlo in una query, puoi usare:

SHOW CREATE TABLE tablename;

Dovresti vedere l'auto_increment in fondo


5
Questo non sembra funzionare se la tabella non ha righe e auto_increment è attivo 1.
Pacerier,

6

Anche se la risposta di methai è corretta se si esegue manualmente la query, si verifica un problema quando 2 transazioni / connessioni simultanee eseguono effettivamente questa query in fase di esecuzione in produzione (ad esempio).

Ho appena provato manualmente nel workbench di MySQL con 2 connessioni aperte contemporaneamente:

CREATE TABLE translation (
  id BIGINT PRIMARY KEY AUTO_INCREMENT
);
# Suppose we have already 20 entries, we execute 2 new inserts:

Transazione 1:

21 = SELECT `AUTO_INCREMENT` FROM INFORMATION_SCHEMA.TABLES
     WHERE TABLE_SCHEMA = 'DatabaseName' AND TABLE_NAME = 'translation';

insert into translation (id) values (21);

Transazione 2:

21 = SELECT `AUTO_INCREMENT` FROM INFORMATION_SCHEMA.TABLES
     WHERE TABLE_SCHEMA = 'DatabaseName' AND TABLE_NAME = 'translation';

insert into translation (id) values (21);

# commit transaction 1;
# commit transaction 2;

L'inserimento della transazione 1 è corretto: l'inserimento della transazione 2 è errato: Codice errore: 1062. Voce duplicata '21' per la chiave 'PRIMARY'.

Una buona soluzione sarebbe la risposta di jvdub perché per transazione / connessione i 2 inserti saranno:

Transazione 1:

insert into translation (id) values (null);
21 = SELECT LAST_INSERT_ID();

Transazione 2:

insert into translation (id) values (null);
22 = SELECT LAST_INSERT_ID();

# commit transaction 1;
# commit transaction 2;

Ma dobbiamo eseguire last_insert_id () subito dopo l'inserimento! E possiamo riutilizzare quell'id da inserire in altre tabelle in cui è prevista una chiave esterna!

Inoltre, non possiamo eseguire le 2 query come segue:

insert into translation (id) values ((SELECT AUTO_INCREMENT FROM
    information_schema.TABLES WHERE TABLE_SCHEMA=DATABASE()
    AND TABLE_NAME='translation'));

perché in realtà siamo interessati a prendere / riutilizzare quell'ID in un'altra tabella o per tornare!


2
Buona spiegazione Grazie. Ora è chiaro perché dovremmo usarelast_insert_id()
Imtiaz,

Questo è uno scenario interessante, ma non credo che risponda effettivamente alla domanda che è quella di recuperare il AUTO_INCREMENTvalore.
Sharlike,

4

codice di esempio eseguibile mysqli:

<?php
    $db = new mysqli("localhost", "user", "password", "YourDatabaseName");
    if ($db->connect_errno) die ($db->connect_error);

    $table=$db->prepare("SHOW TABLE STATUS FROM YourDatabaseName");
    $table->execute();
    $sonuc = $table->get_result();
    while ($satir=$sonuc->fetch_assoc()){
        if ($satir["Name"]== "YourTableName"){
            $ai[$satir["Name"]]=$satir["Auto_increment"];
        }
    }
    $LastAutoIncrement=$ai["YourTableName"];
    echo $LastAutoIncrement;
?>  

1

Se la colonna è autoincrementata nel server sql, per vedere il valore autoincrementato corrente e se si desidera modificare quel valore per quella colonna, utilizzare la seguente query.

-- to get current value
select ident_current('Table_Name')

-- to update current value
dbcc checkident ('[Table_Name]',reseed,"Your Value")

1

Interrogazione per verificare la percentuale di "utilizzo" di AUTO_INCREMENT per tutte le tabelle di un determinato schema (tranne le colonne con tipo bigint senza segno ):

SELECT 
  c.TABLE_NAME,
  c.COLUMN_TYPE,
  c.MAX_VALUE,
  t.AUTO_INCREMENT,
  IF (c.MAX_VALUE > 0, ROUND(100 * t.AUTO_INCREMENT / c.MAX_VALUE, 2), -1) AS "Usage (%)" 
FROM 
  (SELECT 
     TABLE_SCHEMA,
     TABLE_NAME,
     COLUMN_TYPE,
     CASE 
        WHEN COLUMN_TYPE LIKE 'tinyint(1)' THEN 127
        WHEN COLUMN_TYPE LIKE 'tinyint(1) unsigned' THEN 255
        WHEN COLUMN_TYPE LIKE 'smallint(%)' THEN 32767
        WHEN COLUMN_TYPE LIKE 'smallint(%) unsigned' THEN 65535
        WHEN COLUMN_TYPE LIKE 'mediumint(%)' THEN 8388607
        WHEN COLUMN_TYPE LIKE 'mediumint(%) unsigned' THEN 16777215
        WHEN COLUMN_TYPE LIKE 'int(%)' THEN 2147483647
        WHEN COLUMN_TYPE LIKE 'int(%) unsigned' THEN 4294967295
        WHEN COLUMN_TYPE LIKE 'bigint(%)' THEN 9223372036854775807
        WHEN COLUMN_TYPE LIKE 'bigint(%) unsigned' THEN 0
        ELSE 0
     END AS "MAX_VALUE" 
   FROM 
     INFORMATION_SCHEMA.COLUMNS
     WHERE EXTRA LIKE '%auto_increment%'
   ) c

   JOIN INFORMATION_SCHEMA.TABLES t ON (t.TABLE_SCHEMA = c.TABLE_SCHEMA AND t.TABLE_NAME = c.TABLE_NAME)

WHERE
 c.TABLE_SCHEMA = 'YOUR_SCHEMA' 
ORDER BY
 `Usage (%)` DESC;

0

Stavo cercando lo stesso e ho finito per creare un metodo statico all'interno di una classe Helper (nel mio caso l'ho chiamato App \ Helpers \ Database).

Il metodo

/**
 * Method to get the autoincrement value from a database table
 *
 * @access public
 *
 * @param string $database The database name or configuration in the .env file
 * @param string $table    The table name
 *
 * @return mixed
 */
public static function getAutoIncrementValue($database, $table)
{
    $database ?? env('DB_DATABASE');

    return \DB::select("
        SELECT AUTO_INCREMENT 
        FROM information_schema.TABLES 
        WHERE TABLE_SCHEMA = '" . env('DB_DATABASE') . "' 
        AND TABLE_NAME = '" . $table . "'"
    )[0]->AUTO_INCREMENT;
}

Per chiamare il metodo e ottenere MySql AUTO_INCREMENT basta utilizzare quanto segue:

$auto_increment = \App\Helpers\Database::getAutoIncrementValue(env('DB_DATABASE'), 'your_table_name');

Spero che sia d'aiuto.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.