Insert data from Aliases - sql

enter image description hereI have Cyrillic text for input and Latin for output. in Cyrillic I have a variable and I can insert it in a table
But how can I create a variable for the output as well.
I also need to create a variable for EN (output parameters) so that I can insert it into a table or if there is another option.
DECLARE #TEXT NVARCHAR(1000)
SET #TEXT = 'Днес'
DECLARE #EN NVARCHAR(1000)
SET #EN =''
insert into [Anatoli].[dbo].[logg]([date1],lo,[lo1]) values(GETDATE(),#TEXT,ЕN)
SELECT
#TEXT as BG
,replace(replace(replace(replace(replace(replace
(replace(replace(replace(replace(replace(replace(replace(replace
(replace(replace(replace(replace(replace(replace(replace(replace(replace
(replace(replace(replace(replace(replace(replace(replace
(#TEXT,'и','i'),'в','v'),'а','a'),'н','n'),'б','b' )
,'г','g'),'д','d'),'e','е'),'ж','zh'),'з','z'),'й','y'),'к','k')
,'л','l'),'м','m'),'о','o'),'п','p'),'р','r'),'с','s'),'т','t'),'у','u')
,'ф','f'),'х','h'),'ц','ts'),'ч','ch'),'ш','sh'),'щ','sht'),'ъ','a'),'ь','y')
,'ю','yu'),'я','yа') AS EN
Expected result
on the picture

If your Cyrillic-Latin translation needs to be reusable it's going to be most versatile in an Inline Table-Valued Function, e.g.:
create function dbo.app_CyrillicToLatin(
#Cyrillic nvarchar(1000)
)
returns table as
return (
select [Latin] =
replace(replace(replace(replace(replace(replace(replace(replace(
replace(replace(replace(replace(replace(replace(replace(replace(
replace(replace(replace(replace(replace(replace(replace(replace(
replace(replace(replace(replace(replace(replace(#Cyrillic,
N'и', N'i'), N'в', N'v'), N'а', N'a'), N'н', N'n'), N'б', N'b' ),
N'г', N'g'), N'д', N'd'), N'е', N'e'), N'ж', N'zh'), N'з', N'z'),
N'й', N'y'), N'к', N'k'), N'л', N'l'), N'м', N'm'), N'о', N'o'),
N'п', N'p'), N'р', N'r'), N'с', N's'), N'т', N't'), N'у', N'u'),
N'ф', N'f'), N'х', N'h'), N'ц', N'ts'), N'ч', N'ch'), N'ш', N'sh'),
N'щ', N'sht'), N'ъ', N'a'), N'ь', N'y'), N'ю', N'yu'), N'я', N'yа')
);
go
This gives you the flexibility to set variables, as requested, as well as translate in a set-based fashion for INSERT, UPDATE and SELECT operations...
-- Usage 1, setting a variable
select #EN = Latin
from dbo.app_CyrillicToLatin(#TEXT);
-- Usage 2, translating during insert...
insert into [dbo].[logg] ([date1], [lo], [lo1])
select getdate(), #TEXT, Latin
from dbo.app_CyrillicToLatin(#TEXT);
-- Usage 3, translating during update...
update L
set [lo1] = Latin
from [dbo].[logg] L
cross apply dbo.app_CyrillicToLatin([lo]);
-- Usage 4, translating during select...
select [date1], [lo], [Latin] as [lo1]
from [dbo].[logg]
cross apply dbo.app_CyrillicToLatin([lo]);

Related

Scalar variable issue not being able to use in Select Query SQL Server

I 'm not able to use both Declare statements in my select query when I do the insert into.
How do you use a column itemId to be set in a another column called id?
How do you write a same string to a specific column?
Why can't I call my scalar variable ?
DECLARE #Solutions_id as INT
DECLARE #Solutions_name as nvarchar(50)
INSERT INTO ticket_historical_actions
(
[id]
,[type]
[Solutions _rowId]
,[Solutions_dw_dateCreate]
,[Solutions_dw_dateMod]
,[Solutions_dw_dateDelete]
,[Solutions_sourceId]
,[Solutions_date_create]
,[Solutions_date_mod]
,[Solutions_date_approval]
,[Solutions_itemId]
,[Solutions_solutionTypeName]
,[Solutions_content_plainText]
,[Solutions_userId]
,[Solutions_userId_editor]
,[Solutions_userId_approval]
,[Solutions_userName]
,[Solutions_userName_approval]
,[Solutions_status]
,[Ticket_rowId]
,[Ticket_dw_dateCreate]
,[Ticket_dw_dateMod]
,[Ticket_dw_dateDelete]
,[Ticket_sourceId]
,[Ticket_date_create]
,[Ticket_date_mod]
,[Ticket_date_close]
,[Ticket_date_solve]
,[Ticket_entityId]
,[Ticket_name]
,[Ticket_date]
,[Ticket_status]
,[Ticket_is_deleted]
,[Ticket_content_PlainText]
,[Ticket_type]
,[Ticket_urgency]
,[Ticket_impact]
,[Ticket_priority]
,[Ticket_requestTypeId]
,[Ticket_userId_lastUpdater]
,[Ticket_userId_recipient]
,[Ticket_time_to_resolve]
,[Ticket_time_to_own]
,[Users_rowId]
,[Users_dw_dateCreate]
,[Users_dw_dateMod]
,[Users_dw_dateDelete]
,[Users_sourceId]
,[Users_date_create]
,[Users_date_mod]
,[Users_name]
,[Users_LastName]
,[Users_firstName]
,[Users_phone]
,[Users_mobile]
,[Users_language]
,[Users_profileId]
,[Users_entitieId]
,[Users_titleId]
,[Users_categoryId]
,[Users_managerId]
,[Company_rowId]
, [Company_dw_dateCreate]
,[Company_dw_dateMod]
,[Company_dw_dateDelete]
,[Company_sourceId]
,[Company_date_mod]
,[Company_date_create]
,[Company_completename]
,[Company_name]
,[Company_address]
,[Company_postcode]
,[Company_town]
,[Company_state]
,[Company_country]
,[Company_phonenumber]
,[Company_email]
,[Company_admin_email]
,[Company_admin_name]
)
SELECT
#Solutions_id =[itemId], #Solutions_name = 'Solutions',
ts.[rowId]
,ts.[dw_dateCreate]
,ts.[dw_dateMod]
,ts.[dw_dateDelete]
,ts.[sourceId]
,ts.[date_create]
,ts.[date_mod]
,ts.[date_approval]
,ts.[itemId]
,ts.[solutionTypeName]
,ts.[content_plainText]
,ts.[userId]
,ts.[userId_editor]
,ts.[userId_approval]
,ts.[userName]
,ts.[userName_approval]
,ts.[status]
, tt. [rowId]
,tt.[dw_dateCreate]
,tt.[dw_dateMod]
,tt.[dw_dateDelete]
,tt.[sourceId]
,tt.[date_create]
,tt.[date_mod]
,tt.[date_close]
,tt.[date_solve]
,tt.[entityId]
,tt.[name]
,tt.[date]
,tt.[status]
,tt.[is_deleted]
,tt.[content_PlainText]
,tt.[type]
,tt.[urgency]
,tt.[impact]
,tt.[priority]
,tt.[requestTypeId]
,tt.[userId_lastUpdater]
,tt.[userId_recipient]
,tt.[time_to_resolve]
,tt.[time_to_own]
, tu.[rowId]
,tu.[dw_dateCreate]
,tu.[dw_dateMod]
,tu.[dw_dateDelete]
,tu.[sourceId]
,tu.[date_create]
,tu.[date_mod]
,tu.[name]
,tu.[LastName]
,tu.[firstName]
,tu.[phone]
,tu.[mobile]
,tu.[language]
,tu.[profileId]
,tu.[entitieId]
,tu.[titleId]
,tu.[categoryId]
,tu.[managerId]
, tc. [rowId]
,tc.[dw_dateCreate]
,tc.[dw_dateMod]
,tc.[dw_dateDelete]
,tc.[sourceId]
,tc.[date_mod]
,tc.[date_create]
,tc.[completename]
,tc.[name]
,tc.[address]
,tc.[postcode]
,tc.[town]
,tc.[state]
,tc.[country]
,tc.[phonenumber]
,tc.[email]
,tc.[admin_email]
,tc.[admin_name]
FROM
ticket_ticketSolutions ts
left join ticket_tickets tt
on ts.itemId =tt.sourceId
left join ticket_users tu
on ts.userId = tu.sourceId
left join ticket_company tc
on tu.entitieId = tc.sourceId
Would tell me if possible how to do it?
Thank you very much.
I'm just going to answer, even though I have stated this in the comments of both your questions.
The problem here is you are trying to assign a value to your variables in the same statement you are trying to return a dataset; in T-SQL that in not allowed.
In short, you have something like this:
SELECT #MyVariable = SomeColumn,
AnotherColumn
FROM dbo.YourTable
WHERE ID = 'SomeID';
So you want to return the value of AnotherColumn to the presentation layer, but assign the value of SomeColumn to the variable #MyVariable; you can't do this.
Instead, you have to use 2 statements:
SELECT #MyVariable = SomeColumn --Assigns the value to #MyVariable
FROM dbo.YourTable
WHERE ID = 'SomeID';
SELECT AnotherColumn --Returns the dataset to the presentation layer
FROM dbo.YourTable
WHERE ID = 'SomeID';

Error Handling for numbers of delimiters when extracting substrings

Situation: I have a column where each cell can have up to 5 delimiters. However, it's possible that there are none.
Objective: How do i handle errors such as :
Invalid length parameter passed to the LEFT or SUBSTRING function.
in the case that it cannot find the specified delimiter.
Query:
declare #text VARCHAR(111) = 'abc-def-geeee-ifjf-zzz'
declare #start1 as int
declare #start2 as int
declare #start3 as int
declare #start4 as int
declare #start_index_reverse as int
set #start1 = CHARINDEX('-',#text,1)
set #start2 = CHARINDEX('-',#text,charindex('-',#text,1)+1)
set #start3 = CHARINDEX('-',#text,charindex('-',#text,CHARINDEX('-',#text,1)+1)+1)
set #start4 = CHARINDEX('-',#text,charindex('-',#text,CHARINDEX('-',#text,CHARINDEX('-',#text,1)+1)+1)+1)
set #start_index_reverse = CHARINDEX('-',REVERSE(#text),1)
select
LEFT(#text,#start1-1) AS Frst,
SUBSTRING(#text,#start1+1,#start2-#start1-1) AS Scnd,
SUBSTRING(#text,#start2+1,#start3-#start2-1) AS Third,
SUBSTRING(#text,#start3+1,#start4-#start3-1)AS Third,
RIGHT(#text,#start_index_reverse-1) AS Lst
In this case my variable includes 5 delimiters and so my query works but if i removed one '-' it would break.
XML support in SQL Server brings about some unintentional but useful tricks. Converting this string to XML allows for some parsing that is far less messy than native string handling, which is very far from awesome.
DECLARE #test varchar(111) = 'abc-def-ghi-jkl-mnop'; -- try also with 'abc-def'
;WITH n(x) AS
(
SELECT CONVERT(xml, '<x>' + REPLACE(#test, '-', '</x><x>') + '</x>')
)
SELECT
Frst = x.value('/x[1]','varchar(111)'),
Scnd = x.value('/x[2]','varchar(111)'),
Thrd = x.value('/x[3]','varchar(111)'),
Frth = x.value('/x[4]','varchar(111)'),
Ffth = x.value('/x[5]','varchar(111)')
FROM n;
For a table it's almost identical:
DECLARE #foo TABLE ( col varchar(111) );
INSERT #foo(col) VALUES('abc-def-ghi-jkl-mnop'),('abc'),('def-ghi');
;WITH n(x) AS
(
SELECT CONVERT(xml, '<x>' + REPLACE(col, '-', '</x><x>') + '</x>')
FROM #foo
)
SELECT
Frst = x.value('/x[1]','varchar(111)'),
Scnd = x.value('/x[2]','varchar(111)'),
Thrd = x.value('/x[3]','varchar(111)'),
Frth = x.value('/x[4]','varchar(111)'),
Ffth = x.value('/x[5]','varchar(111)')
FROM n;
Results (sorry about the massive size, seems this doesn't handle 144dpi well):
add a test before your last select
then you should decide how to handle the other case (when one of start is 0)
You can also refer to this link about splitting a string in sql server
which is uses a loop and can handle any number of delimiters
if #start1>0 and #start2>0 and #start3>0 and #start4>0
select LEFT(#text,#start1-1) AS Frst,
SUBSTRING(#text,#start1+1,#start2-#start1-1) AS Scnd,
SUBSTRING(#text,#start2+1,#start3-#start2-1) AS Third,
SUBSTRING(#text,#start3+1,#start4-#start3-1)AS Third,
RIGHT(#text,#start_index_reverse-1) AS Lst

How can I write this SQL while loop code to get an XML results in one line instead of 3 separate lines?

I'm trying to get all this XML result in one line instead of 3 for each column
DECLARE #ii INT = 10;
DECLARE #String1 NVARCHAR(4000);
SET #String1 = '';
WHILE(#ii <= 18)
BEGIN
SET #String1 = (#String1 + 'SELECT LoanNumber = ''Complaint'+CONVERT(VARCHAR(2),#ii)+'-Call1'' , LoanStatus=''Compliants'' , LoanStatusDate = CAST(GETDATE() AS DATE)
UNION
SELECT LoanNumber = ''Complaint'+CONVERT(VARCHAR(2),#ii)+'-Call2'', LoanStatus=''Compliants'' , LoanStatusDate = CAST(GETDATE() AS DATE)
UNION
SELECT LoanNumber = ''Complaint'+CONVERT(VARCHAR(2),#ii)+'-Call3'', LoanStatus=''Compliants'' , LoanStatusDate = CAST(GETDATE() AS DATE)')
IF #ii != 18
SET #string1 = #string1 + ' UNION '
ELSE
SET #string1 = #string1 + 'FOR XML PATH (''Loan''),ROOT(''Loans'') '
SET #ii = #ii+1
END
EXEC sp_executesql #String1
I want something like this:
<Loans>
<LoanNumber>Complaint10-Call1<LoanStatus>Compliants<LoanStatusDate>2019-01-18
</Loan>
<Loan>
<LoanNumber>Complaint10-Call2 <LoanStatus>Compliants<LoanStatusDate>2019-01-18
</Loan>
<Loan>
<LoanNumber>Complaint10-Call3<LoanStatus>Compliants<LoanStatusDate>2019-01-18
</Loan>
Instead of the result that you get when you execute the code I provided. I appreciate your help.
This might be wild guessing, but I've got the feeling, that I understand, what this is about:
if you run the code you will see the result. no input data is needed .
I just want the structure of the xml outcome to all be on one line for
one set of each loop
Your provided code leads to this:
<Loans>
<Loan>
<LoanNumber>Complaint10-Call1</LoanNumber>
<LoanStatus>Compliants</LoanStatus>
<LoanStatusDate>2019-01-22</LoanStatusDate>
</Loan>
<Loan>
<LoanNumber>Complaint10-Call2</LoanNumber>
<LoanStatus>Compliants</LoanStatus>
<LoanStatusDate>2019-01-22</LoanStatusDate>
</Loan>
<!-- more of them-->
</Loans>
This is perfectly okay, valid XML.
But you want the result
outcome to all be on one line for one set of each loop
Something like this?
<Loans>
<Loan>
<LoanNumber>Complaint10-Call1</LoanNumber><LoanStatus>Compliants</LoanStatus><LoanStatusDate>2019-01-22</LoanStatusDate>
</Loan>
<!-- more of them-->
</Loans>
There is a big misconception I think... XML is not the thing you see. The same XML can look quite differently, without any semantic difference:
Check this out:
DECLARE #xmltable table(SomeXml XML)
INSERT INTO #xmltable VALUES
--the whole in one line
('<root><a>test</a><a>test2</a></root>')
--all <a>s in one line
,('<root>
<a>test</a><a>test2</a>
</root>')
--each element in one line
,('<root>
<a>test</a>
<a>test2</a>
</root>')
--white space going wild...
,('<root>
<a>test</a>
<a>test2</a>
</root>');
--now check the results
SELECT * FROM #xmltable;
This means: How the XML appears is a matter of the interpreter. The same XML opened with another tool might appear differently. Dealing with XML means dealing with data but not with format... The actual format has no meaning and should not matter at all...
Starting with SQL-Server 2016 you might have a look at JSON, if you need a tiny format:
DECLARE #somedata table(SomeValue VARCHAR(100),SomeStatus VARCHAR(100),SomeDate DATE);
INSERT INTO #somedata VALUES
('Complaint10-Call1','Complaints','2019-01-22')
,('Complaint10-Call2','Complaints','2019-01-22')
,('Complaint10-Call3','Complaints','2019-01-22');
SELECT * FROM #somedata FOR JSON PATH;
The result comes in one line:
[{"SomeValue":"Complaint10-Call1","SomeStatus":"Complaints","SomeDate":"2019-01-22"},{"SomeValue":"Complaint10-Call2","SomeStatus":"Complaints","SomeDate":"2019-01-22"},{"SomeValue":"Complaint10-Call3","SomeStatus":"Complaints","SomeDate":"2019-01-22"}]

Update(Replace partcial value) XML Column in SQL

I have an XML column in my Table and i wanted to replace particular text wherever it appear in that column with a new text. Here is the xml structure,
<Story>
<StoryNonText>
<NonText>
<ImageID>1</ImageID>
<Src>http://staging.xyz.com/FolderName/1.png</Src>
</NonText>
<NonText>
<ImageID>2</ImageID>
<Src>http://staging.xyz.com/FolderName/2.png</Src>
</NonText>
</StoryNonText>
</Story>
In the above XML I wanted to replace all the <Src> values having http://staging.xyz.com/ to http://production.xyz.com/. Please guide me how i can do this!
You can use Replace() function as below:
Update TableName
SET
ColumnName=replace(CAST(ColumnName AS VARCHAR(8000)),'<Src>http://staging.xyz.com/','<Src>http://production.xyz.com/')
With a little help from a couple of XML functions you can do this in a loop.
The loop is necessary since replace value of can only replace one value at a time. This code assumes the URL is located first in the node and not embedded in text anywhere.
declare #T table(X xml);
insert into #T(X) values('<Story>
<StoryNonText>
<NonText>
<ImageID>1</ImageID>
<Src>http://staging.xyz.com/FolderName/1.png</Src>
</NonText>
<NonText>
<ImageID>2</ImageID>
<Src>http://staging.xyz.com/FolderName/2.png</Src>
</NonText>
</StoryNonText>
</Story> ');
declare #FromURL nvarchar(100);
declare #ToURL nvarchar(100);
set #FromURL = 'http://staging.xyz.com/';
set #ToURL = 'http://production.xyz.com/';
while 1 = 1
begin
update #T
set X.modify('replace value of (//*/text()[contains(., sql:variable("#FromURL"))])[1]
with concat(sql:variable("#ToURL"), substring((//*/text()[contains(., sql:variable("#FromURL"))])[1], string-length(sql:variable("#FromURL"))+1))')
where X.exist('//*/text()[contains(., sql:variable("#FromURL"))]') = 1;
if ##rowcount = 0
break;
end;
select *
from #T
replace value of (XML DML)
concat Function (XQuery)
contains Function (XQuery)
string-length Function (XQuery)
sql:variable() Function (XQuery)
There are many ways to do that.
The first way is to add a WHILE loop. Inside a loop, you search (CHARINDEX) for a position of first tag and first tag. Then, knowing the start and end positions, replace the value. Then on the next iteration you search again, but change starting position in CHARINDEX() function
The second way is to use SELECT ... FROM OPENXML + EXEC sp_xml_preparedocument

How to remove links from text with SQL

I need to clean up a database by removing links from tables. So for column entry like this:
Thank you for the important information<br />Read More Here<br /> This is great.
i need to remove the entire link, so it would end up like this:
Thank you for the important information<br /><br /> This is great.
Is there a way to do this with a single UPDATE statement?
For extra credit, is there a way to remove the HTML semantics from the link, while leaving the content in the text?
Just try to find the starting and ending of the hrefj and replace it with a single space.
declare #StringToFix varchar(500)
set #StringToFix = 'Thank you for the important information<br /><a href="http://www.cnn.com">Read More'
select REPLACE(
#stringtofix
, Substring(#StringToFix
, CHARINDEX('<a href=', #StringToFix) -- Starting Point
-- End Point - Starting Point with 4 more spaces
, CHARINDEX('</a>', #StringToFix)
- CHARINDEX('<a href=', #StringToFix) +4 )
, ' '
) as ResultField
If all the links are done in a very consistent way than you can just use a regex replace of
'\<a href.*?\</a\>'
to an empty string.
I don't have SQL Server instance handy but the query in oracle would look something like:
update table
set col1 = REGEXP_REPLACE(col1,'\<a href.*?\</a\>', '', 1, 0, 'in');
I want share my sql script that remove ahref tag from text but leave anchor text.
Source text:
Visit Google, then Bing
Result text:
Visit Google, then Bing
MS SQL CODE:
declare #str nvarchar(max) = 'Visit Google, then Bing'
declare #aStart int = charindex('<a ', #str)
declare #aStartTagEnd int = charindex('>', #str, #aStart)
DECLARE #result nvarchar(max) = #str;
set #result = replace(#result, '</a>', '')
select #result
WHILE (#aStart > 0 and #aStartTagEnd > 0)
BEGIN
declare #rep1 nvarchar(max) = substring(#result, #aStart, #aStartTagEnd + 1 - #aStart)
set #result = replace(#result, #rep1, '')
set #aStart = charindex('<a ', #result)
set #aStartTagEnd = charindex('>', #result, #aStart)
END
select #result