MySQL Trigger with multiple IF statements not working - mysql

I'm working on an 'audit_history' table that stores updates performed on my 'myTable' table. My code works with just the single IF statement that handles password updates. But as soon as I add another, I get the #1064 SQL Error. So I'm guessing it's something to do with my delimiters(?), but I just can't get it to work.
Any and all help would be great. Thanks.
IF (NEW.password <> OLD.password)
OR (NEW.password IS NOT NULL AND OLD.password IS NULL)
OR (NEW.password IS NULL AND OLD.password IS NOT NULL)
THEN
INSERT INTO myTable.audit_history
VALUES (
'update'
, NULL
, NOW()
, #user_id
, 'user'
, 'password'
, OLD.password
, NEW.password);
END IF;
IF (NEW.landline <> OLD.landline)
OR (NEW.landline IS NOT NULL AND OLD.landline IS NULL)
OR (NEW.landline IS NULL AND OLD.landline IS NOT NULL)
THEN
INSERT INTO myTable.audit_history
VALUES (
'update'
, NULL
, NOW()
, #user_id
, 'user'
, 'landline'
, OLD.landline
, NEW.landline);
END IF;
I get this error message:
#1064 - You have an error in your SQL syntax; check the manual that corresponds to you MySQL server version for the right syntax to use near ‘IF (NEW.landline <> OLD.landline) OR (NEW.landline IS NOT NULL AND OLD.landline’ at line 17

You need BEGIN and END keywords for multiple statements
BEGIN
IF (NEW.password <> OLD.password)
OR (NEW.password IS NOT NULL AND OLD.password IS NULL)
OR (NEW.password IS NULL AND OLD.password IS NOT NULL)
THEN
INSERT INTO myTable.audit_history
VALUES (
'update'
, NULL
, NOW()
, #user_id
, 'user'
, 'password'
, OLD.password
, NEW.password);
END IF;
IF (NEW.landline <> OLD.landline)
OR (NEW.landline IS NOT NULL AND OLD.landline IS NULL)
OR (NEW.landline IS NULL AND OLD.landline IS NOT NULL)
THEN
INSERT INTO myTable.audit_history
VALUES (
'update'
, NULL
, NOW()
, #user_id
, 'user'
, 'landline'
, OLD.landline
, NEW.landline);
END IF;
END;

Related

I want to throw an exception when my mysql stored procedure doesn't find any results

I'm having trouble finding a way to throw an exception from a stored procedure if no data is found.
I need a way to check the query results in the if statement.
If the count is 0 then throw exception. If there's data then return the data.
CREATE DEFINER=`adminHC`#`%` PROCEDURE `find_user_with_credentials`(
IN `usernameIN` VARCHAR(45)
, IN `encryptedpwIN` VARCHAR(45)
)
BEGIN
SELECT *
FROM (SELECT distinct
userid
,firstname
,lastname
,publicname
,email
,addressid
,create_date
,update_date
,active
FROM dev_users
WHERE (email = usernameIN OR (
publicname IS NOT null AND
publicname = usernameIN
))
AND encryptedpw = encryptedpwIN
AND active = 1) user;
IF count(user) > 0 THEN
SELECT user;
ELSE
SIGNAL SQLSTATE '45000'
SET MESSAGE_TEXT = "Invalid username or password",
MYSQL_ERRNO = 403;
END IF;
END
Start with a SELECT COUNT(*) query and check the result of that.
CREATE DEFINER=`adminHC`#`%` PROCEDURE `find_user_with_credentials`(
IN `usernameIN` VARCHAR(45)
, IN `encryptedpwIN` VARCHAR(45)
)
BEGIN
IF (SELECT COUNT(*)
FROM dev_users
WHERE (email = usernameIN OR (
publicname IS NOT null AND
publicname = usernameIN
))
AND encryptedpw = encryptedpwIN
AND active = 1) > 0
THEN SELECT
userid
,firstname
,lastname
,publicname
,email
,addressid
,create_date
,update_date
,active
FROM dev_users
WHERE (email = usernameIN OR (
publicname IS NOT null AND
publicname = usernameIN
))
AND encryptedpw = encryptedpwIN
AND active = 1;
ELSE
SIGNAL SQLSTATE '45000'
SET MESSAGE_TEXT = "Invalid username or password",
MYSQL_ERRNO = 403;
END IF;
END
There's also no need for the SELECT * wrapper. And I doubt you need SELECT DISTINCT, since I assume you can't have multiple rows with the same userid, and there's nothing in the query that will duplicate rows.
If the query were too expensive to do twice, you could do it once and save the results in a temporary table. Then you can use SELECT COUNT(*) FROM temp_table to check if there are any results, and finally SELECT * FROM temp_table to return the data.

Sql add condition IF

I have sql like :
SELECT * FROM leads_notes WHERE content <> '' AND lead_id <> ''
I need add rule if type <> close_task then write user_change_task_status IS NULL
My result sql is:
SELECT * FROM leads_notes WHERE content <> '' AND lead_id <> '' IF(task_type <> 'close_task', 'AND user_change_task_status IS NULL',)
But i get many errors.
Cant understand how can i solve this. Please help, thanks!
Don't use if. Boolean logic is sufficient:
WHERE content <> '' AND
lead_id <> '' AND
( type = 'close_task' or user_change_task is null)
Or:
WHERE content <> '' AND
lead_id <> '' AND
NOT ( type = 'close_task' and user_change_task is not null )

NiFi ExecuteSqlRecord not processing SQL query(Presto)

I am running a simple Pivot query in Presto via "ExecuteSqlRecord" processor but the moment I run the processor it gives me the error: Unable to execute SQL select.
Query is:
with map_date as
(
SELECT
vin,
epoch,
timestamp,
date,
map_agg(signalName, value) as map_values
from hive.vehicle_signals.vehicle_signals_flat
where date(date) = date('2020-02-28')
and vin = '000015'
and signalName in ('timestamp','epoch','msgId','usec','vlan','vin','msgName','A','B','C','D','E','F','G','H',
'J','K','L','M','N','O','P','R','S','T','U','V','W','X',
'Y','Z','A1','A5','A2','A3','A4','A6','A8','A9','A10','A11','A12')
GROUP BY vin, epoch, timestamp, date
order by timestamp asc
)
SELECT
epoch
, timestamp
, CASE WHEN element_at(map_values, 'A') IS NOT NULL THEN map_values['A'] ELSE NULL END AS A
, CASE WHEN element_at(map_values, 'B') IS NOT NULL THEN map_values['B'] ELSE NULL END AS B
, CASE WHEN element_at(map_values, 'C') IS NOT NULL THEN map_values['C'] ELSE NULL END AS C
, CASE WHEN element_at(map_values, 'D') IS NOT NULL THEN map_values['D'] ELSE NULL END AS D
, CASE WHEN element_at(map_values, 'E') IS NOT NULL THEN map_values['E'] ELSE NULL END AS E
, CASE WHEN element_at(map_values, 'F') IS NOT NULL THEN map_values['F'] ELSE NULL END AS F
, CASE WHEN element_at(map_values, 'G') IS NOT NULL THEN map_values['G'] ELSE NULL END AS G
, CASE WHEN element_at(map_values, 'H') IS NOT NULL THEN map_values['H'] ELSE NULL END AS H
, CASE WHEN element_at(map_values, 'J') IS NOT NULL THEN map_values['J'] ELSE NULL END AS J
, CASE WHEN element_at(map_values, 'K') IS NOT NULL THEN map_values['K'] ELSE NULL END AS K
, CASE WHEN element_at(map_values, 'L') IS NOT NULL THEN map_values['L'] ELSE NULL END AS L
, CASE WHEN element_at(map_values, 'M') IS NOT NULL THEN map_values['M'] ELSE NULL END AS M
, CASE WHEN element_at(map_values, 'N') IS NOT NULL THEN map_values['N'] ELSE NULL END AS N
, CASE WHEN element_at(map_values, 'O') IS NOT NULL THEN map_values['O'] ELSE NULL END AS O
, CASE WHEN element_at(map_values, 'P') IS NOT NULL THEN map_values['P'] ELSE NULL END AS P
, CASE WHEN element_at(map_values, 'R') IS NOT NULL THEN map_values['R'] ELSE NULL END AS R
, CASE WHEN element_at(map_values, 'S') IS NOT NULL THEN map_values['S'] ELSE NULL END AS S
, CASE WHEN element_at(map_values, 'T') IS NOT NULL THEN map_values['T'] ELSE NULL END AS T
, CASE WHEN element_at(map_values, 'U') IS NOT NULL THEN map_values['U'] ELSE NULL END AS U
, CASE WHEN element_at(map_values, 'V') IS NOT NULL THEN map_values['V'] ELSE NULL END AS V
, CASE WHEN element_at(map_values, 'W') IS NOT NULL THEN map_values['W'] ELSE NULL END AS W
, CASE WHEN element_at(map_values, 'X') IS NOT NULL THEN map_values['X'] ELSE NULL END AS X
, CASE WHEN element_at(map_values, 'Y') IS NOT NULL THEN map_values['Y'] ELSE NULL END AS Y
, CASE WHEN element_at(map_values, 'Z') IS NOT NULL THEN map_values['Z'] ELSE NULL END AS Z
, CASE WHEN element_at(map_values, 'A1') IS NOT NULL THEN map_values['A1'] ELSE NULL END AS A1
, CASE WHEN element_at(map_values, 'A2') IS NOT NULL THEN map_values['A2'] ELSE NULL END AS A2
, CASE WHEN element_at(map_values, 'A3') IS NOT NULL THEN map_values['A3'] ELSE NULL END AS A3
, CASE WHEN element_at(map_values, 'A4') IS NOT NULL THEN map_values['A4'] ELSE NULL END AS A4
, CASE WHEN element_at(map_values, 'A5') IS NOT NULL THEN map_values['A5'] ELSE NULL END AS A5
, CASE WHEN element_at(map_values, 'A6') IS NOT NULL THEN map_values['A6'] ELSE NULL END AS A6
, CASE WHEN element_at(map_values, 'A8') IS NOT NULL THEN map_values['A8'] ELSE NULL END AS A8
, CASE WHEN element_at(map_values, 'A9') IS NOT NULL THEN map_values['A9'] ELSE NULL END AS A9
, CASE WHEN element_at(map_values, 'A10') IS NOT NULL THEN map_values['A10'] ELSE NULL END AS A10
, CASE WHEN element_at(map_values, 'A11') IS NOT NULL THEN map_values['A11'] ELSE NULL END AS A11
, CASE WHEN element_at(map_values, 'A12') IS NOT NULL THEN map_values['A12'] ELSE NULL END AS A12
, vin
, date
from map_date
I can run the ABOVE query in ExecuteSqlRecord perfectly fine if I pivot only ~20 fields but when pivoting ~37 fields then the ExecuteSqlRecord processor immediately Fails.
It is interesting to see that I can run the same pivot query with ~37 fields in Presto CLI and QueryDatabaseTable successfully! Please help me achieve this in ExecuteSQLRecord processor as it has the added benefit of writing the output flowfile in any desired format (for my case, I am writing the output of the SQL query as CSV)
Here is the full stack trace of the error,
java.sql.SQLException: Error executing query. No FlowFile to route to failure: java.sql.SQLException: Error executing query
java.sql.SQLException: Error executing query
at com.facebook.presto.jdbc.PrestoStatement.internalExecute(PrestoStatement.java:279)
at com.facebook.presto.jdbc.PrestoStatement.execute(PrestoStatement.java:228)
at com.facebook.presto.jdbc.PrestoPreparedStatement.<init>(PrestoPreparedStatement.java:80)
at com.facebook.presto.jdbc.PrestoConnection.prepareStatement(PrestoConnection.java:129)
at org.apache.commons.dbcp2.DelegatingConnection.prepareStatement(DelegatingConnection.java:303)
at org.apache.commons.dbcp2.DelegatingConnection.prepareStatement(DelegatingConnection.java:303)
at org.apache.nifi.processors.standard.AbstractExecuteSQL.onTrigger(AbstractExecuteSQL.java:237)
at org.apache.nifi.processor.AbstractProcessor.onTrigger(AbstractProcessor.java:27)
at org.apache.nifi.controller.StandardProcessorNode.onTrigger(StandardProcessorNode.java:1176)
at org.apache.nifi.controller.tasks.ConnectableTask.invoke(ConnectableTask.java:213)
at org.apache.nifi.controller.scheduling.TimerDrivenSchedulingAgent$1.run(TimerDrivenSchedulingAgent.java:117)
at org.apache.nifi.engine.FlowEngine$2.run(FlowEngine.java:110)
at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
at java.base/java.util.concurrent.FutureTask.runAndReset(FutureTask.java:305)
at java.base/java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:305)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
at java.base/java.lang.Thread.run(Thread.java:834)
Caused by: java.lang.RuntimeException: Error fetching next at http://presto.testk8s.content.mywebspace.com:8889/b7/journal/20245300229_0354554_08r940_as8y4/2?slug=78234778257265 returned an invalid response: JsonResponse{statusCode=500, statusMessage=Server Error, headers={connection=[close]}, hasValue=false} [Error: ]
at com.facebook.presto.jdbc.internal.client.StatementClientV1.requestFailedException(StatementClientV1.java:446)
at com.facebook.presto.jdbc.internal.client.StatementClientV1.advance(StatementClientV1.java:386)
at com.facebook.presto.jdbc.PrestoResultSet.getColumns(PrestoResultSet.java:1742)
at com.facebook.presto.jdbc.PrestoResultSet.<init>(PrestoResultSet.java:119)
at com.facebook.presto.jdbc.PrestoStatement.internalExecute(PrestoStatement.java:250)
... 17 common frames omitted

Why "drop procedure if exists konami" not working in mysql?

I write a mysql script , it works fine :
use cloud_fight;
drop procedure if exists `konami`;
drop function if exists `rand_string`;
delimiter //
CREATE FUNCTION `rand_string`(n INT) RETURNS varchar(255)
BEGIN
DECLARE chars_str varchar(255) DEFAULT 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789rew';
DECLARE return_str varchar(255) DEFAULT '';
DECLARE i INT DEFAULT 0;
while i < n do
SET return_str = concat(return_str,substring(chars_str , FLOOR(1 + RAND()*64 ),1));
SET i = i + 1;
END while;
RETURN return_str;
END //
delimiter $$
create procedure konami()
begin
declare q int default 1;
while q<=2 DO
set #N=rand_string(64);
insert into fight_user (user_guid , first_name , last_name , user_name , nick_name , gender , city , province , country , head_img_url , created_at , last_updated) values (#N, '' , '' , '' , rand_string(5) , '2' , 'bj' , 'bj' , 'cn' , '' , now() , now());
insert into fight_user_cake (fight_user_id , t_id , third_party_user_id , type , created_at , last_updated , status) select id , '2' , rand_string(20) , 'WECHAT_UNIONID' , now() , now() , 1 from fight_user where user_guid = #N;
insert into fight_user_cake (fight_user_id , t_id , third_party_user_id , type , created_at , last_updated , status) select id , '2' , rand_string(20) , 'MP_OPENID' , now() , now() , 1 from fight_user where user_guid = #N;
insert into fight_user_cake (fight_user_id , t_id , third_party_user_id , type , created_at , last_updated , status) select id , '2' , rand_string(20) , 'PA_OPENID' , now() , now() , 1 from fight_user where user_guid = #N;
set q=q+1;
end while;
end $$
call konami();
But when I move the command " drop procedure if exists konami " to the front of procedure konami() as shown below:
drop function if exists `rand_string`;
delimiter //
CREATE FUNCTION `rand_string`(n INT) RETURNS varchar(255)
BEGIN
DECLARE chars_str varchar(255) DEFAULT 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789rew';
DECLARE return_str varchar(255) DEFAULT '';
DECLARE i INT DEFAULT 0;
while i < n do
SET return_str = concat(return_str,substring(chars_str , FLOOR(1 + RAND()*64 ),1));
SET i = i + 1;
END while;
RETURN return_str;
END //
drop procedure if exists `konami`;
delimiter $$
create procedure konami()
begin
declare q int default 1;
while q<=2 DO
set #N=rand_string(64);
insert into fight_user (user_guid , first_name , last_name , user_name , nick_name , gender , city , province , country , head_img_url , created_at , last_updated) values (#N, '' , '' , '' , rand_string(5) , '2' , 'bj' , 'bj' , 'cn' , '' , now() , now());
insert into fight_user_cake (fight_user_id , t_id , third_party_user_id , type , created_at , last_updated , status) select id , '2' , rand_string(20) , 'WECHAT_UNIONID' , now() , now() , 1 from fight_user where user_guid = #N;
insert into fight_user_cake (fight_user_id , t_id , third_party_user_id , type , created_at , last_updated , status) select id , '2' , rand_string(20) , 'MP_OPENID' , now() , now() , 1 from fight_user where user_guid = #N;
insert into fight_user_cake (fight_user_id , t_id , third_party_user_id , type , created_at , last_updated , status) select id , '2' , rand_string(20) , 'PA_OPENID' , now() , now() , 1 from fight_user where user_guid = #N;
set q=q+1;
end while;
end $$
call konami();
When I run the second script in mysql workbench 6.3.
It report error : Error Code: 1304. PROCEDURE konami already exists
So my question is when I move the command " drop procedure if exists konami " to the front of procedure konami() , why is this statement "drop procedure if exists konami" not working ?
Since you changed to DELIMITER // you need to use that delimiter at the end of each statement until you change it back.
DROP PROCEDURE and CREATE PROCEDURE are separate statements, and each requires its own statement delimiter.
DROP PROCEDURE IF EXISTS konami //

Mysql conditional case when as column doesnt compile

SELECT
DISPLAY_ID,
PICKER_NAME,
CREDIT,
HOURLY_RATE,
DAILY_RATE,
WEIGHT,
CASE
WHEN (DeviceGroups IS NOT NULL AND WorkerGroups IS NOT NULL) THEN CONCAT(DeviceGroups,',',WorkerGroups);
WHEN (DeviceGroups IS NULL AND WorkerGroups IS NOT NULL) THEN WorkerGroups;
WHEN (DeviceGroups IS NOT NULL AND WorkerGroups IS NULL) THEN DeviceGroups;
WHEN (DeviceGroups IS NULL AND WorkerGroups NOT NULL) THEN NULL;
END as GROUPS
FROM....
I try to use Case When syntax with as for alians, i get this error :
SQL query: Documentation
SELECT DISPLAY_ID, PICKER_NAME, CREDIT, HOURLY_RATE, DAILY_RATE, WEIGHT,
CASE
WHEN (
DeviceGroups IS NOT NULL
AND WorkerGroups IS NOT NULL
)
THEN CONCAT( DeviceGroups, ',', WorkerGroups ) ;
MySQL said: Documentation
1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '' at line 9
Remove the semicolon :
SELECT
DISPLAY_ID,
PICKER_NAME,
CREDIT,
HOURLY_RATE,
DAILY_RATE,
WEIGHT,
CASE
WHEN (DeviceGroups IS NOT NULL AND WorkerGroups IS NOT NULL) THEN CONCAT(DeviceGroups,',',WorkerGroups)
WHEN (DeviceGroups IS NULL AND WorkerGroups IS NOT NULL) THEN WorkerGroups
WHEN (DeviceGroups IS NOT NULL AND WorkerGroups IS NULL) THEN DeviceGroups
WHEN (DeviceGroups IS NULL AND WorkerGroups IS NULL) THEN NULL
END as GROUPS
FROM....
In standard SQL, a semicolon(;) is used to end the query .