I'm new to SQL and C# and am currently trying to create a library software. I'm facing a bit of a problem and would appreciate your input.
I have three tables:
Books (BookID, Title)
Author (AuthorID, AuthorFname, AuthorLname)
WrittenBy (BookID, AuthorID)
BookId in the table Books and AuthorID in the table Author are indexed and are the primary keys.
What I need to do is,
get the bookId from the books table,
get the authorID from the author table,
insert these two values into the writtenby table
My solution is to write two separate SQL statements to select the id columns and then enter it into the third table.
But what if there are two books with the same title?
Is there a way to get the last inserted values in SQL?
If those ID columns are of type INT IDENTITY and you're using SQL Server, then yes - you can get the last inserted value:
INSERT INTO dbo.Books(Title) VALUES('New Book')
DECLARE #NewBookID INT
SELECT #NewBookID = SCOPE_IDENTITY()
INSERT INTO dbo.Author(AuthorFname, AuthorLname) VALUES('John', 'Doe')
DECLARE #NewAuthorID INT
SELECT #NewAuthorID = SCOPE_IDENTITY()
INSERT INTO dbo.WrittenBy(BookID, AuthorID) VALUES(#NewBookID, #NewAuthorID)
The SCOPE_IDENTITY() function will return that last inserted IDENTITY value by the previous statement, which should be exactly what you're looking for, correct?
There are different ways are available :
##IDENTITY
OR
SCOPE_IDENTITY()
OR
IDENT_CURRENT(‘tablename’)
http://blog.sqlauthority.com/2007/03/25/sql-server-identity-vs-scope_identity-vs-ident_current-retrieve-last-inserted-identity-of-record/
You should have a column called something like InsertedDate or CreatedDate. That's the best way to order by last inserted.
Other than that, this sounds like a homework question. This isn't want SO is for - search engines are your friends.
Related
I have a question, let's say I have two tables I am doing an insert operation to the first table with the stored procedure, but how do I insert the auto incrementing ID in the first table in the other table? 🤔🤔
Would be good if you provided one example of what you are trying to achieve.
To get the inserted Id by the store procedure, you could use SCOPE_IDENTITY.
SCOPE_IDENTITY(): returns the last identity value generated in the current scope.
For instance:
INSERT INTO.... VALUES(); SELECT SCOPE_IDENTITY();
This query will insert into a the given table and will return the id inserted.
You can also use Select ##IDENTITY, this will return the last id inserted regardless the scope.
INSERT INTO.... VALUES(); SELECT ##IDENTITY;
I have a query like this
myEntity.Database.ExecuteSqlCommand("insert into mytable (id, name) values (mytable_SEQ.nextval,'John')")
mytable_SEQ is a sequence created to generate unique ID for mytable
What is the best way to get the inserted ID ?
There is no such thing as best way. There are a couple of ways to achieve what you want. Basically the first is to execute sequence.CURRVAL to get the current value of the sequence. You could also do a query using MAX(id) to get the maximum value of the ID column.
Note: both of these aren't safe if you have concurrency. Another thread may modify both the sequence or insert a new record to the table.
To reflect your comment, the only thing I'm aware of is to use pessimistic locking on the table while you insert the row and select the maximum ID in the very same transaction.
I know this absolutly not the proper way, this is how i did so far :
int nextid = myEntity.Database.SqlQuery<int>("select mytable_SEQ.nextval from dual").FirstOrDefault();
and then
myEntity.Database.ExecuteSqlCommand("insert into mytable (id, name) values ("+nextid+",'John')")
I know it can be done somehow in one query..
first of all I am sorry if this question is too obvious, since I am quite new in SQL.
So, I have a list of IDs (variable, depending how many products the user chooses). And I want to check if all of them are in a table. If one of them is not, the result of the query should be null. If all of them are there, the result should be all the rows where those IDs are.
How can I do this?
Best regards,
Flavio
Do a LEFT JOIN from the list to the table on the ID field. You'll get a null if there is no record
You can even put a WHERE clause like 'WHERE List.ID IS NULL' to only see those that aren't in the table
Edit: Original Poster did not say they were using C# when I wrote this answer
UNTESTED:
Not sure if this is the most efficient but it seems like it should work.
1st it generates a count of items in the table for your list. Next it cross joins the 1 result record to a query containing the entire list ensuring the count matches the count in your provided list and limiting the results to your list.
SELECT *
FROM Table
CROSS JOIN (
SELECT count(*) cnt
FROM table
WHERE ID in (yourlist)) b
WHERE b.cnt = yourCount
and ID IN (YourList)
Running two in statements seems like it would be terribly slow overall; but my first step when writing SQL is usually to get something that works and then seek to improve performance if needed.
Get the list of Ids into a table, (you can pass them as a table variable parameter to a Stored proc), then in the stored proc, write
assuming the list of ids from C# is in table variable #idList
Select * from myTable
Where id in (Select id from #idList)
and not exists
(Select * from #idList
where id Not in
(Select id from myTable))
I have to get the IDENTITY values from a table after SQLBULKCOPY to the same table. The volume of data could be thousands of records.
Can someone help me out on this ?
Disclaimer: I'm the owner of the project Bulk Operations
In short, this project overcomes SqlBulkCopy limitations by adding MUST-HAVE features like outputting inserted identity value.
Under the hood, it uses SqlBulkCopy and a similar method as #Mr Moose answer.
var bulk = new BulkOperation(connection)
// Output Identity Value
bulk.ColumnMappings.Add("CustomerID", ColumnMappingDirectionType.Output);
// Map Column
bulk.ColumnMappings.Add("Code");
bulk.ColumnMappings.Add("Name");
bulk.ColumnMappings.Add("Email");
bulk.BulkInsert(dt);
EDIT: Answer comment
can I simply get a IList or simply , I see its saved back in the customers table, but there is no variable where I can get a hold of it, can you please help with that. So, I an insert in Orders.CustomerID table
It depends, you can keep a reference to the Customer DataRow named CustomerRef in the Order DataTable.
So once you merged your customer, you are able to populate easily a column CustomerID from the column CustomerRef in your Order DataTable.
Here is an example of what I'm trying to say: https://dotnetfiddle.net/Hw5rf3
I've used a solution similar to this one from Marc Gravell in that it is useful to first import into a temp table.
I've also used the MERGE and OUTPUT as described by Jamie Thomson on this post to track data I have inserted into my temp table to match it with the id generated by the IDENTITY column of the table I want to insert into.
This is particularly useful when you need to use that ID as a foreign key reference to other tables you are populating.
Try this
CREATE TABLE #temp
(
DataRow varchar(max)
)
BULK INSERT #Temp FROM 'C:\tt.txt'
ALTER TABLE #temp
ADD id INT IDENTITY(1,1) NOT NULL
SELECT * FROM #temp
-- dummy schema
CREATE TABLE TMP (data varchar(max))
CREATE TABLE [Table1] (id int not null identity(1,1), data varchar(max))
CREATE TABLE [Table2] (id int not null identity(1,1), id1 int not null, data varchar(max))
-- imagine this is the SqlBulkCopy
INSERT TMP VALUES('abc')
INSERT TMP VALUES('def')
INSERT TMP VALUES('ghi')
-- now push into the real tables
INSERT [Table1]
OUTPUT INSERTED.id, INSERTED.data INTO [Table2](id1,data)
SELECT data FROM TMP
Hey guys I have a confusing question, I have a user table and it stores all the usual data for a user that you would expect but im trying to figure out how a user could add another user?
Sounds strange but each user in the User table has his own UI which is UserID how could I add another table where UserID can have a relationship with another UserID?
I will give the answer to those that could take the time to upload a table diagram and who can help with some examples for sqlsyntax related to this question, i.e how would I right the syntax for the above question if I wanted to display all the UserIDs friends on a page. How would I add a friend.
You just need another table similar to the Pictures and wallposting table. You just need to be able to record many friend id's for one user id (one to many)
eg:
The query to then get friends would be:
DECLARE #UserID AS BIGINT
SET #UserID = 123
SELECT [friends].*
FROM [friends]
where [parentuserid]=#UserID#
to Insert a Friend:
DECLARE #UserID AS BIGINT
DECLARE #FriendID AS BIGINT
SET #UserID = 123
SET #FriendID = 321
INSERT INTO [Friends]
(
[ParentUserID],
[ChildUserID]
)
VALUES
(
#UserID,
#FriendID
)
Code to insert it example:
private void Test()
{
string Query =
#"INSERT INTO [Friends]
(
[ParentUserID],
[ChildUserID]
)
VALUES
(
#UserID,
#FriendID
)";
using ( SqlConnection oSqlConnection = new SqlConnection( "connect string" ) )
{
oSqlConnection.Open();
using (SqlCommand oSqlCommand = new SqlCommand(Query,oSqlConnection))
{
oSqlCommand.Parameters.AddWithValue("#UserID", Session["UserID"]);
oSqlCommand.Parameters.AddWithValue("#FriendID", Session["FriendID"]);
oSqlCommand.ExecuteNonQuery();
}
}
}
Where would you get your friend ID from? what is the process for adding friends? do you search for them and select them from a list?
You just need a many to many relationship.
Create Table Friend(
UserId int,
FriendId int,
Constraint pk_friends Primary Key (UserId, FriendId),
Constraint fk_friend_user Foreign Key (UserId) References User(UserId),
Constraint fk_friend_friend Foreign Key (FriendId) References User(UserId)
)
Your asking a bit much with the diagrams etc.... for me at least.
It depends on the kind of relationship, one to one, it will be another Column in your user table. If it is many to many you'll need a junction table, with two columns UserIDA, UserIDB. Depending why you need the relationship.
I think you have a simple requirement of a User Referring Other user to join. If that is the case then you can simply have one more column ReferenceUserID in User Table and whenever a new user refers another user then simply add him with a UserID of referring user. If he isn't a referred user then by default it will be NULL.
Later for retrieval you can use a Self Join.
Update:
For Friend (many to many relationship) you should look at following Question at StackOverflow
Database design: Best table structure for capturing the User/Friend relationship?
UserRelationship
====
RelatingUserID
RelatedUserID
Type[friend, block, etc]
A similar approach is used by Facebook where they have a kind of Cross join Table for relation between Friends.