답변:
알아야 할 가장 중요한 사항 중 하나는 "특정 버전"에 적용됩니다 속성이라는 것이다 컴파일 시간 과 하지 런타임에 있습니다.
프로젝트를 빌드 할 때 빌드 시스템이 사용해야하는 실제 어셈블리를 찾으려면 프로젝트의 어셈블리 참조를 확인해야합니다. "특정 버전"점검이 수행되면 ( "특정 버전"은 언제 점검됩니까? "섹션 참조) 조립 해결 프로세스의 결과에 영향을줍니다.
어셈블리 해결 프로세스가 잠재적 어셈블리를 찾는 순서는 다음과 같습니다.
<HintPath>
.csproj 파일 의 요소가 참조하는 어셈블리GAC에 여러 버전의 어셈블리가있는 경우 해결 프로세스는 먼저 가장 높은 버전의 어셈블리로 해결하려고 시도합니다. "특정 버전"점검이 수행되지 않은 경우에만 중요합니다.
Visual Studio는 .csproj 파일에있는 두 가지 정보를 기반으로 "특정 버전"검사를 수행할지 여부를 결정합니다.
<SpecificVersion>
요소의 유무 및 가치 (존재하는 경우)버전 정보가있는 일반적인 어셈블리 참조는 다음과 같습니다.
<Reference Include="Foo, Version=1.2.3.4, Culture=neutral, processorArchitecture=MSIL">
<SpecificVersion>True</SpecificVersion>
<HintPath>..\..\Bar\Foo.dll</HintPath>
</Reference>
버전 정보가 없는 어셈블리 참조 모양은 다음과 같습니다 .
<Reference Include="Foo">
[...]
다음 표는 "특정 버전"검사가 수행 된시기와 그렇지 않은 경우를 보여줍니다.
| Version information
| Present Not present
----------------------------+------------------------------
<SpecificVersion> |
- Present, has value True | Yes (1) Yes (check always fails) (2)
- Present, has value False | No (3) No (4)
- Not present | Yes (5) No (6)
여기서 놀라운 점은 <SpecificVersion>
버전 정보와 버전 정보가 모두 없으면 검사가 수행되지 않는다는 것입니다 (사례 6). 내가 이해하지 못하면 <SpecificVersion>
기본값 "True" 를 의미 하기 때문에 검사가 수행되고 항상 실패 할 것으로 예상했을 것입니다 (사례 2와 동일) . 이것은 테스트를 수행 한 Visual Studio 2010의 단점 일 수 있습니다.
Visual Studio UI에서 어셈블리 참조의 속성을 검사 할 때 (참조를 선택하고 F4를 누름) "Specific Version"속성에 표시되는 값은 Visual Studio가 "Specific Version"을 수행할지 여부를 알려줍니다. 검사. 6의 경우 <SpecificVersion>
요소가 .csproj 파일에 없지만 UI에 "True"가 표시 됩니다.
"로컬 복사"속성이 "참"으로 설정되어 있지만 "특정 버전"확인으로 인해 어셈블리 해결 프로세스가 실패하면 어셈블리가 복사되지 않습니다.
PublicKeyToken=
부품 이없는 경우 ). 또한 내 게시물 끝쪽으로 테이블을 확인 Version=
하면 .csproj의 어셈블리 이름에서 부품이 누락 된 경우에도 버전 확인이 발생할 수 있음을 알 수 있습니다 . 질문 2 : 어셈블리 이름을 비교에 사용한다고 가정합니다. 나는 그 정보에 대한 다른 출처를 모른다.
<SpecificVersion>
태그는 완전히 이전의 값이 있던, 생략 거짓을 .
참조를 추가하면 Visual Studio는 프로젝트 파일에 어셈블리의 [AssemblyVersion]을 기록합니다. 이건 중요하다. 예를 들어, 1 년 후 버그 수정을 작성한 경우 정확히 동일한 버전의 참조로 프로젝트를 다시 빌드해야합니다 . 참조 어셈블리가 변경되면 오류가 발생합니다.
그러나 항상 바람직한 것은 아닙니다. 일부 프로그래머는 어셈블리 버전을 자동으로 증가시켜 다시 빌드 할 때마다 새 버전을 생성 할 수 있습니다. 어셈블리의 공용 인터페이스는 변경되지 않았지만 일부는 Nuget을 사용하여 라이브러리를 확보하여 프로젝트를 구성하고 사용 가능한 새 릴리스가있을 때 라이브러리를 자동으로 업데이트하도록합니다. 컴파일 오류를 억제하기 위해 특정 버전 특성을 False로 설정하려고합니다.
결과를 이해하려면 매우 중요하므로 사고를 피하기 위해 프로그램의 전체 빌드를 재배치해야합니다. 런타임시 버전 불일치로 인해 프로그램이 충돌하고 <bindingRedirect>
위험한 .config 파일 에서만 억제 할 수 있습니다 .
[AssemblyVersion]
어셈블리에 강력한 이름이 서명되지 않은 경우 CLR이 고려하지 않는다고 생각 했습니다.