SQL Error The multi-part identifier could not be bound - sql

When I'm trying to execute this query, I get "The multi-part identifier "#EachEmployee.ResultID" could not be bound." error.
DECLARE #QueryText VARCHAR(1000)
SET #QueryText = '
UPDATE #EachEmployee2
SET #EachEmployee2.CorrectAnswerCount = (
SELECT COUNT (TMID)
FROM
' + #WorkDatabaseName + '.dbo.TestBlockTM AS TBTM,
' + #WorkDatabaseName + '.dbo.TestResultTM AS TRTM
WHERE 1 = 1
AND TBTM.TMID = TRTM.OtvetID
AND TBTM.TMPID = TRTM.VoprosID
AND TRTM.TestResultID = #EachEmployee2.ResultID
)
WHERE
#EachEmployee2.IsGroup = 0 AND #EachEmployee2.BlockID = 1'
EXECUTE(#QueryText)
However, the similar query is working perfectly:
UPDATE #EachEmployee2
SET #EachEmployee2.ResultID = (
SELECT TOP 1 TestResultID
FROM #AnswersList AS a
WHERE 1 = 1
AND a.SID = #EachEmployee2.SID
AND a.UserID = #EachEmployee2.UserID
)
Can someone tell what's a problem here? Thanks and appreciate your help.

try this
SET #QueryText = '
UPDATE emp
SET emp.CorrectAnswerCount = (
SELECT COUNT (TMID)
FROM
' + #WorkDatabaseName + '.dbo.TestBlockTM AS TBTM,
' + #WorkDatabaseName + '.dbo.TestResultTM AS TRTM
WHERE 1 = 1
AND TBTM.TMID = TRTM.OtvetID
AND TBTM.TMPID = TRTM.VoprosID
AND TRTM.TestResultID = emp.ResultID
)
From #EachEmployee2 emp
WHERE
emp.IsGroup = 0 AND emp.BlockID = 1'

Can you try this query and tell me if the error still occurs:
SET #QueryText = '
UPDATE #EachEmployee2
SET CorrectAnswerCount = (
SELECT COUNT (TMID)
FROM
' + #WorkDatabaseName + '.dbo.TestBlockTM AS TBTM,
INNER JOIN ' + #WorkDatabaseName + '.dbo.TestResultTM AS TRTM ON TRTM.OtvetID = TBTM.TMID
AND TRTM.VoprosID = TBTM.TMPID
AND TRTM.TestResultID = E.ResultID
)
FROM #EachEmployee2 E
WHERE E.IsGroup = 0
AND E.BlockID = 1'
I added the FROM clause and modified a bit the subquery in order to replace the old SQL syntax by an explicit INNER JOIN clause.
Hope this will help

Related

Select more values on clause IF in the stored procedure

I have a problem of syntax in my stored procedure when a select more values in my IF, on code snippet 37 OR 35.
IF 37 OR 35 NOT IN (SELECT CodPerfilSistema
FROM [BRSAODB09].[ADMIN].[dbo].[PERFIL_USUARIO]
WHERE CodUsuario = #pCodUsuario)
BEGIN
SET #CondicaoEmpresa = ' AND [Lote].CodEmpresa = ' + CONVERT(varchar(10), #pCodEmpresa);
SET #CondicaoProjeto = ' AND [AUD_Projeto].CodProjeto = ' + CONVERT(varchar(10), #pCodProjeto);
END
I tried the code above.
And below is how the code is running
IF 37 NOT IN (SELECT CodPerfilSistema
FROM [BRSAODB09].[ADMIN].[dbo].[PERFIL_USUARIO]
WHERE CodUsuario = #pCodUsuario)
BEGIN
SET #CondicaoEmpresa = ' AND [Lote].CodEmpresa = ' + CONVERT(varchar(10), #pCodEmpresa);
SET #CondicaoProjeto = ' AND [AUD_Projeto].CodProjeto = ' + CONVERT(varchar(10), #pCodProjeto);
END
I need the permission for Id 37 and 35.
try the below
IF not exists (SELECT * FROM [BRSAODB09].[ADMIN].[dbo].[PERFIL_USUARIO] where CodUsuario = #pCodUsuario
and CodPerfilSistema in (37,35))
BEGIN
SET #CondicaoEmpresa = ' AND [Lote].CodEmpresa = ' + CONVERT(varchar(10), #pCodEmpresa);
SET #CondicaoProjeto = ' AND [AUD_Projeto].CodProjeto = ' + CONVERT(varchar(10), #pCodProjeto);
END
Thanks guys for the help, I found a way to solve the problem I had.
It stayed like this:
IF NOT EXISTS(
SELECT 1
FROM [BRSAODB09].[ADMIN].[dbo].[PERFIL_USUARIO]
WHERE CodUsuario = #pCodUsuario
AND CodPerfilSistema IN(37,35)
)
BEGIN
SET #CondicaoEmpresa = ' AND [Lote].CodEmpresa = ' + CONVERT(varchar(10),
#pCodEmpresa);
SET #CondicaoProjeto = ' AND [AUD_Projeto].CodProjeto = ' + CONVERT(varchar(10),
#pCodProjeto);
END

How to update table with while loop in Stored Procedure?

I want to update my dynamic table in while loop.
Here is my code:
While (#j<=#tmp_getRowCount)
Begin
Set #firstcolumn = (Select SplitFirst_tblAR from #result_AR Where rownumber = #j) //String//
Set #secondcolumn = (Select EMail_tblAR from #result_AR Where rownumber = #j) //String//
Set #thirdcolumn = (Select SplitFirst_tblKul from #result_AR Where rownumber = #j) //String//
Set #fourthcolumn = (Select EMail_tblKul from #result_AR Where rownumber = #j) //String//
insert into #test Values(#tmp_ID, #firstcolumn,#secondcolumn,#thirdcolumn,#fourthcolumn)
if ((#firstcolumn = #thirdcolumn) AND (#secondcolumn != #fourthcolumn) AND (#firstcolumn != ''))
begin
Set #q_updateTable = 'Update '+ quotename(#tablename) +' Set '+#columnname+' = ''' + #fourthcolumn + ''' Where ID = ' + #tmp_ID + ''
Exec sp_executesql #q_updateTable
end
SET #j = #j+1
End
My result_AR table:
I know the error is in here:
Where ID = ' + #tmp_ID + ''
When I change this Where clause as,
Where '+#columnname+' = ''' + #secondcolumn + ''' '
code works correctly.
Why can't I set as ID my where clause? I am getting ID value as integer.
The error is 'Query completed with errors'.
Thanks in advance.
you can not set Id in where clause because the id is integer value and you are concatenating it with string (varchar).
So first you have to convert it in (String)varchar and the you can use it where clause.
Like :
Set #q_updateTable = 'Update '+ quotename(#tablename) +' Set '+#columnname+' = ''' + #fourthcolumn + ''' Where ID = ' + convert(varchar,#tmp_ID) + ''
Exec sp_executesql #q_updateTable
you have to use "convert(varchar,#tmp_ID)" insted of "#tmp_ID"

Concatenating 2 columns in sql and applying like operation on the result

SELECT
CONCAT(SG.firstname +' ', SG.lastName) AS 'Name',
SG.entityId 'ID',
dbo.GetTitleDescriptionByEntityID(SG.entityId) 'Title',
CASE ISNULL(EC.address2, '')
WHEN '' THEN EC.address1
ELSE EC.address1 +', ' + EC.address2
END +', ' + EC.city + ', ' + LDState.ItemName + ', ' + EC.zip 'Address',
CR.clinicalRate
FROM
StaffGeneral SG WITH (NOLOCK)
JOIN
LookupDetails LD WITH (NOLOCK) ON SG.employeeStatus = LD.lookupDetailsId AND LD.ItemAbbreviation = 'SCSSC'
JOIN
othersRating or1 WITH (nolock) ON SG.entityId = or1.entityId AND dateRated = (SELECT TOP 1 MAX(dateRated) FROM OthersRating r1 WITH (nolock) WHERE r1.entityid = SG.entityId)
JOIN
LookupDetails LDRating with (nolock) ON or1.rating = LDRating.lookupDetailsId AND LDRating.ItemAbbreviation NOT IN ('RTNP', 'RTDNU', 'RTPENDING', 'RTDELETE', 'RTTERMI')
JOIN
EntityContacts EC with (nolock) ON SG.entityId = EC.entityId AND (eC.contactId = 'General' or EC.contactId = 'General1') AND EC.deleted = 0
JOIN
LookupDetails LDState WITH (NOLOCK) ON EC.state = LDState.lookupDetailsId
JOIN
ContractorRate CR ON SG.entityId = CR.entityId AND CR.deleted = 0
WHERE
SG.isActive = 0 AND SG.deleted = 0
AND ((SG.entityId = #subContractorID) OR (#subContractorID IS null))
AND ((#subContractorName IS NULL) OR ((EC.firstName + ' ' + EC.lastName) LIKE #subContractorName + '%'))
In the above query I wanted to concat the first and last name with space and query it against the input to the stored procedure #subcontractorname.
When the subcontractorname is null that is fine but I am not able to get results when it jumps to Or clause .
Tried the SQL Server Profiler but does not show anything how the query is formed
I tried executing the SQL by putting the whole SQL in a var but I am hitting the problem of varchar(max).
Please advise

Concatenating row values using Inner Join

I have this query that I'm using to join two tables for an update statement. This is the query that I built:
DECLARE #DocHoldReasons VARCHAR(8000)
SET #DocHoldReasons = 'DocType Hold'
UPDATE dbo.EpnPackages
SET Error = 1, Msg = COALESCE (#DocHoldReasons + ': ', '') + cv.Value
FROM EpnPackages p
INNER JOIN EpnCountyValues cv ON cv.CountyId = p.CountyId and cv.ValueName = 'DocHoldReason'
WHERE p.Status = 1000
AND p.Error = 0
There are two rows in the EpnCountyValues table with the same ValueName, and I need them both concatenated, and I'm having a tough time doing it. All I can get is the first row value. This is what my resulting string should look like - 'DocType Hold: Test: Test.124.'
eidt: I need the rows with the same ValueName to be concatenated for the update query. There could be more than two rows with ValueName = DocHoldReason
Here's the structure of the EpnCountyValues table:
CountyValueId CountyId ValueName Value
1 1 DocHoldReason Test
2 2 xyz Test1
3 3 DocHoldReason Test.124.
Any help would be greatly appreciated. Thanks!
You can do what you want by pre-aggregating the table before the join. If there are only two values and you don't care about the order, then this will work:
DECLARE #DocHoldReasons VARCHAR(8000);
SET #DocHoldReasons = 'DocType Hold';
UPDATE dbo.EpnPackages
SET Error = 1,
Msg = (COALESCE(#DocHoldReasons + ': ', '') + minv +
(case when minv <> maxv then ': ' + maxv else '' end)
)
FROM EpnPackages p INNER JOIN
(select cv.CountyId, min(cv.value) as minv, max(cv.value) as maxv
from EpnCountyValues cv
where cv.ValueName = 'DocHoldReason'
) cv
ON cv.CountyId = p.CountyId
WHERE p.Status = 1000 AND p.Error = 0;
EDIT:
For more than two values, you have to do string concatenation. That is "unpleasant" in SQL Server. Here is the approach:
DECLARE #DocHoldReasons VARCHAR(8000);
SET #DocHoldReasons = 'DocType Hold';
UPDATE dbo.EpnPackages
SET Error = 1,
Msg = (COALESCE(#DocHoldReasons + ': ', '') +
stuff((select ': ' + cv.value
from EpnCountyValues cv
where cv.ValueName = 'DocHoldReason' and
cv.CountyId = p.CountyId
for xml path ('')
), 1, 2, '')
)
WHERE p.Status = 1000 AND p.Error = 0;
This version does it using a correlated subquery rather than a join with an aggregation.
EDIT II:
You can fix this with an additional coalesce:
DECLARE #DocHoldReasons VARCHAR(8000);
SET #DocHoldReasons = 'DocType Hold';
UPDATE dbo.EpnPackages
SET Error = 1,
Msg = (COALESCE(#DocHoldReasons + ': ', '') +
COALESCE(stuff((select ': ' + cv.value
from EpnCountyValues cv
where cv.ValueName = 'DocHoldReason' and
cv.CountyId = p.CountyId
for xml path ('')
), 1, 2, ''), '')
)
WHERE p.Status = 1000 AND p.Error = 0;
You can join the EpnCountyValues table twice!
Something like this,
DECLARE #DocHoldReasons VARCHAR(8000)
SET #DocHoldReasons = 'DocType Hold'
Select #DocHoldReasons + ': ' + ev1.Value + ': ' + ev2.Value
From EpnPackages p
Join EpnCountyValues ev1 on p.packageID = ev1.packageID
Join EpnCountyValues ev2 on ev1.ValueName = ev2.ValueName
Where ev1.ValueName = 'DocHoldRegion'
And p.status = 1000
And p.error = 0
Does that select look right to you? If so, run the update. I always try to run a select before an update. I have to admit, I'm a bit confused why you're joining on CountyID, but then it seems like you'll be updating the values from different counties?

Conversion failed when converting the varchar value '*' to data type int

I'm getting this issue when i'm running nested while loops in sql server 2005.
My outer loop gets one iteration, and then my inner loop gets it's full first iteration, but my statement after the inner loop never gets executed, which then seems to break everything.
I'm lost right now and I feel like I'm missing something very easy, any help is much appreciated.
while exists(select top 1 ident from #tmpAttorneyImport (nolock) where parsed = 0 and zipcode <> '')
begin
set #intCurrentIdent = 0
set #vcrCurrentAttonreyName = ''
set #vcrCurrentZip = ''
select top 1 #intCurrentIdent = ident from #tmpAttorneyImport (nolock) where parsed = 0
select #vcrCurrentAttonreyName = ltrim(rtrim(attorneyname)) from #tmpAttorneyImport (nolock) where ident = #intCurrentIdent
select #vcrCurrentZip = ltrim(rtrim(zipcode)) from #tmpAttorneyImport (nolock) where ident = #intCurrentIdent
if(len(#vcrCurrentZip) > 3)
begin
set #vcrMinZip = ''
set #vcrMaxZip = ''
select #vcrMinZip = ltrim(rtrim(left(#vcrCurrentZip, 3)))
select #vcrMaxZip = ltrim(rtrim(right(#vcrCurrentZip, 3)))
while(convert(int, #vcrMinZip) <= convert(int, #vcrMaxZip)) -- sql is telling me this line has the error
begin
insert into #tmpAttorneysFormatted(
attorneyname,
zipcode
)
select
attorneyname = #vcrCurrentAttonreyName,
zipcode = case
when len(#vcrMinZip) = 1 then '00' + ltrim(rtrim(#vcrMinZip))
when len(#vcrMinZip) = 2 then '0' + ltrim(rtrim(#vcrMinZip))
when len(#vcrMinZip) = 3 then ltrim(rtrim(#vcrMinZip))
end
select #vcrMinZip = convert(int, #vcrMinZip) + 1
end
-- this statement does not get hit
update #tmpAttorneyImport
set
parsed = 1
where
ident = #intCurrentIdent
end
else
begin
insert into #tmpAttorneysFormatted(
attorneyname,
zipcode
)
select
attorneyname = #vcrCurrentAttonreyName,
zipcode = case
when len(#vcrCurrentZip) = 1 then '00' + ltrim(rtrim(#vcrCurrentZip))
when len(#vcrCurrentZip) = 2 then '0' + ltrim(rtrim(#vcrCurrentZip))
when len(#vcrCurrentZip) = 3 then ltrim(rtrim(#vcrCurrentZip))
end
update #tmpAttorneyImport
set
parsed = 1
where
ident = #intCurrentIdent
end
end
select #vcrMinZip = ltrim(rtrim(left(#vcrCurrentZip, 3)))
select #vcrMaxZip = ltrim(rtrim(right(#vcrCurrentZip, 3)))
How sure are you that your data is clean?
I'd put in (right after this) two lines:
print #vcrMinZip
print #vcrMaxZip
and see what is actually being parsed out of the string.