アイドルヲタ開発エンジニアの備忘録

個人的な学習した内容の備忘録です。

シェルスクリプトとcronを使ってJavaプロジェクトを自動実行する

はじめに

今回は、「シェルスクリプト」と「cron」を用いて、

Javaプロジェクトを自動実行する手順について記録していきたいと思います。

メインは「シェルスクリプト」と「cron」の設定ですが、個人的にJavaプロジェクトの扱い方に悩んだ時間が長かったため、コンパイルの部分から手順に含めていきます。

 

開発環境

macOS

・JDK17

・Spring Tool Suite4

PostgreSQL

Eclipseで作成したJavaプロジェクトで問題ありません

 

前提

今回は、「削除扱いになっているユーザーデータ」を「削除済みユーザーテーブル」にデータ移行をするJavaプロジェクトを自動実行するというケースで行います。

プロジェクト自体のコードは割愛しますが、実際に使用するクラスは以下の通りです。

 

 ・DBmanager  → DriverManagerクラスを使用して、データベースへの接続、切断を管理するクラス

 ・DeletedUser → 削除済みユーザー情報を持つEntityクラス

 ・DeletedUserDao → 削除済みユーザーテーブルを操作するDaoクラス( insert処理 )

 ・InsertDeletedUser → 実行を行うMainクラス( ユーザ情報を取得し、削除済みユーザーテーブルへinsert )

 ・UserDao → ユーザーテーブルを操作するDaoクラス

         ( 削除扱いユーザー情報のSELECT処理と移行完了データのユーザーテーブルからの削除)

 

 

手順

①プロジェクト外にコンパイル後のクラスを格納するディレクトリの作成

②作成したプロジェクトのコンパイルを行う(postgeSQLドライバーも格納)

コンパイル後のクラスを格納するディレクトリにmanifest.mfを作成する

④jarファイルを作成する

シェルスクリプトファイルを作成する(実行権限の確認も行う)

⑥cronに自動実行を行う処理を記載する

 

①プロジェクト外にコンパイル後のクラスを格納するディレクトリの作成

保存したいディレクトリに移動してから、コンパイル後のクラスを格納する「deleted_user_compile」ディレクトリを作成する。

ターミナル
 

 % cd / Users / 自分のhome / workspace

 % mkdir deleted_user_compile

 

 

②作成したプロジェクトのコンパイルを行う(postgeSQLドライバーも格納)

コンパイルしたいプロジェクトのクラスが格納されているディレクトリの1つ上のディレクトリに移動し、依存関係の数が少ないクラスからコンパイルをする。

※両方満たさないと「シンボルがありません」のエラーが出てコンパイルできません。

 

ターミナル
 
 % cd ./ test_shell_cron / src
 
 % javac -d .. / .. / deleted_user_compile . / shell_cron / DBManager.java
 % javac -d .. / .. / deleted_user_compile . / shell_cron / DeletedUser.java
 % javac -d .. / .. / deleted_user_compile . / shell_cron / UserDao.java
 % javac -d .. / .. / deleted_user_compile . / shell_cron / DeletedUserDao.java
 % javac -d .. / .. / deleted_user_compile . / shell_cron / InsertDeletedUser.java
 

 

今回の場合、依存関係の数が少ないクラスの順番は、

⒈「DBManagerクラス」

⒉「DeletedUserクラス」(エンティティクラス)

⒊「UserDaoクラス」(Daoクラス)

⒋「DeletedUserDaoクラス」(Daoクラス)

⒌「InsertDeletedUserクラス」(Mainクラス)

となっており、ざっくりな順番だと

DBManagerクラス → エンティティクラス → Daoクラス → Mainクラス

で行うと問題ないかと思います。

 

そして、このコンパイルディレクトリに「PostgreSQLドライバー」のjarファイルを格納することを忘れないようにします。

 

この時点でのコンパイルディレクトリの中身は以下のようになります。

▽deleted_user_compile

 

▽deleted_user_compile / shell_cron

 

コンパイル後のクラスを格納するディレクトリにmanifest.mfを作成する

「deleted_user_comile」ディレクトリに移動した後、

manifest.mfを作成し、その中にメインメソッドのクラスの設定を行います。

 

ターミナル
 
 % cd .. / .. / deleted_user_comiple 
 
 % vi manifest.mf
 
 ---------- ↓ viエディタ ------------------
 Main-Class : shell_cron / InsertDeletedUser
 
 ------------------------------------------
 

ここでの注意点は、

「Main-Class:」の後、必ず空欄「 」を入れることと、

「〜/ InsertDeletedUser」の後改行をすることです。

これがないと上手く実行できないことがあります。

 

④jarファイルを作成する

コンパイルしたクラスのjarファイルを作成します。

 

ターミナル
 
 % jar -cvfm insert_deleted_item.jar manifest.mf .
 

 

ちなみにここで指定しているオプションは以下の通りです。

 -c : jarファイルの新規作成
 -v : コンソールに処理内容を表示
 -f  jarファイル名の指定
 -m : マニフェストファイルの指定

 

シェルスクリプトファイルを作成する(実行権限の確認も行う)

Javaプロジェクト(「test_shell_cron」)に戻り、シェルスクリプトファイルを作成する。

(シェルスクリプトファイル自体は別にJavaプロジェクトに入れなくてもいいかもしれませんが、管理しやすいのでこちらに作成します。)

シェルスクリプトファイルには実行したいファイルの記載と、必要なクラスパスを記載します。

 

ターミナル
 
 % cd .. / test_shell_cron / src
 
 % vi insert_deleted_user.sh
 
 ---------↓ viエディタ---------------
 # ! / bin / bash
 
 java -cp / Users / 自分のhome / workspace / deleted_user_compile / postgresql-42.6.0.jar :/ Users / 自分のhome / workspace / deleted_user_compile / insert_deleted_user.jar shell_cron / InsertDeletedUser
 
 ------------------------------------
 

 

まず、1行目に 「#!/bin/bash」もしくは「#!/bin/sh」を記載する。

bashにしかない機能を使用したいときにこの記載がないと動かない可能性があるため記載しておく。

 

そして、自動実行したいクラスを指定する。

java -cp 依存関係にあるクラスのパス(:繋ぎで記載する) 実行したいクラス」

今回は依存関係にあるのは、「postgreSQLドライバー」とメインクラスと依存関係にあるクラスもまとまっている「insert_deleted_user.jarファイル」のため、

その2つのをパスを記載したあと、メインクラスを記載する。

 

ここで、現在の「insert_deleted_user.sh」ファイルの権限を確認し、

「実行権限」が付与されていない場合は付与しておく。

 

ターミナル
 
 % chmod u+x insert_deleted_user.sh
 

 

所有者(ユーザー)に実行権限(x)を持たせる。

 

⑥cronに自動実行を行う処理を記載する

最後にcronに実行したい日時とファイルを記載します。

 

ターミナル
 
 % sudo crontab -u root -e
 Password:(パスワードを入力)
 
 --------↓ crontabファイル----------
 00 22 1 * * / Users / 自分のhome / workspace / test_shell_cron / src /
 insert_deleted_user.sh
 -------------------------------------
 

 

crontabファイルの中は、

「分 時 日 月 曜日 実行したいこと」

を記載します。

今回の場合は「毎月1日22:00にinsert_deleted_user.shファイルを実行する」ということになります。

 

以上となります。

1つパスが間違っていたり、1つプロジェクト内でエラーが出るともちろん自動実行はされません。

実行されないときは、「Javaプロジェクト内のエラー」なのか

シェルスクリプトファイル内のパスの記載ミス」なのか

「crontabのパスや時間設定にミスがないか」なのかを段階ごとに確認すると発見できました。

特に「Javaプロジェクト内のエラー」はSTSEclipse上の実行ではエラーを吐かなかったのに、

ターミナルでJavaプロジェクトを実行するとエラーを吐くなどが結構あったので、

一度コマンドでの実行でエラーが出ないか確認した方がいいなと思いました。

 

もっとスマートな方法もあるのかもしれませんが、発見したらまた別記事でまとめたいと思います。