2024.11.14
いまさらNode.jsを知ろう~環境構築も~
2018.01.26
DBMySQLのイベントスケジューラを設定した話
こんにちは、shiroです。
個人でサーバーを借りてMySQLを動かそうと思い、テスト用にローカルでスケジューラの作成をしていたので、今回はそれに関する話です。
まぁ、サーバーを借りたはいいけどスケジューラの機能が塞がれていたんですけどね。cron作らなきゃ。
イベントスケジューラに関する記事は探せば出てくるのですが、わかりやすい記事が少なく、苦労して作成しました。
なので設定周りに関する最低限の備忘録になっています。
今回MySQL環境はXAMPP(執筆時最新:7.1.11)を用意しました。
XAMPPはこちらからダウンロードして、インストールします。
設定事項は特に変更しませんでした。
次にコントロールパネルからApacheとMySQLをStartします。
どちらも正常に起動したら、
http://localhost/phpmyadmin/index.php
にアクセスします。
すると下図のような画面が表示されます。
DBはいくつか作成済みなので、多いですが。
データベースタブを押下し、「データベースを作成する」からデータベースを作成します。
今回はデータベース名をevent_test、照合順序をutf8_unicode_ciにします。
すると下図の画面になるので、テーブルを作成します。
テーブル名をcount_up、カラム数を2にします。
1つ目のカラムは
名前:id データ型:INT インデックス:PRIMARY AI:チェック
2爪のカラムは
名前:count データ型:INT デフォルト値:ユーザー定義、0
にします。
その後、挿入タブを押下し、下図の状態で実行ボタンを押下します。
今回は10分に1回、このテーブルのid = 1のcountを+1ずつしていくことを目的とします。
それが完了したら実行時にログを残すためのテーブルを作成します。(任意)
テーブル名をevent_log、カラム数を3にします。
1つ目のカラムは
名前:id データ型:INT インデックス:PRIMARY AI:チェック
2つ目のカラムは
名前:comment データ型:VARCHAR 長さ:50
3つ目のカラムは
名前:dt データ型:DATETIME デフォルト値:CURRENT_TIMESTAMP
にします。
さて、これで下準備ができました。
これから本格的にSQLを書いていきます。
event_testのデータベースを選択し、SQLタブに移動します。
以下のコマンドを使用してイベントスケジューラの機能を有効にしておきましょう。
SET GLOBAL event_scheduler = 1;
次いで、イベント内容(プロシージャ)の作成をします。
CREATE PROCEDUREを使用します。
DELIMITER // CREATE PROCEDURE sample_procedure() BEGIN ... END // DELIMITER ;
上記では、SQL文が2文以上の際にセミコロンで終了してしまわないよう、デリミタを変更しています。
なおphpMyAdminでは画面を見ればわかるとおり、デリミタは別で指定するので、後述するSQL文のようにDELIMITERは書きません。
その後、CREATE PROCEDURE [プロシージャ名]([引数])を書きます。
(IN [変数名] [データ型])で変数名の値を取ってきます。
カンマ区切りで複数指定が可能です。
(OUT [変数名] [データ型])で戻り値となる変数名を指定します。
今回は引数がないので空になっています。
BEGINからENDの間に実際の処理を書いていきます。
この中には
DECLARE v1 INT DEFAULT 1;
のように内部で使う変数を指定できますが、先頭に書かなければならないルールがあるようです。
では、今回のプロシージャです。
INSERT文はログを記述するだけなので、要らない場合は記述不要です。
CREATE PROCEDURE countup_procedure() BEGIN UPDATE count_up SET count = count + 1 WHERE id = 1; INSERT INTO event_log(comment) VALUES('count up procedure was done.'); END //
実行後、上図のようになれば成功です。
では、プロシージャを動かすイベントを組みましょう。
CREATE EVENTを使用します。
CREATE EVENT sample_procedure ON SCHEDULE EVERY 1 DAY STARTS '2017-01-01 00:00:00' DO call sample_procedure();
CREATE EVENT [イベント名]のイベント名はプロシージャと同じ名前にすることが多いと思います。
ON SCHEDULEは
[AT ‘{time}’]か
[EVERY ‘{interval}’ STARTS ‘{time}’ ENDS ‘{time}’]を指定します。
AT ‘{time}’は指定した日時に1回だけ実行します。
EVERY ‘{interval}’は指定した間隔で実行し、STARTS ‘{time}’とENDS ‘{time}’は開始日時と終了日時を指定します。
以下の2文は上が1回のみ、下が期間指定で1時間ごとに繰り返し実行する際の設定サンプルです。
ON SCHEDULE AT '2017-01-01 00:00:00' ON SCHEDULE EVERY 1 HOUR STARTS '2017-01-01 00:00:00' ENDS '2017-02-01 00:00:00'
intervalでは
YEAR | QUARTER | MONTH | WEEK | DAY | HOUR | MINUTE | SECOND | YEAR_MONTH | DAY_HOUR | DAY_MINUTE | DAY_SECOND | HOUR_MINUTE | HOUR_SECOND | MINUTE_SECOND
が指定可能のようです。
その後のDO call sample_procedure();がプロシージャを呼び出す処理になります。
ですので、今回の場合は
CREATE EVENT countup_procedure ON SCHEDULE EVERY 10 MINUTE STARTS now() DO call countup_procedure();
となります。
STARTS now()で登録時が開始日時になります。
これらが完了すると、
画面左部のデータベースの中にイベントとプロシージャが表示されます。
更新しても表示されない場合、キャッシュの削除をしてみてください。
自動で動きました。
やったね!
さて、イベントスケジューラの作成にプロシージャを作成してイベントを作成して……と2段階踏みましたが、これをCREATE EVENTに集約させます。
方法は簡単で、DO call している箇所を処理に置き換えるだけです。
CREATE EVENT countup_event ON SCHEDULE EVERY 10 MINUTE STARTS now() DO BEGIN UPDATE count_up SET count = count + 1 WHERE id = 1; INSERT INTO event_log(comment) VALUES('count up event was done.'); END
読んでもらえればわかるとおり、CREATE PROCEDUREの中身をそのまま持ってきているだけです。
これだけでイベント1つを設定するだけで動くようになります。
プロシージャを作成して呼ぶ形にするか、直接処理を書き込むかは場合によって使い分ける感じですかね。
快適な定期処理を!
EOF.
【記事への感想募集中!】
記事への感想・ご意見がありましたら、ぜひフォームからご投稿ください!【テクノデジタルではエンジニア/デザイナーを積極採用中です!】
下記項目に1つでも当てはまる方は是非、詳細ページへ!Qangaroo(カンガルー)
【テクノデジタルのインフラサービス】
当社では、多数のサービスの開発実績を活かし、
アプリケーションのパフォーマンスを最大限に引き出すインフラ設計・構築を行います。
AWSなどへのクラウド移行、既存インフラの監視・運用保守も承りますので、ぜひご相談ください。
詳細は下記ページをご覧ください。
最近の記事
タグ検索