DeploymentItem属性の問題


94

私は現在、C#.netで記述された「古い」システムを維持しており、古い機能をいくつか削除して、リファクタリングを行っています。ありがとう、前の男はいくつかの単体テスト(MSTests)を書いた。私はJUnitテストにはかなり慣れていますが、MSTestにはまだあまり対応していません。

テストメソッドにはDeploymentItem属性があり、テストされているビジネスロジックメソッドによって解析されるテキストファイルと、DeploymentItem展開する必要がある一連のTIFファイルを含むパスのみが指定されている2番目のテキストファイルを指定します。

[TestMethod()]
[DeploymentItem(@"files\valid\valid_entries.txt")]
[DeploymentItem(@"files\tif\")]
public void ExistsTifTest()
{
   ...
}

テストは以前は機能していましたが、今は\ files \ tifディレクトリに含まれるTIFファイルの名前を変更する必要がありました。ルールによると、TIFファイル名は特定のパターンと一致する必要があり、これもExistsTifTest()メソッドによってチェックされます。新しい要件に合わせるためにファイル名を変更する必要がありましたが、突然、TIFファイルは以前のように展開されなくなりました。

誰かがこれがなぜ起こるのか、何が原因であるのかについてのヒントを教えてくれますか?テストファイルのDeploymentItem属性に応じて、\ files \ valid \ディレクトリの "valid_entries.txt"の横に "my2ndTest.txt"と言う新しいテキストファイルを追加しても、同じことが起こります。ファイルが展開されませんか?

testrunco​​nfigで展開パスを直接定義してイメージを展開しましたが、なぜこれらのことが発生するのか、またはたとえば、新しいファイル "my2ndTest.txt"が他のインスタンスで展開されないのはなぜですか?


2
ここで重要なのは、DeploymentItemAttributeで指定されたすべての項目が、テストアセンブリの実行元の場所にコピーされることを理解することです。つまり、ディレクトリ構造が維持されることを望んでいた場合、運が悪かったことになります。特定のディレクトリにコピーする必要がある場合は、2つのパラメーターDeploymentItem(source、outputDir)versionを使用します。参考までに-System.Console.WriteLine(System.Environment.CurrentDirectory)をテストの1つにドロップすることで、MsTestでファイルが実行されている場所を見つけるために古い学校に行くことができます。NCrunchにはこの問題はありませんでした!
CodeMonkeyKing 2013年

回答:


111

DeploymentItem 少し混乱しています。

ソリューションの各ファイルには、VS.NETの「出力フォルダーにコピー」設定があります。ファイルを出力フォルダーに入れるには、これを「常にコピー」(または同様の)にする必要があります。

新しいファイル用にこのセットがあることを確認してください。この設定がない場合、ファイルは出力フォルダーにコピーされず、出力フォルダーからMSTestが実行するフォルダーに展開できません。

個人的に、ユニットテストに必要なファイルがある場合、それらのファイルをリソースとしてアセンブリに埋め込み、テスト中にそのアセンブリを「アンパック」する方が、より予測可能な方法であることがわかりました。YMMV。

注:これらのコメントは、VS2010での私の経験に基づいています。私の回答へのコメントは、これがVS2012に問題がないことを示唆しています。埋め込みリソースを使用すると「魔法」が少なくなるため、ユニットテストの「配置」段階がより明確になるというコメントを今でも待機しています。


3
[出力ディレクトリにコピー]は、MSTestがファイルを展開する方法に影響を与えることはありません。この答えは間違っています。
kzu

19
VS2010 Premiumでは、この変更(およびその他の変更なし)を行うと、ファイルが展開されました。したがって、MsTestの展開に影響を与えるという実際の証拠に基づいて結論付けます。
JonStonecash

1
同意した。この1回の変更でDeploymentItemが逆さまになります。
マーティンペック

2
これは、VS2012では不要になったようです。配置アイテムが[出力フォルダーにコピー]を[コピーしない]に設定して配置されています。
Mike、

29
提供した単一のファイルをコピーできない場合にDeploymentItemが通知を表示しないのは素晴らしいことです。

74

VS2010では、Local.testsettingsの[Enable Deployment]がオフになっており、DeploymentItem属性が機能していませんでした。私はそれをチェックし、すべてがうまくいきました。これが役に立てば幸いです!


2
私はそれを機能させるために何年もの間、レンガの壁に頭をぶつけてきました...ありがとうございます!
mat-mcloughlin

12
この設定がオフになっている場合、フレームワークがDeploymentItem属性が無視されるという警告を発行したとしたら良かったと思います。また、デスクに凹面の印象を与えました。
アランマクビー-MSFT

2
Local.testsettingsがソリューションアイテムにあることに注意してください
Matthew Lock

また、Local.testsettingsに展開したいアイテムを含むディレクトリも追加する必要がありました。i.imgur.com/ p1z3m9R.png
Matthew Lock

2018年にVS2017を使用して「展開を有効にする」をチェックすることは、この問題の解決策です。残念ながら、今でもVisual Studioから警告が出ています。このソリューションに感謝します。
Don H

19

私も同様の問題に直面しましたが、これのための簡単な3ステップの解決策を見つけました:

フォルダ構造が次のようになっていると想定します。 SolutionFolder\ TestProjectFolder\ SubFolder\

  1. [ソリューションアイテム/Local.testsettings]> [展開]> [展開を有効にする]を選択します
  2. VS2010を使用している場合は、展開するファイルの「出力フォルダーにコピー」プロパティが「常にコピー」または「新しい場合はコピー」に設定されていることを確認してください。
  3. TestMethodを次のいずれかで属性付けします。
    • [DeploymentItem(@"TestProjectFolder\SubFolder")]のすべてのコンテンツを<SubFolder>Test Runディレクトリにデプロイするには
    • [DeploymentItem(@"TestProjectFolder\SubFolder", "TargetFolder")] のすべてのコンテンツをTest Runディレクトリにデプロイ<SubFolder>する<TargetFolder>には

MSTestに関する最後の注意事項(少なくともVS2010の場合):

あなたがしたい場合<TargetFolder>と同じ名前を持っている<SubFolder>使用して、[DeploymentItem(@"SubFolder", @"SubFolder")]MSTestをランナーは愚かなエッジケースに当たるとして黙って失敗します。このため<SubFolder>、の前に次の<TestProjectFolder>ようにプレフィックスを付ける必要があります。[DeploymentItem(@"TestProjectFolder\SubFolder", @"SubFolder")]


SubFolderの命名エラーに関するメモは、gemです。
RJローハン

1
VS 2015は少し違うようです。DeploymentItem Attributeの "TestPojectFolder"部分を削除する必要がありました。
uli78

15

うまくいけば他の人を助けてくれた:私はここですべての提案を試みましたが、それでも私の展開アイテムはコピーされていませんでした。

ここで提案したように、私がしなければならなかったのは、2番目のパラメーターをDeploymentItem属性に追加することでした。

[DeploymentItem(@"UnitTestData\TestData.xml", "UnitTestData")]

10

.testrunco​​nfigファイルに移動し、展開で[展開を有効にする]をオフにすると、テストは通常​​の場所で実行され、ユニットテストの外部でアプリを実行する場合と同様にすべてが機能します。


これにもいくつかの問題がありました。PMとして、開発者が使用するすべてのツールにアクセスできるわけではありません。この場合、MSTestがファイルをコピーできなかったときに、ReSharperがファイルを正しくコピーしました。->開発に問題がないときにエラーが発生しました。問題のファイルを含む「テスト->テスト設定の編集->ローカル設定->デプロイメント」に変更すると、MSTestで使用できるようにこの問題が修正されました。
sonstabo

9

これはおそらく正確な問題とは関係ありませんが、[DeploymentItem]属性で見つけたいくつかのヒントを次に示します。

  1. [出力ディレクトリにコピー]は、[常にコピー]に設定する必要があります。

[TestInitialize]属性と一緒に使用すると機能しません

[TestInitialize]
[DeploymentItem("test.xlsx")]
public void Setup()
{

それはあなたの[TestMethod]にあるべきです、例えば

    [TestInitialize]
    public void Setup()
    {
        string spreadsheet = Path.GetFullPath("test.xlsx");
        Assert.IsTrue(File.Exists(spreadsheet));
        ...
    }

    [TestMethod]
    [DeploymentItem("test.xlsx")]
    public void ExcelQuestionParser_Reads_XmlElements()
    {
        ...
    }

1
これは、めちゃくちゃ迷惑な制限です。多くの場合、デプロイの時間は「初期化」でなければならないような気がします。すべてのテストで同じサポートアーティファクトを使用するとどうなりますか?何十ものテストメソッド間でデコレータをコピーして貼り付けることになっていると思いますか?ばかげた。
Ryanman

5

ここにリストされている他のすべての提案を試した後、私はまだ何が起こっているのか理解できませんでした。最後に、[テスト/テストの設定]メニューで設定ファイルが選択されていないことがわかりました。これは、展開が有効になっていないことを意味します。Test / Test Settings / Select Test Settings Fileメニュー項目をクリックし、Local.TestSettingsファイルを選択すると、すべてが機能しました。


4

これが質問に正確に答えるかどうかはわかりませんが、それはいくつかを助けるかもしれません。まず、展開を機能させるには[展開を有効にする]チェックボックスをオンにする必要があることがわかりました。第二に、ドキュメントはソースパスが「プロジェクトパスに対して相対的」であると言っています。実際には、ビルド出力フォルダーを参照しているようです。したがって、「TestFiles」というプロジェクトフォルダーがあり、その中にと呼ばれるファイルがある場合Testdata.xml、この方法で属性を使用しても機能しません。

[DeploymentItem(@"TestFiles\Testdata.xml")] 

Testdata.xmlファイルCopy Alwaysにマークを付けることができるので、ビルドはコピーを出力フォルダー(例:)の下に置きますDebug\TestFiles\TestData.xml。その後、デプロイメントメカニズムはTestFiles\Testdata.xml、ビルド出力に関連するそのパス()にあるファイルのコピーを見つけます。または、次のように属性を設定できます。

[DeploymentItem(@"..\\..\TestFiles\Testdata.xml")] 

展開メカニズムは元のファイルを見つけます。したがって、どちらでも機能しCopy Alwaysますが、プロジェクトでapp.configファイルを編集するときと同じ問題がときどき発生することに気づきました。コードを変更したり、強制的に再構築したりしないと、マークされたファイルのコピーがトリガーされません。ビルド時にコピーされます。


相対パスは私にとって問題であり、これはそれを修正しました。テストの実行方法に応じて、2セットのDeploymentItemステートメントを追加しました。
Ed Bayiates 2016年

3

最初に展開フラグを無効にしました。しかし、それを有効にした後でも、何らかの未知の理由により、ターゲットDLLでさえもコピーされませんでした。誤ってテスト実行ウィンドウを開いて以前のすべての実行を強制終了し、魔法のように次の実行で必要なすべてのDLLとファイルをテストフォルダーで見つけました...非常に混乱しています。


2

ファイルを展開する際に、上記のすべての提案を試してみると、大きな問題がありました。

次に、VS2010を閉じました。それを再起動し、ソリューションをロードして、すべてが機能しました。(!)

私はいくつかのチェックを行いました。local.TestSettingで「展開を有効にする」フラグを設定した後は、単に[テスト結果]ウィンドウからテストを再実行しないでください。以前のテスト実行をUIから削除する必要があります。たとえば、別のテストを実行するか、ソリューションを再度開きます。


2

使用しないでくださいDeploymentItem

正しくセットアップするのは非常に難しく、ReSharperテストランナーでも、Visual Studio 2017のMSTESTのネイティブランナーでも機能しませんでした。

代わりに、データファイルを右クリックし、プロパティを選択します。[ Copy to output directory:Always]を選択します

テストでこれを行います。ディレクトリは、テストプロジェクトに関連するファイルのディレクトリです。簡単です。

    [TestMethod()]
    public void ParseProductsTest()
    {
        // Arrange
        var file = @"Features\Products\Files\Workbook_2017.xlsx";
        var fileStream = File.Open(file, FileMode.Open);
        // etc.
    }

これは、自動ビルドおよびテストシステムでうまく機能するようです。


1

私は常にDeploymentItem属性が混乱していることを発見したので、ビルド後のスクリプトを使用してそのようなファイルのデプロイメントを行います。-コピーするファイルに[常にコピー]プロパティが設定されていることを確認してください。-テストプロジェクトのビルド後スクリプトを変更して、ファイルをビルドターゲットフォルダー(Bin \ Debug)から、テストが想定している場所にコピーします。


1

これをVS2010で試してください。すべてのは、TIFのためにあなたはDeployItemsを追加する必要はありませんので、
削除します

[DeploymentItem(@"files\valid\valid_entries.txt")]  
[DeploymentItem(@"files\tif\")]  

テスト構成を追加します。
-ソリューションエクスプローラーでソリューションノードを右クリック
-追加->新しい項目...-
左側の[テスト設定]ノードを選択し、右側の項目を選択
-追加をクリック

それを例えば TDD

>のTDD下を選択しTestMenuますEdit Testsettings

Deploymentをクリックします。それを有効にして、必要なファイルとディレクトリを追加します。ソリューションへの相対パスがあります。ファイルが配置されます。たとえば、元のファイルは次のとおりです。

D:\Users\Patrik\Documents\Visual Studio 2010\Projects\DCArrDate\WebMVCDCArrDate\Trunk\WebMVCDCArrDate\Authority.xml  

単体テストを実行すると、次の場所にコピーされます

D:\Users\Patrik\Documents\Visual Studio 2010\Projects\DCArrDate\WebMVCDCArrDate\Trunk\WebMVCDCArrDate.Tests\bin\Debug\TestResults\Patrik_HERKULES 2011-12-17 18_03_27\Authority.xml  

テストコードで私はそれを以下から呼び出します:

[TestMethod()]
public void Read_AuthorityFiles_And_ParseXML_To_Make_Dictonary()  
{  
  string authorityFile = "Authority.xml";  
  var Xmldoc = XDocument.Load(authorityFile);  

常にコピーを選択する必要はありません。ファイルをtestprojectに配置します。テストコードにハードコードされたパスを追加します。私にとって、このソリューションは最も効果的でした。私はDeploymentItemで試しましたが、常にコピーしましたが、私の好みではありませんでした。


1

DeploymentItemの混乱を避け、@ Martin Peckによって提案されたアプローチ(受け入れられた回答)を好む人のために、次のコードを使用して埋め込みリソースのコンテンツにアクセスできます。

public string GetEmbeddedResource(string fullyQulifiedResourceName)
{
    var assembly = Assembly.GetExecutingAssembly();
    // NOTE resourceName is of the format "Namespace.Class.File.extension";

    using (Stream stream = assembly.GetManifestResourceStream(fullyQulifiedResourceName))
    using (StreamReader reader = new StreamReader(stream))
    {
        string result = reader.ReadToEnd();
    }
}

詳細については、このSOスレッドを参照してください


1
ビルドサーバーで実行すると、Assembly.GetExecutingAssembly()で問題が発生しました。実際のテストアセンブリではなく、テストランナーが返されます。テストアセンブリ(たとえば、テストクラス)の固定型でアセンブリを反映してアセンブリを取得することで、これを解決しました。
アルノピーターズ

1

私にとって、根本的な原因はまったく別のものでした。私のテストによって実行されている本番用コードは、デプロイされている.xmlテストファイルの名前変更または削除、あるいはその両方でした。

したがって、テストを個別に実行するとテストは成功しますが、すべてを一緒に実行すると、2番目以降のテストは「ファイルが見つかりません」というエラーで失敗します(DeploymentItem属性が機能していないと当初は誤診断していました)。

私の解決策は、個々のテストメソッドが展開されたファイルのコピーを(この手法を使用し)作成し、テストされる製品コードで元のファイルの代わりにコピーされたファイルを使用することでした。


1

ローカルユニットテストの実行とteamcityユニットテストの再会でもそれを解決するために、展開項目の問題に多くの時間を費やしてきました。それは簡単ではない。

この問題をデバッグするための非常に優れたツールはProcessExplorerです。プロセスエクスプローラーを使用して、Visual Studioが展開項目を検索している場所を確認し、プロジェクトを修正できます。パスにdeploymentitemファイル名が含まれているすべてのファイル操作をフィルタリングするだけで、それが表示されます。


私はこれが非常に古い答えであることを知っていますが、ProcessExplorerの使用方法について詳しく説明できれば、それは役に立ちます。ファイル操作を表示する方法をまったく見ていません。フィルター操作をはるかに少なくしています...
David

1

チェックが必要なDeployment属性の他に、DeploymentItem属性について何か他のことを発見しました。

[TestMethod()]
[DeploymentItem("folder\subfolder\deploymentFile.txt")]
public void TestMethod1()
{
   ...
}

deploymentFile.txtは、testfile.csではなくソリューションファイルに対して相対的である必要があります。

ここに画像の説明を入力してください


私はようやく、DeploymentItemソースをテストプロジェクトに対して相対的にすることで、これを機能させました。だから私は私のソリューション、「Service.Tests」にプロジェクトを持っています。その下に、コピーしたいファイルを含む「FilesForTests」フォルダがあります。使用しました[DeploymentItem(@"FilesForTests\MyFile.txt", "FilesForTests")]。私が考える私たちは同じことを言っていますか?
David

1

私はVS2013でこれに取り組んできました。これを機能させるための私の発見:

  • [新しい場合/常にコピーする場合:必須]の場合、[出力ディレクトリにコピー]を[コピー]に設定する必要があります。
  • .TestSettingsの「Enable Deployment」:必須ではありません。.TestSettingsファイルなしでこれを機能させました。
  • 2番目のパラメーターとしてフォルダーを指定:オプション。出力フォルダーのレイアウトを形成し、なしで正常に動作します。
  • ファイル名のスペース:これは私に頭痛の種を引き起こしました-ファイルは決してコピーされませんでした。スペースを削除すると、これが修正されました。エスケープ文字をまだ調べていません。

私も難しい方法を学んだヒント:この属性を各個別のテストに追加することを忘れないでください。ファイルはtestrunの最初の属性テストでコピーされますが、テストの順序が変更され、非属性テストが最初にファイルを見つけようとしたときに欠落したままでした。


最後の答えであるあなたの答えに到達する前に、ここですべてを試しました。犯人:ファイル名のスペース!良い吹き出し。
joelmdev 2015年

1
Visual Studio 2019を使用。「新しい場合はコピー」で修正。「常にコピーする」は嫌いです。デバッグや増分ビルドなど、多くのシナリオでプロジェクトを強制的に再ビルドするためです。
ヘラルドグリニョーリ

同意した。新しい場合はコピーを含めるように回答を更新しました。
アルノピーターズ

0

私の大きな「問題」は、DeploymentItemがディレクトリを処理する方法でした。展開したいサブディレクトリを含むディレクトリパスとして、両方を使用した2パラメータバージョンを使用していました。私は最初はディレクトリのルートにあるものだけをコピーし、再帰的なフォルダー構造全体をコピーしないことに気づきませんでした!

私は基本的に[DeploymentItem(@ "Foo \"、@ "Foo \")]を持っていて、それが私のFoo \ Barを配備することを期待していました。具体的には、[DeploymentItem(@ "Foo \ Bar \"、@ "Foo \ Bar \")]に変更する必要がありましたが、今では魅力的に機能します。


0

私も同様の問題に直面しています。私は上記のすべてのステップを持っていますが、まだ運がありません。VS2010を使用しています。次に、$ Menu> Test> Select Active Test Setting> Trace and Test Impact が選択されていることがわかりました。トレースとテストの影響をローカルに変更した後、動作し始めました。このページには、テスト結果フォルダーへのファイルのコピーに関する非常にリソースの多い情報が含まれています。このエクスペリエンスも追加したいと思います。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.