Set a limit occurrence for a value in a mysql table - mysql

So let's say i have a table that has a column "id_author" , i'd like to set a limit for the occurrence of the same value ; example : can't have more than 3 same "id_author" values so when i insert the 4th one it's refused.
Is there a way to implement this? Thanks

You can use a trigger before insert, that will throw a signal in case it violates your condition:
CREATE TRIGGER tooManyRecords
BEFORE INSERT ON yourTable
FOR EACH ROW
BEGIN
DECLARE counter INTEGER;
SELECT COUNT(*) INTO counter FROM yourTable
WHERE id_author = NEW.id_author;
IF counter >= 3 THEN
SIGNAL SQLSTATE '45000' SET message_text = 'there are already 3 records for the provided id';
END

Related

MySQL: how to make an attribute "nullable" only if certain condition

I am creating a table for a DB, and I would like (if possible) to do something like this:
Attribute X can be NULL if, and only if, attribute Y is "value1".
Is there a way to do this? I want to do this because I could delete an entity, reducing the complexity of my project (or at least I think I would get some advantages).
Thanks :)
In very recent versions of MySQL, you can use a check constraint for this:
create table mytable (
x int,
y int,
check(x is not null or y = 1)
)
If MySQL version is not new enough for to use CHECK constraint (below 8.0.16) then use
DELIMITER ##;
CREATE TRIGGER tr_bi_check_my_constraint
BEFORE INSERT
ON my_table
FOR EACH ROW
BEGIN
IF NEW.attribute_X IS NULL AND NEW.attribute_Y != 'value1' THEN
SIGNAL SQLSTATE 45000
SET MESSAGE_TEXT = 'Attribute X can be NULL if, and only if, attribute Y is "value1".';
END IF;
END
##;
CREATE TRIGGER tr_bu_check_my_constraint
BEFORE UPDATE
ON my_table
FOR EACH ROW
BEGIN
IF NEW.attribute_X IS NULL AND NEW.attribute_Y != 'value1' THEN
SIGNAL SQLSTATE 45000
SET MESSAGE_TEXT = 'Attribute X can be NULL if, and only if, attribute Y is "value1".';
END IF;
END
##;
DELIMITER ;

set maximum limits in mysql sql database

I have 2 tables. Concerts / Tickets
I want to set Concert 1 to have maximum of 100 tickets and Concert 2 to have maximum of 200 tickets. so like have a concert_id be linked with a maximum number of ticket_id.
How can I do this in mysql? thanks
You can write triggers:
delimiter //
drop trigger if exists limitInsertsTrigger //
create trigger limitInsertsTrigger before insert on tickets
for each row
begin
declare msg varchar(128);
if (select count(*) from tickets where concert_id = new.concert_id)>
(select max_tickets_number from concert where id=new.concert_id)
then
set msg = concat('MyTriggerError: Trying to insert too many tickets');
signal sqlstate '45000' set message_text = msg;
end if;
end //
Remember to have a max_tickets_number column in the concert table.

error 1329 (02000): no data - zero rows fetched, selected, or processed

I am getting an error in the following code below. The error is #1329 - No data - zero rows fetched, selected, or processed. What exactly does this mean and what is it that i am doing incorrectly? Thanks
create or replace procedure grade()
begin
declare no,s1,s2,s3,cnt,i,per int(20);
declare c1 cursor for select roll,sub1,sub2,sub3 from student;
set i=0;
select count(*) into cnt from student;
open c1;
while i<=cnt do
fetch c1 into no,s1,s2,s3;
set per=s1+s2+s3/3;
if per>=90 then
update student set grade='A+' where roll=no;
elseif (per<90 and per>=80)then
update student set grade='A' where roll=no;
elseif (per<80 and per>=70)then
update student set grade='B+' where roll=no;
elseif (per<70 and per>=60)then
update student set grade='B' where roll=no;
elseif (per<60 and per>=50)then
update student set grade='C+' where roll=no;
elseif (per<50 and per>=40)then
update student set grade='C' where roll=no;
else
update student set grade='FAIL' where roll=no;
end if;
set i=i+1;
end while;
close c1;
end$$
This logic:
set i = 0;
select count(*) into cnt from student;
while i <= cnt do
is going through the loop 1 extra time. It is on the last trip through the loop that you are getting the error.
If cnt is 3, for instance, then the loops are:
0
1
2
3
You either want:
set i = 1
or alternatively
while i < cnt
In SQL, I would use the first method, because things usually start counting at 1 rather than 0 in SQL -- but they are equivalent.

How to create a before insert trigger based on previously inserted values in the table

I have a table which contains two columns
1.Clanid
2.Active
My problem is that i dont want any value in Clanid column to be inserted in this table if this value is already in Clanid column and Active for that value is 1.
For example
Clanid Active
1 1
2 1
3 0
Now it should not be possible to insert a record with Clanid=1 and Active=1 but i can insert Clanid=3 and Active=1 as this record is not there.
Try this:
delimiter //
create trigger unique_clanid
before insert on mytable
for each row
begin
if new.active and exists (
select * from mytable
where clanid = new.clanid
and active) then
signal sqlstate '02000' set MESSAGE_TEXT = 'Duplicate ClanID';
end if;
end//
delimiter ;
I think you should handle in your app level, but you want to handle in DB lavel, you can write trigger check it
you can check count record ( where Clanid = #param and Active =1)
if count > 1 : rollback
I am not available mysql to test , i just can describe my solution as following ( i;m not sure the syntax correct, it is too long time i don't write trigger in mysql)
CREATE TRIGGER test BEFORE INSERT ON table_name
FOR EACH ROW
BEGIN
DECLARE newClanId integer;
DECLARE counts integer;
Set #newClanId = NEW.Clanid;
Set #count := (SELECT count (*) FROM table_name
WHERE Clanid = #newClanId and Active =1)
IF #count > 1 THEN ROLLBACK;
END;

MYSQL - can a extra column is forced to update every time

i have a table with 3 column A, B, & C.
when ever some one update any column(A or B or both) it should update column C also.
Means someone cann't just write "update tableName set a=1, b=2 where blah blah".
It should be always "update tableName set a=something, b=something2, c=something3 where blah blah".
if someone don't do it, it returns some error.
i tried using trigger. But it didn't help me out. Below is the trigger that executed before update.
BEGIN
DECLARE TIMESTAMP DATE DEFAULT now();
DECLARE msg VARCHAR(255);
IF NEW.C IS NULL OR NEW.C = "" THEN
SET msg = concat("Trying TO UPDATE NULL OR empty VALUE of C.");
SIGNAL SQLSTATE "4500" SET MESSAGE_TEXT = msg;
END IF;
END
New.C give the Existing Value of C in row