insert value from one table to another checking id - sql

I have 2 tables.All the ids are include in table one (Tbl_Distributor). 2nd table have all the names.
I want to add all the names to first table according to id.
My select query as below.
INSERT INTO dbo.Tbl_Distributor(Giv_Name) where dealercode= a.dealercode
SELECT a.dealercode,d.nameinfull
FROM dealerplacement a,dealer d
where a.dealercode= d.dealercode
order by a.dealercode ASC
This returns nameinfull and dealercode. I want to add this nameinfull to Tbl_Distributor .
Please help me to solve this issue.

UPDATE R
SET Giv_Name = D.FirstName
FROM
dbo.Tbl_Distributor R
INNER JOIN dbo.Dealer D
ON R.Dis_ID = D.DealerCode

You cannot use INSERT here. You need to use update. I'd do such a task using cursors.
declare #id int, #name varchar(1000)
DECLARE c CURSOR FOR
SELECT a.dealercode,d.nameinfull
FROM dealerplacement a,dealer d
where a.dealercode= d.dealercode
order by a.dealercode ASC
OPEN c
FETCH NEXT FROM c
INTO #id, #name
WHILE ##FETCH_STATUS = 0
BEGIN
update Tbl_Distributor set Giv_Name = #name where dealercode = #id
FETCH NEXT FROM c
INTO #id, #name
end
CLOSE c;
DEALLOCATE c;
Also, I'd use join in the select statement:
SELECT a.dealercode,d.nameinfull
FROM dealerplacement a inner join dealer d
on a.dealercode= d.dealercode
order by a.dealercode ASC

Related

SQL Server stored procedure breaking up results

I am trying to get a list back from a stored procedure, but I believe I may have used the wrong method?
The data I am getting back is fine, but is breaking up the results into sections instead of one continuous result.
I need it to be in one continuous result as it needs to be then exported out to an accounting program.
UPDATE
I maybe should have mentioned I am teaching myself SQL and procedures, so I don't entirely know what I am doing, so please forgive me. :)
I spent most of last week writing and re-writing before finally coming here to ask for help.
What I had written was overly complicated I now realise (not to mention not giving the response the way I needed.) I was trying to repurpose code I had found elsewhere.
This is my corrected code.
#varBillingDealerPeriodID int
AS
DECLARE #BillingDealerBatchRosterID int;
BEGIN TRY
SELECT count( * ) AS ItemTotalCount
, di.DealerName
, di.DealerID
, bdbr.BillingDateTo
, bdinr.BillingDealerInvoiceNumber
FROM dbo.billing_dealer_batch_item bdbi
LEFT JOIN dbo.dealer_info di ON di.DealerID = bdbi.DealerID
LEFT JOIN dbo.billing_dealer_batch_roster bdbr ON bdbr.BillingDealerBatchRosterID = bdbi.BillingDealerBatchRosterID
LEFT JOIN dbo.billing_dealer_invoice_number_roster bdinr ON bdinr.DealerID = di.DealerID
WHERE bdbi.BillingDealerBatchRosterID IN (
SELECT DISTINCT BillingDealerBatchRosterID
FROM dbo.billing_dealer_batch_roster
WHERE BillingDealerPeriodID = #varBillingDealerPeriodID
)
AND bdbi.ItemConditionID < 2
GROUP BY di.DealerName
, di.DealerID
, bdbr.BillingDateTo
, bdinr.BillingDealerInvoiceNumber
END TRY
Thank you for everyone's help!
Get rid of the cursor and the loop.
Then change this
AND bdbi.BillingDealerBatchRosterID = #BillingDealerBatchRosterID
To this
AND bdbi.BillingDealerBatchRosterID IN (
SELECT DISTINCT BillingDealerBatchRosterID
FROM dbo.billing_dealer_batch_roster
WHERE BillingDealerPeriodID = #varBillingDealerPeriodID
)
By using the cursor you can just use the following codes. Here, you may need to change the data type for the temp table as per your need.
CREATE PROCEDURE [dbo].[billing_generate_invoice]
#varBillingDealerPeriodID int
AS
BEGIN
IF OBJECT_ID('tempdb..##tmp_billing_generate_invoice', 'U') IS NOT NULL
BEGIN
DROP TABLE ##tmp_billing_generate_invoice
END
CREATE TABLE ##tmp_billing_generate_invoice
(
ItemTotalCount INT,
BillingDealerBatchRosterID INT,
DealerName VARCHAR(500),
ServiceLevelID INT,
FreshItemFeeID INT,
WebsiteFeeID INT,
WebsiteBillingFrequencyID INT,
BillingDateTo DATE,
BillingDealerInvoiceNumber VARCHAR(500)
)
DECLARE #BillingDealerBatchRosterID int;
DECLARE MyCursor CURSOR LOCAL FOR
SELECT BillingDealerBatchRosterID
FROM dbo.billing_dealer_batch_roster
WHERE BillingDealerPeriodID = #varBillingDealerPeriodID;
OPEN MyCursor;
FETCH NEXT FROM MyCursor INTO #BillingDealerBatchRosterID;
WHILE ##fetch_status = 0
BEGIN
-- START
INSERT INTO ##tmp_billing_generate_invoice(
ItemTotalCount,
BillingDealerBatchRosterID,
DealerName,
ServiceLevelID,
FreshItemFeeID,
WebsiteFeeID,
WebsiteBillingFrequencyID,
BillingDateTo,
BillingDealerInvoiceNumber
)
SELECT
COUNT(*) AS ItemTotalCount,
bdbr.BillingDealerBatchRosterID,
di.DealerName,
-- di.DealerID
da.ServiceLevelID,
da.FreshItemFeeID,
da.WebsiteFeeID,
da.WebsiteBillingFrequencyID,
bdbr.BillingDateTo,
bdinr.BillingDealerInvoiceNumber
FROM
dbo.billing_dealer_batch_item bdbi
LEFT JOIN
dbo.dealer_info di ON di.DealerID = bdbi.DealerID
LEFT JOIN
dbo.dealer_account da ON da.DealerID = di.DealerID
LEFT JOIN
dbo.billing_dealer_batch_roster bdbr ON bdbr.BillingDealerBatchRosterID = bdbi.BillingDealerBatchRosterID
INNER JOIN
dbo.billing_dealer_invoice_number_roster bdinr ON bdinr.DealerID = di.DealerID
-- LEFT JOIN dbo.lookup__rate_weekly_fee_LR lrwf ON lrwf.ItemQuantity = ItemTotalCount
-- LEFT OUTER JOIN dbo.billing_dealer_batch bdb ON bdb.DealerID = di.DealerID
WHERE
bdbi.DealerID IN (SELECT DISTINCT DealerID
FROM dbo.billing_dealer_batch
WHERE DealerID = bdbi.DealerID
AND BillingDealerBatchRosterID = #BillingDealerBatchRosterID
AND DealerAccountStatusID = 4 -- Dealer Status 4 is ACTIVE only
)
AND bdbi.BillingDealerBatchRosterID = #BillingDealerBatchRosterID -- Roster Week
AND bdbi.ItemConditionID < 2 -- Less than 2 is AS-IS and Used
GROUP BY
bdinr.BillingDealerInvoiceNumber,
bdbi.DealerID,
di.DealerName,
-- di.DealerID
bdbr.BillingDateTo,
da.ServiceLevelID,
da.FreshItemFeeID,
da.WebsiteFeeID,
da.WebsiteBillingFrequencyID,
bdbr.BillingDealerBatchRosterID
ORDER BY
bdinr.BillingDealerInvoiceNumber;
-- END
FETCH NEXT FROM MyCursor INTO #BillingDealerBatchRosterID;
END;
CLOSE MyCursor;
DEALLOCATE MyCursor;
SELECT * FROM ##tmp_billing_generate_invoice
END

Using a for loop in sql procedure

I want to check out #deemeturu in sql prosudure and check in where condition. For example, I want to continue where (# odemetur = 1 OR # odemetur = 2 OR # odemetur = 3 OR # odemetur = 4). How can we find a solution to this problem?
NOTE: #odemetur changes the number of indices. '1,2,3,4' is not static
alter PROCEDURE sp_siparis
(
#PageNo INT,
#RowCountPerPage INT,
#adsoyadfilter nvarchar(50),
#toplamtutarfilter decimal,
#tarihfilter datetime,
#odemeturu nvarchar(500) = '1,2,3,4'
)
AS
SELECT
u.AdiSoyadi as AdSoyad,
s.OdemeTipAdi as OdemeTipAdi,
sd.Adi as SiparisDurumAdi,
s.OlusturmaTarihi as OlusturmaTarihi,
s.GenelToplam as GenelToplam
FROM
Siparis as s with(NOLOCK)
inner join
SiparisDurum as sd with(NOLOCK) on s.Durumu=sd.Id
inner join
Uye as u with(NOLOCK) on s.Uye_Id=u.Id
WHERE
(u.AdiSoyadi LIKE '%' + #adsoyadfilter + '%') OR (s.GenelToplam = #toplamtutarfilter) OR (s.OlusturmaTarihi = #tarihfilter)
ORDER BY
s.Id OFFSET (#PageNo) ROWS FETCH NEXT #RowCountPerPage ROWS ONLY
GO
you may add this conditions in where clause
or
you may use Cursor and in while use if to pass specific records
DECLARE data_Cursor Cursor For
-- SELECT data here
OPEN data_Cursor
FETCH NEXT FROM data_Cursor INTO
-- add variables here
WHILE ##FETCH_STATUS = 0
BEGIN
IF -- your if condition
BEGIN
-- your logic here
END
FETCH NEXT FROM data_Cursor INTO
-- add variables here
END
CLOSE data_Cursor
DEALLOCATE data_Cursor

Combine results of multiple queries as one result in a SQL Server stored procedure

I need some help with a stored procedure. It contains a loop which runs a Select query. What I get is 3 tables with result if it loops thrice. How can I combine the results as one table?
The procedure is as below:
CREATE PROCEDURE [dbo].[spGetRndQuestions]
#ExamCode Nvarchar(60)
AS
BEGIN
Declare #NosQues Int, #Catgry nvarchar(50)
DECLARE CategCursor CURSOR FOR
(Select Category From tblExamDetail Where ExamCode = #ExamCode)
OPEN CategCursor
FETCH NEXT FROM CategCursor INTO #Catgry
WHILE ##FETCH_STATUS = 0
BEGIN
SET #NosQues = (Select NoOfQues from tblExamDetail Where ExamCode=#ExamCode AND Category=#Catgry)
SELECT TOP(#NosQues) QM.QuestionID, QM.QuestionDesc, QM.QuestionMarks, QM.Answer1, QM.Answer2, QM.Answer3, QM.Answer4 FROM tblQuestionMaster QM
INNER JOIN tblExamMaster EM ON QM.Dept = EM.Dept AND QM.Location = EM.Location AND QM.QuesModule = EM.ExamModule
Where EM.ExamCode=#ExamCode AND QM.Category =#Catgry
Order by NEWID()
/*SELECT TOP (#NosQues) QuestionID,QuestionDesc,Answer1,Answer2,Answer3,Answer4,QuestionMarks from [dbo].[tblQuestionMaster] Where Category=#Catgry AND
Order by NEWID() */
FETCH NEXT FROM CategCursor INTO #Catgry
END
CLOSE CategCursor
DEALLOCATE CategCursor
END
Thanks, your help is truly appreciated.
Create the table variable in start of your SP of appropriate structure of your return table. In each iteration insert selected data to that table. After deallocating cursor select from that table.
CREATE PROCEDURE [dbo].[spGetRndQuestions]
#ExamCode Nvarchar(60) AS
BEGIN
Declare #NosQues Int, #Catgry nvarchar(50)
DECLARE #tbl TABLE(QuestionID int, QuestionDesc ....)
DECLARE CategCursor CURSOR FOR (Select Category From tblExamDetail Where ExamCode=#ExamCode)
OPEN CategCursor
FETCH NEXT FROM CategCursor INTO #Catgry
WHILE ##FETCH_STATUS = 0
BEGIN
SET #NosQues = (Select NoOfQues from tblExamDetail Where ExamCode=#ExamCode AND Category=#Catgry)
INSERT INTO #tbl
SELECT TOP(#NosQues) QM.QuestionID, QM.QuestionDesc, QM.QuestionMarks, QM.Answer1, QM.Answer2, QM.Answer3, QM.Answer4 FROM tblQuestionMaster QM
INNER JOIN tblExamMaster EM ON QM.Dept = EM.Dept AND QM.Location = EM.Location AND QM.QuesModule = EM.ExamModule
Where EM.ExamCode=#ExamCode AND QM.Category =#Catgry
Order by NEWID()
/*SELECT TOP (#NosQues) QuestionID,QuestionDesc,Answer1,Answer2,Answer3,Answer4,QuestionMarks from [dbo].[tblQuestionMaster] Where Category=#Catgry AND
Order by NEWID() */
FETCH NEXT FROM CategCursor INTO #Catgry
END
CLOSE CategCursor
DEALLOCATE CategCursor
SELECT * FROM #tbl
END
Hamlet does answer the question. However, the query you posted could be optimized to eliminate the need for the cursor or table variable. The following code should do that nicely:
CREATE PROCEDURE [dbo].[spGetRndQuestions]
#ExamCode Nvarchar(60)
AS
SELECT
--A.[category],
B.*
FROM tblExamDetail A
CROSS APPLY (
SELECT TOP (A.[NoOfQues])
QM.QuestionID,QM.QuestionDesc,QM.QuestionMarks,
QM.Answer1,QM.Answer2,QM.Answer3,QM.Answer4
FROM tblQuestionMaster QM
INNER JOIN tblExamMaster EM
ON QM.Dept = EM.Dept
AND QM.Location = EM.Location
AND QM.QuesModule = EM.ExamModule
WHERE EM.ExamCode = A.[ExamCode]
AND QM.Category = A.[Category]
ORDER BY NEWID()
) B
WHERE A.[ExamCode] = #ExamCode

How to join data from the same table and same column to two different columns

LN_REF_NO is the reference number of the loan. LN_REF_NO must have one ACNO AND ONE LRAC.
BOTH OF THEM ARE STORED TO ACCOUNTS UNDER ACNO COLUMN.
HOW I WILL SEPARATE THEM ? PLS LOOK THE IMAGE
ALTER PROCEDURE sp_FinalLoanPayment
AS
DECLARE #LN_REF_NO char(13)
DECLARE #TempA
TABLE (
[LN_REF_NO] [char](13),
[Status] [varchar](15),
[ACNO] [varchar](21),
[ACNOBalance] [dbo].[Amount]
)
DECLARE #TempL
TABLE (
[LN_REF_NO] [char](13),
[Status] [varchar](15),
[LRAC] [varchar](21),
[LRACBalance] [dbo].[Amount]
)
DECLARE #TempAll
TABLE (
[LN_REF_NO] [char](13),
[Status] [varchar](15),
[ACNO] [varchar](21),
[ACNOBalance] [dbo].[Amount],
[LRAC] [varchar](21),
[LRACBalance] [dbo].[Amount]
)
INSERT INTO #TempL (LN_REF_NO ,Status,LRAC,LRACBalance)
SELECT Loan.LN_REF_NO, Loan.Status,ACCOUNTS.ACNO ,ACCOUNTS.BALANCE
FROM Loan
INNER JOIN Accounts
ON LOAN.LRAC = ACCOUNTS.ACNO
WHERE Loan.Status ='Paid' AND ACCOUNTS.BALANCE>0
INSERT INTO #TempA (LN_REF_NO ,Status,ACNO,ACNOBalance)
SELECT Loan.LN_REF_NO, Loan.Status,ACCOUNTS.ACNO ,ACCOUNTS.BALANCE
FROM Loan
INNER JOIN Accounts
ON LOAN.ACNO = ACCOUNTS.ACNO
WHERE Loan.Status ='Paid' AND ACCOUNTS.BALANCE<0
-- START CURSOR 1
DECLARE #cursor CURSOR
SET #cursor = CURSOR FOR
select LN_REF_NO from #TempL
OPEN #cursor
FETCH NEXT
FROM #cursor INTO
#LN_REF_NO
WHILE (##FETCH_STATUS = 0)
BEGIN
INSERT INTO #TempAll (LN_REF_NO ,Status,ACNO,ACNOBalance)
select LN_REF_NO,Status,ACNO,ACNOBalance
from #TempA
where LN_REF_NO = #LN_REF_NO
FETCH NEXT
FROM #cursor INTO
#LN_REF_NO
END
CLOSE #cursor
DEALLOCATE #cursor
-- CURSOR 1 END
select * from #TempAll order by LN_REF_NO
Results:
I think you should be able to get this data as you need it with this query:
SELECT
ln.LN_REF_NO, ln.Status, a1.ACNO, a1.BALANCE, a2.ACNO, a2.BALANCE
FROM
dbo.Loan ln
INNER JOIN
dbo.Accounts a1 ON ln.LRAC = a1.ACNO
INNER JOIN
dbo.Accounts a2 ON ln.ACNO = a2.ACNO
WHERE
ln.Status = 'Paid'
AND a1.Balance > 0
AND a2.Balance > 0
You basically just join to the Accounts table twice - once for the link to Loan.LRAC and a second time for the link on Loan.ACNO.
Based on those two joins, you just pick those columns from all joined tables that you need - and that's really all there is! No cursor, no temp tables - nothing like that needed !

How to update a column fetched by a cursor in TSQL

Before I go any further: Yes, I know that cursors perform poorly compared with set-based operations. In this particular case I'm running a cursor on a temporary table of 100 or so records, and that temporary table will always be fairly small, so performance is less crucial than flexibility.
My difficulty is that I'm having trouble finding an example of how to update a column fetched by a cursor. Previously when I've used cursors I've retrieved values into variables, then run an update query at each step based upon these values. On this occasion I want to update a field in the temporary table, yet I can't figure out how to do it.
In the example below, I'm trying to update the field CurrentPOs in temporary table #t1, based upon a query that uses #t1.Product_ID to look up the required value. You will see in the code that I have attempted to use the notation curPO.Product_ID to reference this, but it doesn't work. I have also attempted to use an update statement against curPO, also unsuccessfully.
I can make the code work by fetching to variables, but I'd like to know how to update the field directly.
I think I'm probably missing something obvious, but can anyone help?
declare curPO cursor
for select Product_ID, CurrentPOs from #t1
for update of CurrentPOs
open curPO
fetch next from curPO
while ##fetch_status = 0
begin
select OrderQuantity = <calculation>,
ReceiveQuantity = <calculation>
into #POs
from PurchaseOrderLine POL
inner join SupplierAddress SA ON POL.Supplier_ID = SA.Supplier_ID
inner join PurchaseOrderHeader POH ON POH.PurchaseOrder_ID = POL.PurchaseOrder_ID
where Product_ID = curPO.Product_ID
and SA.AddressType = '1801'
update curPO set CurrentPOs = (select sum(OrderQuantity) - sum(ReceiveQuantity) from #POs)
drop table #POs
fetch next from curPO
end
close curPO
deallocate curPO
After doing a bit more googling, I found a partial solution. The update code is as follows:
UPDATE #T1
SET CURRENTPOS = (SELECT SUM(ORDERQUANTITY) - SUM(RECEIVEQUANTITY)
FROM #POS)
WHERE CURRENT OF CURPO
I still had to use FETCH INTO, however, to retrieve #t1.Product_ID and run the query that produces #POs, so I'd still like to know if it's possible to use FETCH on it's own.
Is this what you want?
declare curPO cursor
for select Product_ID, CurrentPOs from #t1
for update of CurrentPOs
open curPO
fetch next from curPO
while ##fetch_status = 0
begin
update curPO set CurrentPOs =
(select sum(<OrderQuantityCalculation>)
from PurchaseOrderLine POL
inner join SupplierAddress SA ON POL.Supplier_ID = SA.Supplier_ID
inner join PurchaseOrderHeader POH ON POH.PurchaseOrder_ID = POL.PurchaseOrder_ID
where Product_ID = curPO.Product_ID
and SA.AddressType = '1801') -
(select sum(<ReceiveQuantityCalculation>)
from PurchaseOrderLine POL
inner join SupplierAddress SA ON POL.Supplier_ID = SA.Supplier_ID
inner join PurchaseOrderHeader POH ON POH.PurchaseOrder_ID = POL.PurchaseOrder_ID
where Product_ID = curPO.Product_ID
and SA.AddressType = '1801')
fetch next from curPO
end
close curPO
deallocate curPO
Maybe you need something like that:
update DataBaseName..TableName
set ColumnName = value
where current of your_cursor_name;
Here's an example to calculate one column based upon values from two others (note, this could be done during the original table select). This example can be copy / pasted into an SSMS query window to be run without the need for any editing.
DECLARE #cust_id INT = 2, #dynamic_val NVARCHAR(40), #val_a INT, #val_b INT
DECLARE #tbl_invoice table(Cust_ID INT, Cust_Fees INT, Cust_Tax INT)
INSERT #tbl_invoice ( Cust_ID, Cust_Fees, Cust_Tax ) SELECT 1, 111, 11
INSERT #tbl_invoice ( Cust_ID, Cust_Fees, Cust_Tax ) SELECT 2, 222, 22
INSERT #tbl_invoice ( Cust_ID, Cust_Fees, Cust_Tax ) SELECT 3, 333, 33
DECLARE #TblCust TABLE
(
Rec_ID INT
, Val_A INT
, Val_B INT
, Dynamic_Val NVARCHAR(40)
, PRIMARY KEY NONCLUSTERED (Rec_ID)
)
INSERT #TblCust(Rec_ID, Val_A, Val_B, Dynamic_Val)
SELECT Rec_ID = Cust_ID, Val_A = Cust_Fees, Val_B = Cust_Tax, NULL
FROM #tbl_invoice
DECLARE cursor_cust CURSOR FOR
SELECT Rec_ID, Val_A, Val_B, Dynamic_Val
FROM #TblCust
WHERE Rec_ID <> #cust_id
FOR UPDATE OF Dynamic_Val;
OPEN cursor_cust;
FETCH NEXT FROM cursor_cust INTO #cust_id, #val_a, #val_b, #dynamic_val;
WHILE ##FETCH_STATUS = 0
BEGIN
UPDATE #TblCust
SET Dynamic_Val = N'#c = "' + LTRIM(STR((#val_a + #val_b), 40)) + N'"'
WHERE CURRENT OF cursor_cust
FETCH NEXT FROM cursor_cust INTO #cust_id, #val_a, #val_b, #dynamic_val;
END
CLOSE cursor_cust
DEALLOCATE cursor_cust
SELECT * FROM #TblCust