sql >> Base de Datos >  >> RDS >> Oracle

LAST_NUMBER en la secuencia de Oracle

Esto es normal, si. De la documentación para all_sequences vista del diccionario de datos , last_number es:

Esto se puede recrear con una nueva secuencia:

SQL> create sequence SEQ_PAGE_ID start with 2222292436 increment by 1 cache 20;

sequence SEQ_PAGE_ID created.

SQL> select sequence_name, increment_by, cache_size, last_number
  2  from user_sequences where sequence_name = 'SEQ_PAGE_ID';

SEQUENCE_NAME                  INCREMENT_BY CACHE_SIZE LAST_NUMBER
------------------------------ ------------ ---------- -----------
SEQ_PAGE_ID                               1         20  2222292436 

SQL> select SEQ_PAGE_ID.nextval from dual;

   NEXTVAL
----------
2222292436 

SQL> select sequence_name, increment_by, cache_size, last_number
  2  from user_sequences where sequence_name = 'SEQ_PAGE_ID';

SEQUENCE_NAME                  INCREMENT_BY CACHE_SIZE LAST_NUMBER
------------------------------ ------------ ---------- -----------
SEQ_PAGE_ID                               1         20  2222292456 

El last_number saltó por el tamaño del caché, lo cual es normal.

SQL> alter sequence SEQ_PAGE_ID CACHE 5000;

sequence SEQ_PAGE_ID altered.

SQL> select sequence_name, increment_by, cache_size, last_number
  2  from user_sequences where sequence_name = 'SEQ_PAGE_ID';

SEQUENCE_NAME                  INCREMENT_BY CACHE_SIZE LAST_NUMBER
------------------------------ ------------ ---------- -----------
SEQ_PAGE_ID                               1       5000  2222292437 

El last_number baja, pero ahora refleja el último número de secuencia real generado. El DDL (aparentemente) ha provocado que los datos escritos en el disco se actualicen para reflejar lo que resulta ser el valor actual, en lugar de la parte superior del caché, ya sea el antiguo caché de 20 valores o el nuevo caché de 5000 valores. En tu caso tienes 2222292447 , lo que solo significa que estaba diez valores más a través del caché que yo cuando ejecuté el alter .

El valor guardado en el disco está en gran parte allí, de modo que si la base de datos falla, sabe dónde recuperarlo. Al reiniciar, la secuencia comenzará a generar números a partir del last_number registrado. . Durante la ejecución normal, no necesita volver a consultar eso, solo actualiza el valor en el disco cuando se almacenan nuevos valores en caché. Esto evita que los números de secuencia se vuelvan a emitir después de un bloqueo, sin necesidad de realizar un bloqueo costoso (lento) para mantener el valor en tiempo real, que es lo que el caché debe evitar, después de todo.

Solo habría un problema si el last_value fue menor que una secuencia generada real, pero eso no puede suceder. (Bueno, a menos que la secuencia esté configurada en ciclo).

SQL> select SEQ_PAGE_ID.nextval from dual;

   NEXTVAL
----------
2222292437 

El siguiente número de secuencia generado sigue al último antes del cambio de tamaño de caché; no ha reutilizado un valor anterior, ya que podría haber estado preocupado por el valor del diccionario.

SQL> select sequence_name, increment_by, cache_size, last_number
  2  from user_sequences where sequence_name = 'SEQ_PAGE_ID';

SEQUENCE_NAME                  INCREMENT_BY CACHE_SIZE LAST_NUMBER
------------------------------ ------------ ---------- -----------
SEQ_PAGE_ID                               1       5000  2222297437 

El last_number ahora muestra el valor almacenado anterior incrementado por el tamaño del caché de 5000. Lo que está en el diccionario de datos ahora no cambiará nuevamente hasta que hayamos consumido los 5000 valores del caché, o algo sucede en otro lugar que lo afecta:la base de datos se rebota , la secuencia se altera de nuevo, etc.