これは私を数ヶ月間狂わせており、それを達成することはまだできません。私のマネージライブラリはNugetパッケージから抽出されますが、ネイティブライブラリからは抽出されません。
他の会社が提供する管理されたネイティブライブラリがたくさんあります。 _x86
_と_x64
_の両方のバージョンがあります。それらをASP.NET Coreプロジェクトで使用するには、Nugetパッケージを作成する必要があります。
私のアーキテクチャは:
もちろん、最後に、ネイティブライブラリをWebサイトの適切なランタイムフォルダーに抽出する必要があります(例:_\bin\Debug\net461\win7-x64
_)。
当面の私の解決策は:
build
フォルダ内に配置する$(OutputPath)
にコピーするtargets
ファイルを作成します(ランタイムフォルダーでもありません)。xproj
に追加して、$(USERPROFILE)\.nuget\packages\
フォルダー内のターゲットファイルを取得して実行しますbin
フォルダーに抽出してruntime
にコピーします_project.json
_の構成を使用して、それらをランタイムフォルダーに直接コピーしようとしました(正直に言って、この部分で試したすべてのことを覚えていません)。これは常に失敗していました。また、ターゲットファイルで_SkipUnchangedFiles="true"
_を指定した場合でも、これは無視され、ビルドごとにDLLがbinフォルダーにコピーされます。
これは、DLLの抽出を実現するだけの重いプロセスです。今、私はMsBuildをすべて取り除き、より単純なソリューションを取得したいと思っています。
Nugetの新しいバージョンでは、カスタムMsBuildコマンドを追加せずにネイティブに抽出できるようになりました。 ここに書かれているように 、C#プロジェクトはtargets
ファイルすら必要としません
次に、NuGetパッケージを使用する可能性のあるC++およびJavaScriptプロジェクトには、必要なアセンブリファイルとwinmdファイルを識別するための.targetsファイルが必要です。 (C#およびVisual Basicプロジェクトはこれを自動的に行います。)
私はブラウザーでタブを数か月間開いたままにして( 元のリンク )、このリソースが最近Nuget Webサイトから削除されたことに気付きました。 runtimes
フォルダーを使用してネイティブDLLを自動的に抽出する方法を説明していました。しかしそれが説明されたように私は成功した結果を得ることができたことはありません。このページは削除され、 this one に置き換えられました。説明が少なく、このruntimes
フォルダーについてはまったく触れていません。
私の推測では、ネイティブDLLにはruntimes
フォルダーを使用し、マネージDLLにはlib
フォルダーを使用する必要がありますが、100%確実ではありません。 (build
フォルダも使用する必要がありますか?)
私はいくつかのことを試しました(私は数か月の頭痛のように言ったように、試行回数を思い出せません...) thisアーキテクチャ (ここでは何がわからないのか) _build/native
_およびruntimes
)の下のネイティブフォルダーがあることのポイント
また、マネージライブラリの こちら に記載されている.NETフレームワークのバージョン構造を使用しようとしました。
これ も解決策の一部のようです
アセンブリ参照を作成するとき、アーキテクチャはコンパイラによって無視されます。これはロード時間の概念です。ローダーは、アーキテクチャ固有の参照が存在する場合、それを優先します。
AnyCPUアセンブリを生成するために使用できる1つのトリックは、x86アセンブリからアーキテクチャを削除するためにcorflagsを使用することです。 EG:corflags/32BITREQ- MySDK.dll。 Corflagsは.NET SDKの一部であり、VSの開発者コマンドプロンプトにあります。
それは私がやったことであり、x86とx64の両方のDLLをAnyCPU
に変換し(x64 DLLに対して何かを行うかどうかはわかりませんが、エラーは発生しませんでした)、次にNugetパッケージでいくつかの異なるアーキテクチャを試しましたが、機能していません。
Project.jsonにエントリがないデフォルトのランタイムは_win7-x64
_なので、念のため明示的に指定することにしました
_"runtimes": {
"win7-x64": {}
},
_
これが、Nugetパッケージでのすべての試行に使用しているランタイム識別子です。ただし、Windowsのバージョンは気にしません。私は実際にはwin-x86またはwin-x64を使用することを好みますが、 このページ によれば無効な値のようです
Windows RID
Windows 7/Windows Server 2008 R2
- win7-x64
- win7-x86
Windows 8/Windows Server 2012
- win8-x64
- win8-x86
- win8アーム
Windows 8.1/Windows Server 2012 R2
- win81-x64
- win81-x86
- win81アーム
Windows 10/Windows Server 2016
- win10-x64
- win10-x86
- win10-arm
- win10-arm64
ただし、これは Github source がより多くのRIDを記述しているため、どのソースが正しいですか?
ご覧のように、ここには非常に多くの謎があります。これは、主にドキュメントが不足しているか、異なるドキュメント間の矛盾が原因です。
少なくとも実用的な例があるとしたら、テストを実行して、一般的な_win-x64
_ RIDを試すなどの他の質問に答えるか、.NET Frameworkのバージョンに関係なく、マネージライブラリを1回含めることができるかどうかを確認します。
私の特別なコンテキストに注意してください:完全な.NET Frameworkを対象とするASP.NET Coreプロジェクトがあります
あなたの答えをありがとう、私はこの単純なことを機能させるために必死です。
私が経験したすべての苦痛と解決策をできるだけ詳しく説明しようと思います。私の例では、ネイティブDLLの代わりに、単純なテキストファイルAAA86.txt
、AAA64.txt
、AAAany.txt
を使用して、抽出プロセスを簡単に説明しています。
最初に知っておくべきこと:native
NuGetのアーキテクチャを、いくつかを含むlib
フォルダと混在させようとする場合管理ライブラリ、ITは機能しません
その場合、マネージDLLはプロジェクトの出力ディレクトリにコピーされますが、ネイティブDLLはコピーされません。
Grpc.Coreパッケージ を参照するようにアドバイスしてくれたJon Skeetに感謝します。コツは、DLL抽出を処理するtargets
ファイルを作成することです。
ターゲットファイルには次のようなものが含まれている必要があります
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.Microsoft.com/developer/msbuild/2003">
<ItemGroup Condition=" '$(Platform)' == 'x64' ">
<Content Include="$(MSBuildThisFileDirectory)..\..\runtimes\win-x64\native\AAA64.txt">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
<Link>AAA64.txt</Link>
</Content>
</ItemGroup>
<ItemGroup Condition=" '$(Platform)' == 'x86' OR '$(Platform)' == 'AnyCPU' ">
<Content Include="$(MSBuildThisFileDirectory)..\..\runtimes\win-x86\native\AAA86.txt">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
<Link>AAA86.txt</Link>
</Content>
</ItemGroup>
</Project>
ここで、知っておく必要がある他のいくつかの事項:
1)Visual Studioは気にしません選択すると、常にダミーのRIDが使用されます。 (私の場合、Windows 10を使用している場合でも、常にwin7-x64
フォルダが表示されます...)
2)project.json
の- プラットフォーム設定 もまったく役に立たない
{
"buildOptions": {
"platform": "x64"
}
}
3)ランタイム設定 でwin
またはwin-x64
のみを設定した場合
"runtimes": {
"win": {},
"win-x64": {}
}
Visual Studioは代わりにwin7-x64
を使用します。ただし、Windows 10マシンでwin10-x64
を追加すると、これが使用されます
4)このような一般的なRIDを使用してアプリケーションをコンパイルする場合
dotnet build -c debug -r win
次に、あなたのtargets
ファイルは、私が期待していたAnyCPU
ではなく、マシンのアーキテクチャ(私の場合はx64)を受け取ります。
5)マネージドライブラリのないネイティブライブラリのみで、アーキテクチャに従うと、ターゲットファイルなしで抽出が機能しますruntimes/RID/native
6)パッケージにネイティブライブラリのみが含まれている場合、選択したRIDは常にwin-x64
になります。選択した構成に関係なく、常にwin7-x64
が作成されます。パッケージにwin
RIDが1つしかない場合は、正常に選択されます。