Dynamic appending constraints in SQL query - sql

I have this SQL
SELECT devudp1.deviceoid,devudp1.valueType
FROM DeviceUdpValues devUDP1
WHERE devudp1.udpname='TestUDP'
and <<either bdvalue or string value based on user selected value datatype>>
Here in the Query based on the devudp1.valueType I want to append below attribute
If the valueType is 3 then I want to append my above select clause with devudp1.bdvalue ='10', else it should be appended by devudp1.bdvalue = 'Hello'
So the above query when valueType is 3 will look like
SELECT devudp1.deviceoid,devudp1.valueType
FROM DeviceUdpValues devUDP1
WHERE devudp1.udpname='TestUDP'
AND devudp1.bdvalue = '10'
else it will look like
SELECT devudp1.deviceoid,devudp1.valueType
FROM DeviceUdpValues devUDP1
WHERE devudp1.udpname='TestUDP'
AND devudp1.stringValue = 'Hello'
Can anyone suggest me how to put this logic in place

Try this:
SELECT devudp1.deviceoid,devudp1.valueType
FROM DeviceUdpValues devUDP1
WHERE devudp1.udpname='TestUDP'
AND (
(<USER-SELECTED-VALUE> = 3 AND devudp1.bdvalue ='10') OR
(<USER-SELECTED-VALUE> <> 3 AND devudp1.stringvalue ='Hello')
)

Related

WHERE JSON_Value Dynamically

I am working with the JSON_VALUE function and I need a kind of dynamic query
I have a column called Criteria and sometimes it has 1 value but sometimes it has 2 or 3 vales like:
Example of 1 value: $.IRId = 1
Example of 2 values: $.IROwner = 'james.jonson#domain.com' AND DaysTillDue < 10
So in order to read the values from a JSON column and taking the Criteria column I am using this logic:
DECLARE #CriteriaValue int
,#CriteriaStatement VARCHAR(50)
SELECT #CriteriaValue=SUBSTRING(Criteria, CHARINDEX('=',Criteria)+1, len(Criteria)) FROM #SubscriptionCriteria;
SELECT #CriteriaStatement= SUBSTRING(Criteria,0, CHARINDEX('=',Criteria)) FROM #SubscriptionCriteria;
SELECT #CriteriaValue,#CriteriaStatement
SELECT *
FROM [SAAS].[ObjectEvent]
WHERE
JSON_VALUE(JSONMessageData, #CriteriaStatement) = #CriteriaValue
That SQL code is taking only the Criteria Column with only 1 value ($.IRId = 1), but the idea is to have something that reads the criteria no matter the different filters and apply them into the final query. The idea I have is that the query would look like this:
SELECT *
FROM [SAAS].[ObjectEvent]
WHERE
JSON_VALUE(JSONMessageData, #CriteriaStatement1) = #CriteriaValue1 ADN JSON_VALUE(JSONMessageData, #CriteriaStatement2) = #CriteriaValue2 AND
JSON_VALUE(JSONMessageData, #CriteriaStatement3) = #CriteriaValue3
ETC
Any suggestion?

Add filter on column which subtract to columns

i have long store procedure in whcih i want Add filter on this Column
select (PaymentAmount-PaymentPosted) as Unapplied, BalancDue from ERAMaster
where Unapplied = 22
but i run the query they give me error invalid column name. any one tell me the write way to Add filter on Unapplied Column
You can do it like below :
select * from
(
select (PaymentAmount-PaymentPosted) as Unapplied, BalancDue from ERAMaster
) as T where Unapplied = 22
Or like this :
select (PaymentAmount-PaymentPosted) as Unapplied, BalancDue from ERAMaster
where PaymentAmount-PaymentPosted = 22
It should be like this:
select (PaymentAmount-PaymentPosted) as Unapplied, BalancDue from ERAMaster
where (PaymentAmount-PaymentPosted) = 22
'Unapplied' is not a column name it is only alias.

How to give change working of having function dynamicaly on executing an sql statement?

I'm having a Sql code like as follows
Select a.ItemCode, a.ItemDesc
From fn_BOM_Material_Master('A', #AsOnDate, #RptDate, #BranchID, #CompID)a
Left Outer Join fn_INV_AsOnDate_Stock(#StockDate, #AsOnDate, #RptDate, #BranchID, #CompID, #Finyear)b
On a.ItemCode=b.ItemCode and b.WarehouseCode<>'WAP'
and a.BranchID=b.BranchID and a.CompID=b.COmpID
Where a.ItemNatureCode = 'F' and a.BranchID = #BranchID and a.CompID = #CompID
Group by a.ItemCode, a.ItemDesc
Having sum(b.CBQty)<=0
Here the problem is that im passing an "#ShowZeroStock" value as as bit if the "#ShowZeroStock" value is '1' then Having should not be validated or (i.e: All values from the table should be returned including zero)
So How to change the query based on passed bit value "#ShowZeroStock"
I can Use "If else " condition at the top and remove having in else part, but for a lengthy query i can't do the same.
Is this the logic you want?
Having sum(b.CBQty) <= 0 or #ShowZeroStock = 1

Check if a value exists in a collection stored in XML data type column

I have an XML data type column called "tags".
In that, I am storing a collection, like so:
<ArrayOfString>
<string>personal</string>
<string>travel</string>
<string>gadgets</string>
<string>parenting</string>
</ArrayOfString>
I want to select all the rows, that have one of the values that I am looking for: for example, I want to select all rows in the table that have a tag "travel".
I know that this works, if I know the index of the value I am looking for:
select * from posts
where tags.value('(/ArrayOfString/string)[1]', 'nvarchar(1000)') = 'travel'
but this query works only if the tag "travel" is the 2nd item in the nodes. How do I check if a value exists, irrespective of the position it is in?
select *
from tags
where tags.exist('/ArrayOfString/string[. = "travel"]') = 1
Or like this if you want to check against a variable.
declare #Val varchar(10)
set #Val = 'travel'
select *
from tags
where tags.exist('/ArrayOfString/string[. = sql:variable("#Val")]') = 1
You can try something like this:
SELECT
*
FROM
dbo.Posts
WHERE
tags.exist('/ArrayOfString/string/text()[. = "travel"]') = 1
This will list all the rows that have "travel" in one of the strings in your XML

Modify Return Value of SELECT-Statement (TSQL) [Optimizing query]

Problem:
A Database collumn has a Tristate (0,1,2).
Each of the values are used serversidely.
The Clientcode (which cant be changed anymore) is only able to understand '0,1'.
In the Clients view '1' is identic with '2'. So I want to change the SQL Query in the Database to return '1', if the specific value is > 0.
My current Solution is combining 2 Selects (using UNION SELECT) with different WHERE-Clauses and returning '1' or '0' as static values. Now I'm looking for a solution to 'translate' the value within only ONE SELECT statement.
This is my current Solution:
SELECT
dbo.Nachricht.NachrichtID, dbo.Nachricht.Bezeichnung, '1' AS BetrifftKontoeinrichtung,
FROM dbo.Nachricht INNER JOIN dbo.AdditionalData
ON dbo.Nachricht.NachrichtID = dbo.AdditionalData.NachrichtID
WHERE (dbo.Nachricht.NachrichtID in ( 450,439 ))
AND dbo.AdditionalData.BetrifftKontoeinrichtung > 0
UNION SELECT
dbo.Nachricht.NachrichtID, dbo.Nachricht.Bezeichnung, '0' AS BetrifftKontoeinrichtung,
FROM dbo.Nachricht INNER JOIN dbo.AdditionalData
ON dbo.Nachricht.NachrichtID = dbo.AdditionalData.NachrichtID
WHERE (dbo.Nachricht.NachrichtID in ( 450,439 ))
AND dbo.AdditionalData.BetrifftKontoeinrichtung = 0
You can use a case statement, like this:
SELECT
dbo.Nachricht.NachrichtID, dbo.Nachricht.Bezeichnung,
CASE WHEN dbo.AdditionalData.BetrifftKontoeinrichtung = 0
THEN '0' ELSE '1'
END AS BetrifftKontoeinrichtung,
FROM dbo.Nachricht
INNER JOIN dbo.AdditionalData
ON dbo.Nachricht.NachrichtID = dbo.AdditionalData.NachrichtID
WHERE (dbo.Nachricht.NachrichtID in ( 450,439 ))
Looks like you need to use CASE. A decent tutorial here
http://www.databasejournal.com/features/mssql/article.php/3288921/T-SQL-Programming-Part-5---Using-the-CASE-Function.htm
See the worked example
If you just CAST(CAST(val AS BIT) AS INT) you will get integer 0 for 0 and integer 1 for everything else.