MSBuild nie kopiuje referencji (plików DLL), jeśli używasz zależności projektu w rozwiązaniu

Mam cztery projekty w moim rozwiązaniu Visual Studio (każdy celuje w. NET 3.5) - dla mojego problemu ważne są tylko te dwa:

  1. MyBaseProject
  2. MyWebProject1

Dodałem elmah.odniesienie dll do MyBaseProject w Visual studio 2008, klikając "Dodaj odniesienie..." → Zakładka "przeglądaj" → wybierając " elmah.dll".

Właściwości odniesienia Elmah są następujące:

  • aliasy-global
  • Copy local-true
  • Kultura-
  • Opis-Moduły rejestrujące błędy i manipulatory (ELMAH) dla ASP.NET
  • Typ Pliku-Montaż
  • Ścieżka - D:\webs\otherfolder\_myPath\__tools\elmah\Elmah.dll
  • Resolved-True
  • Runtime version-v2.0.50727
  • określona wersja-false
  • silny Name-false
  • Wersja-1.0.11211.0

W MyWebProject1 dodałem odnośnik do projektu MyBaseProject by: "Dodaj referencję..."→"Projekty" → wybór "MyBaseProject". Właściwości tego odniesienia są takie same, z wyjątkiem następujących członów:

  • Opis -
  • Ścieżka - D:\webs\CMS\MyBaseProject\bin\Debug\MyBaseProject.dll
  • Wersja-1.0.0.0

Jeśli uruchomię kompilację w Visual Studio elmah.plik dll jest kopiowany do katalogu mywebproject1 wraz z MyBaseProject.dll!

Jednak jeśli wyczyszczę i uruchomię MSBuild dla rozwiązania (poprzez D:\webs\CMS> C:\WINDOWS\Microsoft.NET\Framework\v3.5\MSBuild.exe /T: ReBuild / P: Configuration=Debug MyProject.sln) elmah.brak dll w katalogu bin MyWebProject1 - chociaż sama kompilacja nie zawiera ostrzeżeń ani błędów!

Już się upewniłem, żecsproj z MyBaseProject zawiera private element o wartości "true" (który powinien być aliasem dla" copy local " w Visual Studio):
<Reference Include="Elmah, Version=1.0.11211.0, Culture=neutral, processorArchitecture=MSIL">
  <SpecificVersion>False</SpecificVersion>
  <HintPath>..\mypath\__tools\elmah\Elmah.dll</HintPath>
    **<Private>true</Private>**
</Reference>

(tag prywatny nie pojawił się w .CSPROJ XML domyślnie, chociaż Visual Studio powiedział" copy local " prawda. Przełączyłem "copy local" NA false-saved - i ponownie ustawiłem na true - save!)

Co jest nie tak z MSBuild? Jak zdobyć (elmah.dll) odniesienie skopiowane do kosza MyWebProject1?

Nie chcę dodawać kopii postbuild działanie na polecenie postbuild każdego projektu! (Wyobraź sobie, że wiele projektów zależy od MyBaseProject!)

Author: Peter Mortensen, 2009-07-15

19 answers

Nie jestem pewien, dlaczego jest inaczej podczas budowania między Visual Studio i MsBuild, ale oto, co znalazłem, gdy napotkałem ten problem w MsBuild i Visual Studio.

Wyjaśnienie

Dla przykładowego scenariusza Załóżmy, że mamy project X, assembly A i assembly B. Assembly a odwołuje się do assembly B, więc project X zawiera odwołanie zarówno do A jak I B. również, project X zawiera kod odwołujący się do assembly a (np. A. SomeFunction ()). Teraz tworzysz nowy projekt Y które odwołują się do projektu X.

Więc łańcuch zależności wygląda tak: Y = > X => A = > B

Visual Studio / MSBuild stara się być inteligentny i przenosić tylko odwołania do projektu Y, które wykrywa jako wymagane przez Projekt X; robi to, aby uniknąć zanieczyszczenia odniesienia w projekcie Y. problem polega na tym, że projekt X nie zawiera żadnego kodu, który jawnie używa assembly B (np. nie kopiuje go do katalogu bin projektu Y; kopiuje tylko zespoły X i A.

Rozwiązanie

Masz dwie opcje rozwiązania tego problemu, z których obie spowodują skopiowanie zestawu B do katalogu bin projektu Y:

  1. Dodaj odniesienie do zespołu B w projekcie Y.
  2. Dodaj kod atrapy do pliku w projekcie X, który używa assembly B.

Osobiście wolę opcję 2 z kilku powodów.

  1. Jeśli dodasz kolejną projekt w przyszłości, który odwołuje się do projektu X, nie będziesz musiał pamiętać, aby również zawierać odniesienie do assembly B (tak jak w przypadku opcji 1).
  2. możesz mieć wyraźne komentarze mówiące, dlaczego atrapa kodu musi tam być, a nie go usuwać. Więc jeśli ktoś usunie Kod przez przypadek (powiedzmy za pomocą narzędzia refactor, które szuka nieużywanego kodu), możesz łatwo zobaczyć z kontroli źródła, że kod jest wymagany i przywrócić go. Jeśli używasz opcji 1 i ktoś używa narzędzie refactor aby wyczyścić nieużywane odniesienia, nie masz żadnych komentarzy; zobaczysz, że odniesienie zostało usunięte z.plik csproj.

Oto przykład "atrapy kodu", który zazwyczaj dodaję, gdy napotykam taką sytuację.

    // DO NOT DELETE THIS CODE UNLESS WE NO LONGER REQUIRE ASSEMBLY A!!!
    private void DummyFunctionToMakeSureReferencesGetCopiedProperly_DO_NOT_DELETE_THIS_CODE()
    {
        // Assembly A is used by this file, and that assembly depends on assembly B,
        // but this project does not have any code that explicitly references assembly B. Therefore, when another project references
        // this project, this project's assembly and the assembly A get copied to the project's bin directory, but not
        // assembly B. So in order to get the required assembly B copied over, we add some dummy code here (that never
        // gets called) that references assembly B; this will flag VS/MSBuild to copy the required assembly B over as well.
        var dummyType = typeof(B.SomeClass);
        Console.WriteLine(dummyType.FullName);
    }
 161
Author: deadlydog,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-01-19 16:37:09

Po prostu tak sobie z tym radzę. Przejdź do właściwości referencji i zrób to:

Set "Copy local = false"
Save
Set "Copy local = true"
Save
I to wszystko.

Visual Studio 2010 początkowo nie stawia: <private>True</private> w znaczniku odniesienia i ustawienie "copy local" NA false powoduje utworzenie znacznika. Następnie ustawi ją odpowiednio na true I false.

 171
Author: andrew,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-10-21 23:54:33

Jeśli nie używasz złożenia bezpośrednio w kodzie, Visual Studio, starając się być pomocnym, wykrywa, że nie jest on używany i nie zawiera go w wyjściu. Nie jestem pewien, dlaczego widzisz odmienne zachowanie między Visual Studio a MSBuild. Możesz spróbować ustawić wyjście kompilacji do diagnostyki dla obu i porównać wyniki zobaczyć, gdzie się rozchodzi.

Co do twojego elmah.jeśli nie odwołujesz się do niego bezpośrednio w kodzie, możesz dodać go jako element do swojego zaprojektuj i ustaw akcję Build na Content, a Skopiuj do katalogu wyjściowego na Always.
 38
Author: John Hunter,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-20 17:58:18

Spójrz na:

Ten wątek na forum MSBuild założyłem

Znajdziesz tam moje tymczasowe rozwiązanie / obejście!

(mybaseproject potrzebuje kodu, który odwołuje się do niektórych klas (cokolwiek) z elmah.dll dla elmah.dll jest kopiowany do kosza MyWebProject1!)

 15
Author: toebens,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-20 17:57:19

Miałem ten sam problem.

Sprawdź, czy wersja frameworkowa twojego projektu jest taka sama jak wersja frameworkowa biblioteki dll, którą umieściłeś w referencji.

W moim przypadku mój klient został skompilowany przy użyciu "Framework 4 Client", a DLL był w "Framework 4".

 8
Author: Andre Avelar,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-25 08:22:42

Problem, z którym miałem do czynienia, polegał na tym, że mam projekt, który jest zależny od projektu biblioteki. W celu zbudowania wykonywałem następujące kroki:

msbuild.exe myproject.vbproj /T:Rebuild
msbuild.exe myproject.vbproj /T:Package

To oczywiście oznaczało, że brakowało mi plików dll mojej biblioteki w bin, a co najważniejsze w pliku zip pakietu. Znalazłem to działa idealnie:

msbuild.exe myproject.vbproj /T:Rebuild;Package

Nie mam pojęcia, dlaczego to działa lub dlaczego nie w ogóle. Ale mam nadzieję, że to pomoże.

 6
Author: vangorra,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-07-18 22:49:52

Po prostu miałem dokładnie ten sam problem i okazało się, że jest to spowodowane faktem, że 2 projekty w tym samym rozwiązaniu odnosiły się do innej wersji biblioteki 3rd party.

Kiedy poprawiłem wszystkie referencje wszystko działało idealnie.

 5
Author: Steven Engels,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-02-12 15:24:53

Używając schematu deadlydog,

Y = > X = > A = > B ,

Mój problem polegał na tym, że gdy zbudowałem y, zespoły (A i B, wszystkie 15 z nich) z X nie pojawiały się w folderze bin Y.

Udało mi się to rozwiązać usuwając odniesienie X Z Y, Zapisz, zbuduj, a następnie ponownie dodaj odniesienie x (odniesienie do projektu), i zapisz, zbuduj, A A i B zaczęły pojawiać się w folderze bin y.

 4
Author: J Z,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-12-08 20:39:56

Jak Alex Burtsev wspomniał w komentarzu wszystko, co jest używane tylko w słowniku zasobów XAML, lub w moim przypadku, wszystko, co jest używane tylko w XAML, a nie w kodzie za, nie jest uważane za "w użyciu" przez MSBuild.

Więc po prostu nowe-dodanie atrapy odniesienia do klasy / komponentu w zestawie w jakimś kodzie za wystarczyło przekonać MSBuild, że zestaw był rzeczywiście w użyciu.

 4
Author: Scott,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-20 18:01:56

Zmiana docelowego frameworka z . NET Framework 4 Client Profile na . NET Framework 4 rozwiązała ten problem.

Więc w twoim przykładzie: Ustaw docelowy framework na MyWebProject1 na . NET Framework 4

 3
Author: Fuyu Persimmon,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-08-02 19:20:50

Miałem ten sam problem i dll był dynamicznie ładowanym referencją. Aby rozwiązać problem dodałem "korzystanie"z przestrzeni nazw dll. Teraz dll jest kopiowany w folderze wyjściowym.

 2
Author: Spamme,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-27 09:39:57

Wymaga to dodania pliku .targets do projektu i ustawienia go w sekcji zawiera projektu.

Zobacz moja odpowiedź tutaj {[5] } na temat procedury.

 2
Author: Alex Essilfie,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 11:54:44

Odwoływanie się do zestawów, które nie są używane podczas budowania, nie jest właściwą praktyką. Powinieneś powiększyć swój plik kompilacji, aby skopiował dodatkowe pliki. Używając zdarzenia post build lub aktualizując grupę właściwości.

Niektóre przykłady można znaleźć w innym poście

 2
Author: verbedr,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 12:10:36

Inny scenariusz, w którym pojawia się to, jeśli używasz starszego typu projektu" Web Site " w Visual Studio. Dla tego typu projektu nie można się odwołać .biblioteki DLL, które znajdują się poza własną strukturą katalogów (bieżący folder i dół). Więc w odpowiedzi powyżej, powiedzmy, że struktura katalogu wygląda tak:

Tutaj wpisz opis obrazka

Gdzie ProjectX i ProjectY są katalogami nadrzędnymi/podrzędnymi i referencjami ProjectX A.dll które z kolei odwołują się do B.dll, oraz B.dll na poza strukturą katalogów, np. w pakiecie Nuget w katalogu głównym (Packages), wtedy A.dll zostaną uwzględnione, ale B.dll nie zrobię tego.

 2
Author: Focker,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-03-20 18:19:29

Miałem podobny problem dzisiaj, i na pewno nie jest to odpowiedź na twoje pytanie. Ale chciałbym poinformować wszystkich, i być może zapewnić iskrę wglądu.

Mam ASP.NET podanie. Proces budowania jest ustawiony na clean, a następnie build.

Mam dwa Ci Skrypty. Jeden do produkcji i jeden do inscenizacji. Wdrożyłem moją aplikację do stagingu i wszystko działało dobrze. Wdrożony do produkcji i brakowało pliku DLL, który był / align = "left" / Ten plik DLL był tylko w katalogu głównym projektu. Nie w żadnym repozytorium NuGet. DLL został ustawiony na do not copy.

Skrypt CI i aplikacja były takie same między dwoma wdrożeniami. Jeszcze po wyczyszczeniu i wdrożeniu w środowisku przejściowym plik DLL został zastąpiony w lokalizacji wdrażania ASP.NET application (bin/). Tak nie było w przypadku środowiska produkcyjnego.

Okazuje się, że w gałęzi testowej dodałem krok do procesu budowania, aby skopiować nad tym plikiem DLL do katalogu bin. Teraz część, która zajęła trochę czasu, aby dowiedzieć się. Proces CI nie czyścił się sam. DLL został pozostawiony w katalogu roboczym i został przypadkowo spakowany z ASP.NET .plik zip. Gałąź produkcyjna nigdy nie miała skopiowanego pliku DLL w ten sam sposób i nigdy nie została przypadkowo wdrożona.

TLDR; Sprawdź i upewnij się, że wiesz, co robi twój serwer kompilacji.

 0
Author: Jason Portnoy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-20 18:06:05

Upewnij się, że oba projekty są w tej samej wersji. NET, sprawdź również właściwość copy local, ale domyślnie powinno to być true

 0
Author: john.kernel,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2019-02-08 08:08:51

Użycie Visual Studio 2015 dodanie dodatkowego parametru

/deployonbuild=false

Do wiersza poleceń msbuild Naprawiono problem.

 0
Author: Giles Roberts,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2019-11-27 16:40:22

Właśnie natknąłem się na bardzo podobny problem. Podczas kompilacji przy użyciu programu Visual Studio 2010 plik DLL znalazł się w folderze bin. Ale podczas kompilacji przy użyciu MSBuild plik DLL innej firmy nie został dołączony.

Bardzo frustrujące. Sposób, w jaki go rozwiązałem, polegał na dodaniu NuGet do pakietu w moim projekcie internetowym, mimo że nie używam go bezpośrednio tam.
 -1
Author: Gary Brunton,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-20 18:00:51

Włączenie do projektu wszystkich odwołanych plików DLL z projectreferences nie zawsze jest dobrym pomysłem, zwłaszcza gdy używasz dependency injection : Twój projekt internetowy chce tylko dodać odniesienie do pliku DLL interfejsu/projektu, a nie konkretnego pliku DLL implementacji.

Ponieważ jeśli dodasz odniesienie bezpośrednio do pliku/projektu DLL implementacji, nie możesz uniemożliwić programiście wywołania "nowego" na konkretnych klasach DLL implementacji plik / projekt zamiast poprzez interfejs. Jest to również podałeś "hardcode" w swojej witrynie, aby korzystać z implementacji.

 -3
Author: Hung Nguyen,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-20 18:03:31