クォーツ公式翻訳チュートリアルシリーズ-Lesson 3

オリジナル住所:http://www.quartz-scheduler.org/documentation/2.4.0-SNAPSHOT/tutorials/tutorial-lesson-03.html

レッスン:ジョブとジョブの詳細詳細

2番目のレッスンで見たように、タスクは、インタフェースで唯一「を実行」メソッドがあり、実装するのは非常に簡単です。ここでは、仕事の性質について理解する必要がある唯一のいくつかのことであり、仕事を(...)メソッドと同様に、JobDetailsを実行するインターフェースについて。

あなたはクラスの割り当てを実装する場合、作業の特定の種類のコードを実行する方法を知っているが、クォーツの必要性は、タスク・インスタンスを持つようにしたいというさまざまな属性について知っています。これは、すでに述べたシンプルで、JobDetailで完了します。

例JobDetailはJobBuilderクラスによって構築しました。あなたは通常、感情の仕様記述言語のあなたのコードのルックス領域を作成するために、そのすべてのメソッドのstaticインポートを使用することができます。


import static org.quartz.JobBuilder.*;复制代码

のは自然クォーツポイントジョブとジョブインスタンスにおけるライフサイクルを議論する瞬間を見てみましょう。まず、私たちは最初のレッスンスニペットを振り返ってみましょう:



  // 定义任务并绑定我们的 HelloJob 类
  JobDetail job = newJob(HelloJob.class)
      .withIdentity("myJob", "group1") // name "myJob", group "group1"
      .build();

  // 触发任务立刻运行,并且妹40秒有也行
  Trigger trigger = newTrigger()
      .withIdentity("myTrigger", "group1")
      .startNow()
      .withSchedule(simpleSchedule()
          .withIntervalInSeconds(40)
          .repeatForever())            
      .build();

  // 告诉 quartz 执行调度使用的触发器
  sched.scheduleJob(job, trigger);复制代码

次のように今考えるタスククラス「HelloJob」が定義されています。


public class HelloJob implements Job {

    public HelloJob() {
    }

    public void execute(JobExecutionContext context)
      throws JobExecutionException
    {
      System.err.println("Hello!  HelloJob is executing.");
    }
  }复制代码

私たちは、タスクJobDetailインスタンスのスケジュールを指定することに注意してください、とJobDetailを構築する際、ただの仕事を実行するためのジョブ・クラスの種類を提供します。すべてのタスクスケジューリングタスクの新しいインスタンスが(...)メソッドを実行すると呼ばれる前に、それが作成されます。実行の最後には、タスクの参照クラスのインスタンスは破棄され、および実施例は、リサイクルされますとき。この動作の1つの結果が必要なタスクがあることがあり、引数のコンストラクタ(デフォルトを使用して達成していないJobFactoy)。別の結果は、ジョブステータスデータフィールドにクラス定義が無意味であるということである - 彼らの値は、タスクの実行中に保存されません。

あなたが「どのように私は間に実行するタスクのステータスを追跡することができますか?」「?どうやっプロパティ保存/タスクインスタンスを設定することができます」お尋ねしたいかもしれない彼らの答えは同じですが、キーはJobDataMap、JobDetailオブジェクトでありますその一部。

JobDataMap

JobDataMapを使用すると、タスクインスタンスを実行時には、使用可能な任意の数(連載)データオブジェクトを保持するために使用することができます。JobDataMapJavaは、Mapインタフェースの実装であり、データの元の種類を格納し、復元するためのいくつかの便利な方法を追加しました。

ここでは、構築するために定義/ JobDetailは、ストアデータ上にあるJobDataMapコードセグメントを、タスクでの追加スケジュールタスクの前に:


// 定义任务并且绑定到DumbJob类
  JobDetail job = newJob(DumbJob.class)
      .withIdentity("myJob", "group1") // name "myJob", group "group1"
      .usingJobData("jobSays", "Hello World!")
      .usingJobData("myFloatValue", 3.141f)
      .build();复制代码

以下はの実装から参照するには、タスクでJobDataMapのデータ取得の簡単な例:


public class DumbJob implements Job {

    public DumbJob() {
    }

    public void execute(JobExecutionContext context)
      throws JobExecutionException
    {
      JobKey key = context.getJobDetail().getKey();

      JobDataMap dataMap = context.getJobDetail().getJobDataMap();

      String jobSays = dataMap.getString("jobSays");
      float myFloatValue = dataMap.getFloat("myFloatValue");

      System.err.println("Instance " + key + " of DumbJob says: " + jobSays + ", and val is: " + myFloatValue);
    }
  }复制代码

あなたが永続的なストレージタスクをしたい場合、あなたは慎重に決定する必要があります(このチュートリアルのJobStoreのセクションで説明)JobDataMapオブジェクトがシリアライズされているので、彼らは簡単にバージョン管理の問題のように見えることができますので、場所。明らかに、標準のJavaの型を使用して、定義を実装していることをクラスのインスタンスは非常に安全な、しかしこれ以上、いつでも誰かが変化する必要があり、互換性を壊さないように注意しなければなりません。別のオプションは、あなたがJDBC_JobStoreとJobDataMapを置くことができるという専用モードプリミティブと文字列を入力することができ、それによって将来のシリアル化の問題の可能性を排除し、マップに格納されています。

デフォルトJobFactoryたとえば、あなたのタスククラス仕事で彼のセッターがインスタンス化した後の方法(setJobSay(文字列val)でのデータの次の例のように)、そしてQurartzが自動的に呼び出されます、に方法セッターJobDataMapキーに対応して増加した場合そのため、明示的な値は、あなたのexecuteメソッドにマップから取得していません。

トリガすることもできますJodDataMaps協会。したがってタスクが周期的スケジューラ複数のフリップフロップに格納された/再使用可能で有用である場合には、しかしながら、各個々のトリガのためには、タスクごとに異なるデータ入力を提供します。

JobDataMapタスクが実行されると、JobExeccutionContextで見つけることは容易です。これは、同じ名前の前の値をカバーするために、後者の値を使用して、JobDataMap JobDataMapとトリガーJobDetailにバインドされています。

ここでは、タスクを実行する際に、JobExecutionContextとJobDataMapの統合からデータを取得する方法を実証するための簡単な例です。


public class DumbJob implements Job {

    public DumbJob() {
    }

    public void execute(JobExecutionContext context)
      throws JobExecutionException
    {
      JobKey key = context.getJobDetail().getKey();

      JobDataMap dataMap = context.getMergedJobDataMap();  // Note the difference from the previous example

      String jobSays = dataMap.getString("jobSays");
      float myFloatValue = dataMap.getFloat("myFloatValue");
      ArrayList state = (ArrayList)dataMap.get("myStateData");
      state.add(new Date());

      System.err.println("Instance " + key + " of DumbJob says: " + jobSays + ", and val is: " + myFloatValue);
    }
  }复制代码

あなたは、データが独自のクラス地図注入することによって、JobFactory値に依存するかどうか、それは次のようになります。


public class DumbJob implements Job {


    String jobSays;
    float myFloatValue;
    ArrayList state;

    public DumbJob() {
    }

    public void execute(JobExecutionContext context)
      throws JobExecutionException
    {
      JobKey key = context.getJobDetail().getKey();

      JobDataMap dataMap = context.getMergedJobDataMap();  // Note the difference from the previous example

      state.add(new Date());

      System.err.println("Instance " + key + " of DumbJob says: " + jobSays + ", and val is: " + myFloatValue);
    }

    public void setJobSays(String jobSays) {
      this.jobSays = jobSays;
    }

    public void setMyFloatValue(float myFloatValue) {
      myFloatValue = myFloatValue;
    }

    public void setState(ArrayList state) {
      state = state;
    }

  }复制代码

あなたは、全体のコードがより明確にコード内の単一execute()メソッドでは、長いことがわかります。IDEをプログラミングすることはJobDataMapから各呼び出しの値を取得するために、手動で書き込みコードすることなく、セッターメソッドは、自分自身を持って作成する場合のコードは、長く、単一実用少ないコードであるもののひとつは、それを言うかもしれません。あなたの選択。

タスクの「インスタンス」

ユーザーは多くの時間がどのようなタスクインスタンスかなり確実ではありません過ごします。次のセクションでは、我々は、それがどのタスクの状態と並行性を明確にしてみてください。

スケジューラへのすべてのアドオンを独自の属性とJobDataMap-とそれぞれ、彼ら - あなたは別のタスククラスを作成することができ、店舗の複数JobDetailsの複数のインスタンスを作成することによって、スケジューラに「インスタンスが定義されました」。

たとえば、名前「SalesReportJob」タスクインスタンスを作成することができます。このタスクは、販売スタッフに基づいて売上レポートの名前を指定する(JobDataMapのような)送信パラメータを希望することができます。彼らは、「ジョー」と「マイク」とに対応JobDataMapsに各ジョブの入力として指定された「SalesReportForJbe」および「SaleReportForMike」のような、タスクに複数の定義(JobDetails)を作成することができます。

JobDetailがロードされる(実施例において定義される)トリガ点火、アソシエーション、およびクラスのタスクインスタンスがJobFactoryを参照されるとき、スケジューリングを実行するように構成される。デフォルトJobFactoryコールのnewInstance・ジョブ・クラス()メソッド、クラス上に呼び出すことと方法JobDataMapキー名が一致することを意図。あなたのアプリケーションIOCまたはDIコンテナの生産/初期化タスクインスタンスを完了するために、独自のJobFactoryインスタンスを作成することもできます。

「クォーツ話す」では、我々は、我々は、「ジョブ・インスタンス」または「ジョブ定義のインスタンス」のように実行された各タスクを参照して、「ジョブdefiniton」または「JobDetailインスタンス」のように、格納された各JobDetailを参照してください。私たちは言葉だけの「仕事」を使用する場合、一般的に、我々は名前が定義されて言及し、またはJobDetail。私たちは、ジョブ・クラスのインスタンスを参照するとき、私たちは通常、用語「ジョブ・クラス」を使用します。

そして、並列タスクのステータス

(すなわちJobDataMap)と並列)のジョブステータスデータについて何か、今注釈付き。ここではノートのペアは、あなたのタスククラス、インパクトQuzrtzの振る舞いに追加することができています。

@DisallowConcurrentExecutionタスククラスはタスク定義石英(ここで指定されたタスククラス)指定された複数のインスタンスの並列実行を語っていない、アノテーションで添加することができるです。言葉遣いは非常に慎重に選択されていることに注意してください。一例では、「SalesReportJob」このアノテーション場合、唯一の「SalesReportForJoe」としては、例えば、指定された時間で行うことができるが、並列に「SaleReportForMike」インスタンスを実行することができます。制約条件は、実施例(JobDetail)、ないタスクのインスタンスに基づいて定義されます。それは多くの場合、エンコードクラスに影響を与えるようしかし、それは、(クォーツ設計時)かどうか、プロセス自体にコメントに依存しています。

@PersistJobDataAfterExecutionタスククラスは、execute()メソッドを実行した後Quzrtzを伝える、コメントを追加することができることは、JobDetail JobDataMapストレージを更新する(スローされない)成功した​​ので、次回同じタスク(JobDetail)は更新値を受信し、実行します格納された値は、タスクの例のよう@DisallowConcurrentExcetionない場合、タスクはクラスではないが、一般的に符号化クラスに影響を与えるため、タスククラスの性質に応じて、インスタンスです。(同様に「ステートフル」は、実行メソッドのコードによって「理解」が明らかに必要であろう)。

あなたは@PersistJobDataAfterExecutionこのコメントを使用する場合は、@DisallowConcurrentExecutionノートを使用している可能混乱(カオススピード)に同じタスクデータ(JobDetail)パラレルストレージリードを避けるために、慎重に検討する必要があります。

その他のタスクプロパティ

ここでは、オブジェクトのJobDetailその他のプロパティで、タスクインスタンスの定義の簡単な概要は以下のとおりです。

  • 持続性 - タスクは永久ではない場合、彼は一度トリガーのいずれかに関連付けられていないタスクスケジューラを実行する、トリガーの存在下での結合の非耐久性のあるタスクのライフ・サイクル。
  • 回収可能性 - タスクスケジューラ、それが再実行され、その後、タスク、「回復可能」場合、それは「ハードクローズ」(ある、ベンの崩壊を実行する過程で、プロセス、またはマシンシャットダウン)によって実行されたときに再び開始。この場合には、真JobExecutionContext.isRecovering()メソッドを返します。

JobExecutionException

最後に、私たちはあなたに指示する必要がありJob.execute(...)詳細の一部を。あなたは、実行メソッドから例外を投げることができる例外の唯一のタイプは、(RuntimeEcxeptionを含ん)JobExecutionExceptionです。このため、あなたは通常「のtry-catch」ブロックの内容全体を詰めなければなりません。またJobExecutionExcetionの一部にあなたが例外を処理する方法を決定するために、スケジューラのためのさまざまなコマンドを提供し、文書を読むために時間を取る必要があります。

ブログ記事複数のプラットフォームからこの記事OpenWriteリリース!

おすすめ

転載: juejin.im/post/5de0dd2d5188254cb43db753