LoginSignup
16
13

NuGetForUnityを使うときの注意点メモ

Last updated at Posted at 2024-03-21

はじめに

UnityでNugetパッケージを管理するツールとしてNuGetForUnityがあります。こちらを使ってパッケージ管理する際の注意点をメモしておきます。

メモ

どう使うのか

基本、READMEを読みましょう。

導入について

導入方法として「OpenUPM」「UPM経由(Git指定)」「unitypackage」の3つが紹介されていますが、 UPM経由(Git指定) が2024年3月時点ではオススメです。というのも、2024年3月時点での最新版である「v4.0.2」にはtargetFrameworkの指定機能がまだ入っていません。そのためtargetFramework指定を行いたいのであれば最新版の状態を引いてくる必要があります。
Git指定でのインストールなら(stableではないが)最新版を引っ張ってこれます。

この方法でEditor拡張はtargetFramework指定が使えますが、NuGetForUnity.Cli側が未対応だったので意味がなかったです。
v4.0.2より新しいバージョンが公開されるのを待ちましょう。

NuGetForUnityを使っている場合のバージョン管理方法

NuGetForUnityを使っているUnityプロジェクトをGit管理する場合は「Assets/Packages」(設定で他のディレクトリをパッケージ保存先にしている場合はそこを)をgitignoreに指定することを推奨します。

直接Nugetパッケージのdllを管理するのではなく、代わりに次の4ファイルをGit管理下にいれて都度restoreするのがよいでしょう。

  • Assets/NuGet.config
  • Assets/NuGet.config.meta
  • Assets/packages.config
  • Assets/packages.config.meta

パッケージの復元(Restore)方法

NuGetForUnityを使っているUnityプロジェクトをgit cloneしたりgit pullしたときに、Assets/Packagesの状態がpackages.configで指定した状態に一致しない場合があります。この場合は復元(Restore)をしましょう。

UnityEditorが正常に立ち上がり、コンパイルエラーが出ていない場合

UnityEditorが正常に立ち上がり、コンパイルエラーなども出ていない場合はNuGetForUnityのエディタ拡張メニューから復元ができます。

image.png

CI時やコンパイルエラーが出てしまう場合

JenkinsなどでBatchModeでUnityを使っている場合はエディタ拡張から復元することができません。

またプロジェクト中で利用しているdllが欠けている場合、コンパイルエラーが出てしまいNuGetForUnityのエディタ拡張メニューが消えてしまいます(これを解消するために復元がしたいのにそれができないという状態になる)

こういった場合のために、コマンドラインから復元ができるCLIツールが用意されています。

NuGetForUnity.Cliをグローバルに導入する場合

# 導入
dotnet tool install --global NuGetForUnity.Cli

# Unityプロジェクトのディレクトリを指定して復元
nugetforunity restore <PROJECT_PATH>

NuGetForUnity.Cliをローカルに導入する場合

cd  <PROJECT_PATH>
dotnet new tool-manifest
dotnet tool install NuGetForUnity.Cli
# パス指定を省略するとカレントディレクトリ指定になる
dotnet nugetforunity restore

うまくパッケージが導入できないとき

回避策は2つあります。

  1. targetFrameworkを指定する(後述)
  2. 該当のdllのみ手動で導入する(NugetパッケージをDLしてzip解凍し、中のdllを手動でプロジェクトに配置する)

targetFrameworkを指定する

※この機能はNuGetForUnity v4.0.2ではまだ使えません。またNuGetForUnity.Cli 1.0.0もこの機能にはまだ未対応です。

一部のパッケージはtargetFrameworkを指定しないと正しく導入できない場合があります。
とくにUnityの場合は.NET Framework 4.x.NET Standard 2.1の2つを併合したAPIセットになっているため、これらが混在したNugetパッケージを導入しようとした場合に正しく導入できなかったり、問題を引き起こす場合があります。

こうした事態を回避したい場合はAssets/packages.configからtargetFrameworkを指定しましょう。

<?xml version="1.0" encoding="utf-8"?>
<packages>
  <package id="Microsoft.Bcl.AsyncInterfaces" version="6.0.0" targetFramework=".netstandard2.1"/>
  <package id="Microsoft.Bcl.TimeProvider" version="8.0.0" targetFramework=".netstandard2.0"/>
  <package id="R3" version="1.1.11" manuallyInstalled="true" />
  <package id="System.ComponentModel.Annotations" version="5.0.0" />
  <package id="System.Runtime.CompilerServices.Unsafe" version="6.0.0" />
  <package id="System.Threading.Channels" version="8.0.0" />
</packages>
# これ
<package id="Microsoft.Bcl.AsyncInterfaces" version="6.0.0" targetFramework=".netstandard2.1"/>
<package id="Microsoft.Bcl.TimeProvider" version="8.0.0" targetFramework=".netstandard2.0"/>

※ただしこの方法で導入できたからといって、Unity上で正しく動作する保障はありません。場合によっては他のパッケージと干渉してしまう可能性もあります。

mscorlibとの干渉を避ける

Microsoft.Bcl.AsyncInterfacesを導入した状態でIAsyncDisposableなどを触ろうとするとエラーが出てしまう可能性があります。

image.png

これはUnity側が提供するランタイム側にIAsyncDisposableが既に定義されてしまっているためです。その状況でMicrosoft.Bcl.AsyncInterfacesを導入したため発生します。

回避策としては「Microsoft.Bcl.AsyncInterfacesを導入する場合は.NET Standard 2.1向けのdllを使う」です。.NET Standard 2.1向けdllはこのあたりの干渉がしないように調整されています。

特にUnityのAPI Compatibility Levelが「.NET Framework」を指定している場合はこの問題を踏む可能性があります。

API Compatibility Levelが「.NET Framework」設定の場合、NuGetForUnityはnet462版のdllを優先して解決しようとします。そのため干渉する.NET Framework 4.6.2版のMicrosoft.Bcl.AsyncInterfacesを引っ張ってきてしまい、干渉を引き起こします。

なのでNuGetForUnityを使う場合はAPI Compatibility Levelは「.NET Standard」にしておいたほうがよいかもしれないです。

16
13
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
16
13