15. 仕事の完了を待つ

ゴーレムが採掘に向かっても、鉱石はすぐには届きません。この章では頼んだ仕事が終わるのを待ち、その結果を確かめてから先へ進む術式を書きます。async、await、Job.Waitは初回Rebuildで解放されます。

受付と完了を分ける

Mineの結果がOkでも、採掘はまだ始まったところです。受け付けられた仕事は「ジョブ」として進みます。そのジョブをJobから受け取り、Waitで終わるのを待ちます。

ArcaneScript
public class Program : ArcaneProgram
{
    public async void OnStart()
    {
        var result = Workshop.Golems[0].Mine(Mineral.Ore, 20);
        if (!result.Ok)
        {
            return;
        }
        var job = result.Job;
        await job.Wait();
        if (job.Status == JobStatus.Completed)
        {
            Workshop.Log.Write("Mining completed.");
        }
    }
}

最初のifで受付を確認します。!result.OkならreturnでOnStartを終えるため、その後のJobには触れません。受け付けられた場合だけ次の行へ進みます。

awaitの行で待ってから続ける

await job.Wait();へ来ると、そのメソッドの先の処理をいったん待ちます。ジョブの待機が解除されると、その次のifへ進みます。asyncはそのメソッドでawaitを使えるようにする指定です。

取消や失敗でも待機は解除されます。そのためjob.Status == JobStatus.Completedで正常に完了したかを確かめてから文章を出しています。

一定時間だけ待つ

await Workshop.Clock.Delay(1.0);はオンライン中の時間で1秒待ちます。1.0のように小数点のある数も使えます。指定できるのは0〜86400秒です。Delayだけではジョブの完了は分かりません。

待機中は別イベントを同時に実行しません。待機中に来たOnTickは最新1件にまとめられます。

停止した場合

Scriptを停止すると、待っていた行から再開するための続きは破棄されます。通常再開ではOnStartを初めから呼びます。再入室後の再開はOnRestoredなので、この例のOnStartは呼びません。

受け付け済みの採掘ジョブはオンライン中に進みます。Scriptの待機と、ジョブそのものは別に扱われます。

練習問題

ジョブが取り消され、Waitの待機が解除されました。この例はMining completed.を表示するでしょうか。

解答例を表示する解答例を閉じる

表示しません。待機の次の行には進みますが、StatusがCompletedではないため、ifの中に入りません。