差分cook (-cookincremental) 有効時、BlueprintのConstruction Script変更後に"Content is missing from cook"でcookが失敗します

差分cookを利用している環境で、BlueprintのConstruction Scriptに含まれるAdd Component系ノードの構成を変更した後、cookが以下のエラーで失敗することがあります。

ログ例:

LogCook: Error: Content is missing from cook. Source package referenced an object in target package but the object was stripped out of the target package when saved.

Source package: /Game/<Project>/Maps/<RootMap>/_Generated_/<GeneratedPackageName>

Target package: /Game/<Project>/Path/To/<BlueprintAsset>

Referenced object: /Game/<Project>/Path/To/<BlueprintAsset>.<BlueprintClass>:NODE_Add<CustomComponent>-0

同様のエラーが複数のgenerated packageから出ており、参照先オブジェクト名は以下のようなConstruction ScriptのAdd Componentノード由来と思われる名前です。

- NODE_Add<CustomComponent>-0

- NODE_Add<CustomComponent>-2

最終的には以下で失敗します。

AutomationTool exiting with ExitCode=25 (Error_UnknownCookFailure)

こちらの推測:

差分cookにより、過去のgenerated package側に古いConstruction ScriptのAdd Componentノード由来のコンポーネントテンプレート参照が残っているように見えます。

一方で、変更後のBlueprint packageをcook保存する際には、その古いNODE_Add…オブジェクトが存在しない、またはstripされるため、参照検証で"Content is missing from cook"になっているのではないかと考えております。

暫定回避策:

現状、Saved/Cookedを削除した後に再度パッケージ作成を行い、エラーに対処している状態です。

​​​

確認させて頂きたい事:

1. 差分cookとBlueprint Construction ScriptのAdd Component系ノード変更の組み合わせで、このようなstale referenceが残ることは既知の制限でしょうか。

2. /<MapName>/_Generated_/以下のgenerated packageは、参照先BlueprintのConstruction Scriptのコンポーネント構成が変わった場合、自動的に無効化・再生成される想定でしょうか。

3. 差分cookを継続利用しつつ、この問題を避ける推奨運用はありますでしょうか。

4. Saved/Cooked全体を削除する以外に、影響を受けたgenerated/cooked packageだけを無効化するcookオプションやcommandletはありますでしょうか。

5. レベルに配置されるActor Blueprintでは、Construction Script内のAdd Component系ノードを避けた方がよろしいでしょうか。

[Attachment Removed]

再現手順
環境:

  • Unreal Engine 5.7.4
  • Windows / Win64
  • UAT BuildCookRunによるパッケージ作成
  • 差分cook有効
    • ​-cookincremental
  • マルチプロセスcook有効
    • AdditionalCookerOptions=“-cookprocesscount=2”

再現手順:

1. 差分cookを有効にした状態で、パッケージ作成を正常完了させます。

2. レベルに配置、またはルートマップから参照されるActor Blueprintを用意します。

3. そのActor BlueprintのConstruction Script内で、Add Component系ノードによるコンポーネント生成処理を追加または変更します。

- 今回は独自コンポーネントをConstruction Scriptで生成するBlueprintが対象です。

4. 変更を保存し、ソース管理へsubmitします。

5. 再度、差分cook有効のままパッケージ作成を実行します。

6. cook終了付近で"Content is missing from cook"が発生し、パッケージ作成が失敗します。

[Attachment Removed]

お世話になっております。

再現手順のご提供をありがとうございました。

ご推察の通り、ビルドマシンにサブミットしたBPクラス側がConstruction Script由来のコンポーネント構成の変更があるなか、それを参照する _Generated_ セル側が変更を自動検知できず、古い名前の参照へのアクセスを試みてコンテンツを見失っているという状況と思われます。

頂戴しました5つの確認事項について、以下の通り回答申し上げます。

> Q1. 差分cook × CS の Add Component 変更で stale reference が残るのは既知の制限か?

はい、差分クックの依存追跡が持つ既知の制限のひとつに該当します。差分クックはまだ Beta 段階で、目標はフルクックと同等の結果をもたらすこととしながらも、依存変化の検出にはまだ取りこぼしがあるというのが現実です。

> Q2. _Generated_ パッケージは、参照先 BP の CS 構成が変われば自動的に無効化・再生成される想定か?

はい、設計上は自動的に再生成される想定です。実際、単一の最新ワークスペースで再現ステップを踏んだ場合は、その BP を参照する _Generated_ セルは依存追跡により正しく再クックされました。

問題が起きるのは、変更を submit した後に別環境(ビルドマシン等)で差分クックを行うケースです。このとき、ビルドマシン側が保持している差分クック状態によっては、本来再クックされるべき _Generated_ セルが誤って「変更なし」と判定されてスキップされ、古い参照が残ることがあります。つまり「自動再生成される想定だが、CI構成下で無効化トリガが立たない場合がある」という状態です。

> Q3. 差分cookを継続しつつ問題を避ける推奨運用は?

本来はエンジン側ですみやかに修正を図るのが第一ではありますが、現時点では、以下の運用方法が考えられます。

・ CSを変更した BP を submit した回は、その BP が配置されたマップを強制再クックする仕組みを作る

・ もしくは、CI側でエラーを検出し、該当マップを強制再クックする形でリトライする

・ あるいは、差分クック世代を一括無効化する

3つ目の「一括無効化」は、エンジンソース内の差分クックのバージョン識別子を変更することで行えます。具体的には、 Engine/Source/Editor/UnrealEd/Private/Cooker/CookIncrementalVersion.cpp に定義されている以下の GUID を、任意の別の値に書き換えていただくというものです。

// Change CookIncrementalVersion to a new guid when all packages in an incremental cook need to be invalidated
FGuid CookIncrementalVersion( 0x9F3A7C12, 0x4B8E2F90, 0xC1D47A6B, 0x6E9B0FD3 );

この識別子はクック全体のグローバルなハッシュに含まれており、値を変更すると、次回のクック時にそれまでの差分クック成果物がすべて無効化(削除)され、一度だけフルクック相当の再クックが走る仕組みになっています。弊社でも、強制フルクックをかけざるをえない際に、利用している手法となります。

> Q4. Saved/Cooked 全削除以外に、影響パッケージだけ無効化する手段は?

エラーログに出ている Source package(/<Map>/_Generated_/…)の親マップを対象に、-cooksinglepackagenorefs -package=<Map> で強制再クックすることが考えられます。

(例)
<YourProject> -run=cook -targetplatform=<ターゲット> -cookincremental -forcerecook -cooksinglepackagenorefs -package=<対象マップの LongPackageName>

> Q5. レベル配置の Actor BP では CS の Add Component を避けた方がよいか?

大変申し上げにくいのですが、現に差分クックの運用で問題が生じておりますので、CI側で自動強制再クックなどの仕組みが作れない限り、Construction Script から Add Component でコンポーネントを追加することは避けていただくのが現実的かもしれません。

問題点を解決する回答になっておらず、誠に申し訳ございません。

取り急ぎ一旦ご返信申し上げます。

以上、よろしくお願いいたします。

[Attachment Removed]

こちらこそお世話になっております。

ご丁寧なご返答ありがとうございます。大変助かります。

一旦弊社内で「CSを変更した BP を submit した回は、その BP が配置されたマップを強制再クックする」こちらの仕組みを作る事を目標に

問題への対処を行ってみます。

また、問題がありましたら再度スレッドを建てさせて頂きますので

本スレッドはクローズして頂いて大丈夫です。

以上、ありがとうございました。

[Attachment Removed]

お世話になっております。

ご確認ありがとうございました。

それではお言葉に甘えまして、案件管理上、本件は一旦Closeとさせていただきます。

なにかありましたら、再度スレッドの作成(もしくは本スレッドへのコメント追記による再Open)をお願いいたします。

当方からも何か新しい情報があれば再Openしてお知らせいたします。

以上、よろしくお願いいたします。

[Attachment Removed]