Auto Increment in String Value - sql

I need query for auto increment in string value-
I need XS000001,XS000009....XS000099...XS000999,XS009999,XS099999,XS999999
Please help me...

If this is for SQL Server (you're not clear on which actual database you're using), the best solution is to use
an ID INT IDENTITY(1,1) column to get SQL Server to handle the automatic increment of your numeric value
a computed, persisted column to convert that numeric value to the value you need
So try this:
CREATE TABLE dbo.YourTable
(ID INT IDENTITY(1,1) NOT NULL PRIMARY KEY CLUSTERED,
AutoIncID AS 'XS' + RIGHT('000000' + CAST(ID AS VARCHAR(6)), 6) PERSISTED,
.... your other columns here....
)
Now, every time you insert a row into YourTable without specifying values for ID or AutoIncID:
INSERT INTO dbo.YourTable(Col1, Col2, ..., ColN)
VALUES (Val1, Val2, ....., ValN)
then SQL Server will automatically and safely increase your ID value, and AutoIncID will contain values like XS000001, XS000002,...... and so on - automatically, safely, reliably, no duplicates.
But the question really is: what if your number range is used up? What do you do after have handed out XS999999 ? We cannot answer that for you .....

Related

How to create an insert trigger based on primary key?

I am stuck on a problem creating a trigger in SQL Server. I have MyTable with the following columns (simplified):
Sn - Identity, not nullable;
SomeId - int, not nullable;
miscellaneous other columns
The Sn column is nothing special, values 1,2...n.
SomeId needs to be 1000 + Sn, i.e. this is what I want the trigger to do on insert.
The problem I am having is a standard trigger fails if I don't include something for SomeId (error is that null is not allowed), if that trigger is using after insert. Maybe I am meant to use instead of insert, but I am having trouble getting that to work correct or find details about it.
The other factor here - I am not even sure if it is possible for what I am trying to do to work. I.e when a new row is being created and SQL Server generates an Sn (Identity column), can a trigger be part of that process and also compute the SomeId value (which needs the Sn value) before inserting?
If not, as a fallback I could either make the SomeId column nullable (not desirable), or always insert 0 into it (and let the trigger fire afterwards to update it), but that would be a bit grim also.
No need for a trigger. Just use a SEQUENCE to generate the ID values instead of an IDENTITY column, eg
create sequence seq_MyTable
start with 1
increment by 1
go
CREATE TABLE MyTable
(
Sn int not null primary key default (next value for seq_MyTable),
SomeID int not null unique default (next value for seq_MyTable) + 1000,
Name VARCHAR(50) NOT NULL
)
insert into MyTable(Name)
values ('A'),('B'),('C')
select * from Mytable

Insert query: Column name or number of supplied values does not match table definition

This is a table that auto increments the ID, takes the time input, and sets the default of the total column as zero and the date column with getdate()
CREATE TABLE OrderPlaced (
OrderID bigint IDENTITY(1,1) PRIMARY KEY,
PlacedAt time NOT NULL,
PlacedOn DATE NOT NULL default getdate(),
Total MONEY default 0
)
So the only value that I have to insert is the time.
insert into OrderPlaced values ('13:40');
However on insertion SQL Server gives me this error:
Column name or number of supplied values does not match table definition.
The error is telling you the problem. Your table, OrderPlaced, has four columns, but you only supply one column in the INSERT and don't tell the instance what column to insert it into.
For your table, if you don't specify the columns then it will expect values for PlacedAt, PlacedOn and Total; it won't expect a value for OrderID as it is an IDENTITY and you haven't turned on IDENTITY_INSERT. As the instance is expecting 3 columns, and you only provide one, you get an error telling you that the number of columns don't match (3 != 1).
If you only want to insert a value into PlacedAt, and allow the rest of the columns use their DEFAULT values then define in your INSERT clause you only want to provide a value for PlacedAt:
INSERT INTO dbo.OrderPlaced(PlacedAt)
VALUES ('13:40');
Or, if you are (oddly) opposed to defining the columns in the INSERT clause, then tell the instance that the other 2 columns need their DEFAULT values.
INSERT INTO dbo.OrderPlaced
VALUES ('13:40',DEFAULT, DEFAULT);
Though I don't recommend this solution, be explicit as then if you change definition of the table, the above statement will fail.
You need to specify the column name as well, like this:
INSERT INTO table_name (column1, column2, column3, ...) VALUES (value1, value2, value3, ...);
So it will be like this:
insert into OrderPlaced values ('13:40');

SQL Server - Create a custom auto-increment field

I am trying to produce a custom auto-increment functionality in sql. my custom auto-incerement ID should be like below...
S1501.001
"S" is for Supplier's name first letter.
"15" is for this year's last 2 digits.
"01" is today's month
"." will always be there
"001" is my incrementer.
the counter will go on like below
S1501.001
S1501.002
S1501.003
S1501.004
Firstly, I have to find the "S1501." and find the ID with highest digits at the end. I can create a new "S1501.005". How can I do this?
I have done something but didnt work.
SELECT TOP 1 (SELECT SUBSTRING('S1501.001', 7,3)),*
FROM LG_001_01_SERILOTN
WHERE CODE LIKE SUBSTRING('S1501.001', 1,6)+'%'
ORDER BY (SELECT SUBSTRING('S1501.001', 7,3)) DESC
The best solution is to use
an ID INT IDENTITY(1,1) column to get SQL Server to handle the automatic increment of your numeric value
a computed, persisted column to convert that numeric value to the value you need
So try this:
CREATE TABLE dbo.tblCompany
(ID INT IDENTITY(1,1) NOT NULL PRIMARY KEY CLUSTERED,
CompanyID AS 'S1501.' + RIGHT('000' + CAST(ID AS VARCHAR(3)), 3) PERSISTED,
.... your other columns here....
)
Now, every time you insert a row into tblCompany without specifying values for ID or CompanyID:
INSERT INTO dbo.tblCompany(Col1, Col2, ..., ColN)
VALUES (Val1, Val2, ....., ValN)
then SQL Server will automatically and safely increase your ID value, and CompanyID will contain values like S1501.001, S1501.002,...... and so on - automatically, safely, reliably, no duplicates.

SQL - Inserting a row and returning primary key

I have inserted a row with some data in a table where a primary key is present. How would one "SELECT" the primary key of the row one just inserted?
I should have been more specific and mentioned that I'm currently
using SQLite.
For MS SQL Server:
SCOPE_IDENTITY() will return you the last generated identity value within your current scope:
SELECT SCOPE_IDENTITY() AS NewID
For SQL Server 2005 and up, and regardless of what type your primary key is, you could always use the OUTPUT clause to return the values inserted:
INSERT INTO dbo.YourTable(col1, col2, ...., colN)
OUTPUT Inserted.PrimaryKey
VALUES(val1, val2, ....., valN)
SQL Server:
You can use ##IDENTITY. After an insert statement, you can run:
select ##identity
This will give you the primary key of the record you just inserted. If you are planning to use it later, I suggest saving it:
set #MyIdentity = ##identity
If you are using this in a stored procedure and want to access it back in your application, make sure to have nocount off.
For MySQL, use LAST_INSERT_ID()
http://dev.mysql.com/doc/refman/5.0/en/getting-unique-id.html
You should also be able to start a transaction, insert the row, and select the row using some field that has a unique value that you just inserted, like a timestamp or guid. This should work in pretty much any RDBMS that supports transactions, as long as you have a good unique field to select the row with.
If you need to retrieve the new index in MS SQL when there are triggers on the table then you have to use a little workaround. A simple OUTPUT will not work. You have to do something like this (in VB.NET):
DECLARE #newKeyTbl TABLE (newKey INT);
INSERT INTO myDbName(myFieldName) OUTPUT INSERTED.myKeyName INTO #newKeyTbl VALUES('myValue'); " & _
SELECT newKey FROM #newKeyTbl;"
If using .NET, then the return value from this query can be directly cast to an integer (you have to call "ExecuteScalar" on the .NET SqlCommand to get the return).
For SQLite:
SELECT [Column_1], [Column_2],... [Column_n]
FROM [YourTable]
WHERE rowid = (SELECT last_insert_rowid())
whereas:
Column_1, Column_2,... Column_n: are the primary key of YourTable.
If you'd created YourTable with primary key replaced rowid (i.e. one column pk defined as INTEGER PRIMARY KEY) you just use:
SELECT last_insert_rowid()
Which is a common case.
Finally, this wont work for WITHOUT_ROWID tables.
Please Check:
https://www.sqlite.org/lang_corefunc.html#last_insert_rowid
For PostgreSQL,
INSERT INTO tablename (col1, col2, ...)
VALUES (val1, val2, ...)
RETURNING idcol;
The optional RETURNING clause causes INSERT to compute and return value(s) based on each row actually inserted (or updated, if an ON CONFLICT DO UPDATE clause was used). This is primarily useful for obtaining values that were supplied by defaults, such as a serial sequence number. However, any expression using the table's columns is allowed.
https://www.postgresql.org/docs/current/sql-insert.html
For Postgresql:
SELECT CURRVAL(pg_get_serial_sequence('schema.table','id'))
Source: PostgreSQL function for last inserted ID
select MAX(id_column) from table
That, in theory, should return you that last inserted id. If it's a busy database with many inserts going on it may not get the one you just did but another.
Anyhow, an alternative to other methods.

Asking a Microsoft SQL Server database for the next auto-generated identifier on a table

I have a table in a SQL Server database that has an auto-generated integer primary key. Without inserting a record into the table, I need to query the database and get what the next auto-generated ID number will be.
I think it's SQL Server version 2005, if that makes a difference.
Is there a way to do this?
Yes, but it's unreliable because another session might use the expected number.
If you still want to do this, use IDENT_CURRENT
Edit, as the comments have pointed out (improving my answer):
you need to add one IDENT_INCR('MyTable') to this to get the potential next number
another process may rollback and this number may not be the one used anyway
No, there is not. The ID will only ever be defined and handed out when the actual INSERT happens.
You can check the last given ID by using
DBCC CHECKIDENT('YourTableName')
but that's just the last one used - no guarantee that the next one is really going to be this value + 1 - it could be - but no guarantees
The only way to get a number that is guranteed not to be used by another process (i.e., a race condition) is to do the insert - is there any reason you can't do a NULL insert (i.e., just insert into the table with NULLs or default values for all other columns) and then subsequently UPDATE it?
i.e.,
CREATE TABLE bob (
seq INTEGER IDENTITY (1,1) NOT NULL,
col1 INTEGER NULL
)
GO
DECLARE #seqid INTEGER
INSERT INTO bob DEFAULT VALUES
SET #seqid = SCOPE_IDENTITY()
-- do stuff with #seqid
UPDATE bob SET col1 = 42 WHERE seq = #seqid
GO
You shouldn't use the technique in code, but if you need to do it for investigative purposes:
select ident_current(‘foo’) + ident_incr(‘foo’)
That gives you the last value generated + the incrementation for the identity, so should represent the next choice SQL would make without inserting a row to find out. This is a correct value even if a rollback has pushed the value forwards - but again, this is investigative SQL not stuff I would put in code.
The two values can also be found in the sys.identity_values DMV, the fields are increment_value and last_value.
Another way, depending on what your doing, is inserting whatever data goes into the table, and then using ##identity to retrieve the id of the record inserted.
example:
declare #table table (id int identity(1,1), name nvarchar(10))
insert into #table values ('a')
insert into #table values ('b')
insert into #table values ('c')
insert into #table values ('d')
select ##identity
insert into #table values ('e')
insert into #table values ('f')
select ##identity
This is pretty much a bad idea straight off the bat, but if you don't anticipate high volume and/or concurrency issues, you could just do something like this
select #nextnum = max(Id) + 1 from MyTable
I don't think thats possible out of the box in MS SQL (any version). You can do this with column type uniqueidentifier and using function NEWID().
For int column, you would have to implement your own sequential generator.