Let's say I have rows of information in an SQL database.
I want to have rows of information that are older than 30 days to be automatically removed.
Is this possible?
Additional information:
I am using the SQL date function provided to collect the dates.
This problem has two aspects:
How to schedule
Actual SQL Statement
How to Schedule
You have multiple options, but all of this revolves around whether you will schedule, or whether you will have a stored procedure triggered.
Three options
Use MySql event scheduling: http://dev.mysql.com/doc/refman/5.1/en/events-overview.html
Schedule through an operating system (CRON, SCHEDULED TASK) the execution of an app using SQL (either PHP script, java etc)
Have a trigger that is executes a stored procedure every time a change is made to a table.
I would propose options 1 and 2 are the best.
SQL Statement
The actual SQL statement is quite easy provided you have a field (e.g. dateField) that represents insertDate...
delete from myTable where insertDate < DATE_SUB(NOW(), INTERVAL 1 MONTH);
You can easily generate this value using the NOW() function within an insert statement, for example:
insert into myTable values (NOW(), 'value1', 'value2', ... , 'valueN');
Scheduling Using Event Scheduler at End of Day
If you have the CREATE EVENT privilege this will work through PHP MyAdmin.
See also: http://www.sitepoint.com/how-to-create-mysql-events/
CREATE EVENT `clean_up2`
ON SCHEDULE EVERY 1 DAY STARTS CURRENT_DATE
DO
delete from `data` where updated_on < DATE_SUB(NOW(), INTERVAL 1 MONTH);
END;
Yes. In SQL Server you could create a stored procedure to perform the delete, and create a SQL Agent job that runs every day (or a schedule of your choosing)
Related
I am running event to fetch data from main table and inserting it into Summary table
I am running MySQL event every 2 minute and calling stored procedure inside my event for some grouping, parsing and calculations from main table to summary table.
But while selecting 2 minutes records, some time last record got missed while creating summary occasionally
Frequency of missing record is in 1 day 90-100 records (1 day record count in main table is 30K).
MySQL select query inside stored procedure:
SELECT ID, COUNT(*) AS TOT_COUNT
FROM CUSTOMER
WHERE (TIMESTAMP > (DATE_FORMAT((NOW() - INTERVAL 3 MINUTE),"%Y-%m-%d
%H:%i:00"))
AND TIMESTAMP <= (DATE_FORMAT((NOW() - INTERVAL 1 MINUTE),"%Y-%m-%d %H:%i:00")))
GROUP BY ID, NAME;
Note: selecting previous 2 minutes record, skipping current minute records
I have tried updating select statement where condition as below (missing record frequency reduced to 50%)
SELECT ID, NAME, COUNT(*) AS TOT_COUNT
FROM CUSTOMER
WHERE (SUBSTRING_INDEX(TIMESTAMP, ':', 2) != SUBSTRING_INDEX((NOW()), ':', 2)
AND SUBSTRING_INDEX(TIMESTAMP,':',2) >= SUBSTRING_INDEX((NOW() - INTERVAL 2 MINUTE),':',2))
GROUP BY ID,NAME;
Also try to catch exception by using below statement in stored procedure.
DECLARE EXIT HANDLER FOR SQLEXCEPTION
BEGIN
GET DIAGNOSTICS CONDITION 1 #sqlstate = RETURNED_SQLSTATE,
#errno = MYSQL_ERRNO, #text = MESSAGE_TEXT;
SET #full_error = CONCAT("ERROR ", #errno, " (", #sqlstate, "): ", #text);
SELECT #full_error;
INSERT INTO ERRORS_TABLE (Level,Code,Message,INSERT_TMST) VALUES ("ERROR ", #errno, #full_error, now());
END;
No event or stored procedure fail log or MySQL error log found.
also checked for null values.
If I call the stored procedure manually for that missed minute record set manually then it returns the correct count.
Can you please help me how can I debug this issue, any other perfect select query to fetch 2 minutes record or i am missing something ?
Thanks in advance
You simply cannot rely on events running precisely on time. You just can't. You have learned what happens if you do.
You're trying to create a so-called materialized view of your data in your summary table. What can you do about this? A few different things.
You can use an ordinary, non-materialized, VIEW of your data. If you have the correct indexes on your table the VIEW will most likely perform well. And it's a robust solution.
You can rewrite the stored code in your event so it handles everything since the last event ran. To do that you may need a tiny one-row table with the TIMESTAMP used in the previous run.
Switch to a RDBMS that supports materialized views natively. That's probably Oracle, so it will cost a fortune.
Say you have a query you want to run on your database, but you know that query is going to take a long time to complete, and you don't have direct access to the machine where MySQL is running, or to some other endpoint which has a stable connection with that machine. What do you do?
Well, you create a one time event that performs the necessary query.
Something like this:
CREATE EVENT <event_name>
ON SCHEDULE
AT CURRENT_TIMESTAMP + INTERVAL 10 SECOND
ENABLE DO
BEGIN
-- log the event started
INSERT INTO EventLogs (`Name`, `Start`, `Query`)
VALUES (<event_name>, CURRENT_TIMESTAMP, <query_string>);
-- run the query
....
... <query>
....
-- log the event done
UPDATE EventLogs
SET `Done` = CURRENT_TIMESTAMP
WHERE `Name` = <event_name>;
END
The above template can handle any arbitrary query.
How can i make the following query execute each hour automatically?
SELECT count(*)
FROM user_tab_columns
WHERE table_name='MYTABLE'
Usually in a DBMS exist some schedule of instrument. In Oracle the instrument is DBMS_SCHEDULER.
MySQL same have scheduler. You should check global variable event_scheduler=1. Then you can create schedule:
CREATE EVENT 'new_event'
ON SCHEDULE EVERY 1 HOUR STARTS CURRENT_TIMESTAMP
ON COMPLETION NOT PRESERVE
ENABLE
COMMENT '' DO
call new_proc();
where new_proc() is procedure with your query.
Sorry, don't really know much about this stuff!
I have a table with a few columns, one of them is called 'expirationday' and every row has its unix timestamp for this column.
I would like to know, if at all possible, how to delete a row when the time in the 'expirationday' column (for that row) is reached.
Please note that it does not need to delete rows accurately to the second, a couple of hours is fine.
script.sh
Create a shell script like this:
#!/bin/bash
mysql --user=[username] --password=[password] --database=[db name] --execute="DELETE FROM tbl_name WHERE expiration_date < NOW()
Create a cron job that executes the (it will run every 30 min)
type
crontab -e
Add:
0,30 * * * * /path/script.sh
It's worth looking at the MySQL event scheduler. You could schedule a job to run for example every half hour.
It could then call a DELETE statement directly or to call a MySQL Function or Procedure.
DELIMITER $$
CREATE
EVENT `deleteExpire`
ON SCHEDULE EVERY 1 HOUR STARTS '2015-01-01 00:00:00'
DO BEGIN
DELETE FROM mytable
WHERE expirationday < UNIX_TIMESTAMP();
END */$$
DELIMITER ;
Also see this for more example usage.
I need to delete rows from table 14 days after the DELETE query has been made. Is it possible to do this using MySQL?
You can use the built-in MySQL Event Scheduler to schedule a query or a stored routine to run at an arbitrary point in time:
This is an example of a minimal CREATE EVENT statement:
CREATE EVENT myevent
ON SCHEDULE AT CURRENT_TIMESTAMP + INTERVAL 1 HOUR
DO
UPDATE myschema.mytable SET mycol = mycol + 1;
Please mind, the Event Scheduler is disabled by default.