콘텐츠 파일을 asp.net 프로젝트 파일에 자동으로 포함하는 방법이 있습니까?


88

ASP.NET 프로젝트에 많은 콘텐츠 파일 (주로 이미지 및 js)을 자주 추가하고 있습니다. VS 게시 시스템을 사용하고 있으며 게시시 새 파일을 프로젝트에 포함 할 때까지 게시되지 않습니다. 지정된 디렉토리의 모든 파일을 자동으로 포함하고 싶습니다. csproj 파일이나 다른 곳에 자동으로 포함되어야하는 디렉토리를 지정하는 방법이 있습니까?


참조 : 이것은 당신을 도울 수 있습니다 stackoverflow.com/questions/1743432/…
Saar

1
내가 찾고있는 것이 정확히 아닙니다
Marko

vs 솔루션 브라우저 내부의 폴더를 수정할 때 문제에 대한 내 답변을 업데이트했습니다.
Filburt 2010

답변:


135

이전 스레드, 알아요.하지만 계속 잊고있는이 작업을 수행하는 방법을 찾았습니다. 마지막으로 한 번 찾기 위해 검색 할 때이 질문을 발견했습니다. 내가 찾은 가장 좋은 방법은 .csproj 파일에서 BeforeBuild 대상을 사용하는 것입니다.

<Target Name="BeforeBuild">
    <ItemGroup>
        <Content Include="**\*.less" />
    </ItemGroup>
</Target>

VS 2010은이 섹션을 다루지 않으며 프로젝트가 빌드 될 때마다 파일이 콘텐츠로 포함되도록합니다.


.less의 의미는 무엇입니까? 그리고 전체 문자열은 무엇을 의미 **\*.less합니까?
등록 된 사용자

3
.less 파일은 Less CSS 전처리기에 의해 구문 분석되는 css 파일입니다. 이에 대한 자세한 정보는 Google "점수 줄이기"를 참조하십시오. 이 표현 **\*.less은 모든 디렉토리에 모든 * .less 파일을 포함한다는 의미입니다. MSBUILD에서 **는 '모든 디렉터리를 재귀 적으로'를 의미합니다.
Chris

4
적어도 VS 2012에서는 프로젝트에서 파일을 추가 / 제거하고 저장하자마자 불행히도 전체 목록으로 확장됩니다. :(
Chris Phillips

3
이것은 BeforeBuild를 AfterBuild로 변경 한 후에 만 ​​내 상황에 효과적이었습니다. 내 빌드는 파일을 이동하는 powershell 스크립트를 시작합니다. 그러면 빌드가 성공한 후에 만 ​​존재했기 때문에 Azure 웹 배포 시도에서 선택되지 않습니다. "BeforeBuild"를 보면 아마 "AterBuild"도있을 것입니다. 이것이 다른 사람에게 도움이되기를 바랍니다.
Luke Rice

1
@John은 VS2015 +에 대한 수정 사항에 대해 아래 내 대답을 참조하십시오 .
Jesse

55

웹 사이트 .csproj 파일을 확장하기 만하면됩니다. 재귀 와일드 카드를 사용하여 콘텐츠 루트 폴더를 추가하기 만하면됩니다.

...
<ItemGroup>
    <!-- your normal project content -->
    <Content Include="Default.aspx" />

    <!-- your static content you like to publish -->
    <Content Include="Images\**\*.*" />
</ItemGroup>
...

이렇게하면이 폴더와 아래의 모든 콘텐츠가 솔루션 브라우저에 표시됩니다.

다음을 지정하여 솔루션 브라우저 내에서 폴더를 숨기려고하면

<Content Include="Images\**.*.*">
    <Visible>false</Visible>
</Content>

게시되지 않습니다.


최신 정보

이미 발견했듯이 VS 프로젝트는 임의의 콘텐츠를 포함하도록 설계되지 않았기 때문에 솔루션 내의 폴더를 터치하자마자 와일드 카드가 대체됩니다.

따라서 폴더와 그 내용이 VS 내에서 수정되지 않도록해야합니다. 파일 추가 또는 제거는 파일 시스템에서만 수행 할 수 있습니다.

폴더를 VS에서 숨길 수 있으면 더 쉬울 수 있지만 숨기고 게시하는 방법을 찾을 수 없습니다.

실패한 또 다른 접근 방식은 CreateItem작업 별로 폴더를 포함하는 것이 었습니다 . 이로 인해 폴더의 내용이 \ bin \ app.publish \ ... 에 게시되었으며 .csproj 내의 내용 항목과 함께 게시하도록 설득 할 수 없었으므로 내 대답에 표시하지 않았습니다.


3
수동으로 파일을 추가하거나 제거 할 때까지 작동합니다. 그 줄 다음에 <Content Include = "Images * *. "/>가 프로젝트 파일에서 사라집니다.
Marko

2
@Marko가 정확합니다. 추가 후 <Content Include="Images\**\*.*" />작동했습니다. 이미지를 더 추가하면 .csproj가 변경되고 images / ...의 모든 파일 목록으로 돌아가고 <Content Include = "Images * *. "/>가 사라집니다.
Ravi Ram

이 코드를 별도의 .proj 파일에 넣고 .csproj 파일의 이전 빌드 대상에서 호출하십시오.
NL-Monica에게 사과합니다.

21

Chris의 답변을 사용하는 데 문제 가있는 경우 Visual Studio 2012 이상을위한 솔루션입니다.

<Target Name="ContentsBeforeBuild" AfterTargets="BeforeBuild">
  <ItemGroup>
    <Content Include="images\**" />
  </ItemGroup>
</Target>

크리스는 그의 대답에 언급 한 바와 같이 - 비주얼 스튜디오가 되지 않습니다 이 눌러 <Target>수동으로 대상 디렉토리로 (파일 추가 / 제거) 주변에 바이올린 경우에도, 절을 참조하십시오.

노트는 것을 바랍니다 해야 파일이있는 하위 디렉토리 포함 (위의 경우를, 그것입니다 images). Visual Studio / MSBuild는 이러한 파일을 프로젝트 구조 내의 동일한 디렉터리에 배치합니다. 하위 디렉토리를 사용하지 않는 경우 파일은 프로젝트 구조의 루트에 배치됩니다.

와일드 카드에 대한 간단한 설명은 다음과 같습니다.

  • **모든 것을 재귀 적으로 의미합니다 (파일, 하위 디렉터리 및 그 안의 파일).
  • *.extext최상위 디렉토리 내에 확장자가있는 모든 파일을 포함 하지만 하위 디렉토리 는 포함 하지 않습니다.
    • 예를 들어, *.ext*.png, *.js모든 파일 확장자가 작동합니다
  • **\*.extext최상위 디렉토리 및 모든 하위 디렉토리의 확장자 를 가진 모든 파일을 포함합니다 .
  • Nant / Ant 이름 지정 패턴을 사용하려면 어떻게해야합니까? 의 답변을 참조하십시오 . 예제와 함께 더 완전한 설명은.

완성을 위해 사용 <Target>과 사용하지 않는 것에 는 차이가 있습니다.

<Target>접근 방식을 사용하면 Visual Studio 솔루션 탐색기 내에 파일을 표시 하지 않습니다 .

<Target Name="ContentsBeforeBuild" AfterTargets="BeforeBuild">
  <ItemGroup>
    <Content Include="images\**" />
  </ItemGroup>
</Target>

<Target>접근 방식 Visual Studio에 솔루션 탐색기 내에 파일 을 표시 하도록 지시 합니다. 이 방법의 단점은 자동 디렉터리를 조작 하면 Visual Studio가 와일드 카드 항목을 재정의하게된다는 것입니다. 아래의 접근 방식 은 VS에서 솔루션 / 프로젝트를 열 때만 솔루션 탐색기를 업데이트합니다. 솔루션 탐색기의 "새로 고침"도구 모음 단추조차도이를 수행하지 않습니다.

<ItemGroup>
  <Content Include="images\**" />
</ItemGroup>

1
<Target> 사용과 사용하지 않는 것의 차이점을 실험하고 지적 해 주셔서 감사합니다. 와일드 카드의 세부 사항에 대한 훌륭한 설명도 있습니다.
Kurt Hutchinson

@KurtHutchinson-문제 없습니다. =)
Jesse

이 솔루션은 연마가 필요하다고 생각합니다. "BeforeBuild"이후에 target을 실행하도록 지시하면 이론적으로 게시 후에도 발생할 수 있습니다. 현재 솔루션은 아마도 운 때문에 작동 할 것입니다.
Imre Pühvel

@ ImrePühvel 게시 파악 어떻게 발생 하기 전에BeforeBuild 이벤트? MSBuild는 게시를 고려하기 전에 먼저 프로젝트와 바이너리를 빌드해야합니다.
Jesse

1
빌드 전에 게시가 발생한다고 주장하지는 않았지만 선언이 항목이 게시 전에 콘텐츠에 추가된다는 것을 보장하지는 않습니다. 코드 샘플에서 : .. AfterTargets="BeforeBuild". 의미, 사용자 지정 대상은 BeforeBuild 이후에 실행되어야하지만 이후에 얼마를 지정하지 않습니다. 하지만 내 실수로 현재 대상 주문 알고리즘에 따라 괜찮을 것입니다 : msdn.microsoft.com/en-us/library/ee216359.aspx
Imre Pühvel

10

프레임 워크의 System.IO.Directory.GetFile(string)메서드와 오버로드를 사용하여 모든 파일을 재귀 적으로 포함 할 수 있습니다.

  <ItemGroup>
    <Content Include="$([System.IO.Directory]::GetFiles('$(ProjectDir)Scripts\', '*.js', SearchOption.AllDirectories))" />
    <Content Include="$([System.IO.Directory]::GetFiles('$(ProjectDir)Images\', '*.png', SearchOption.AllDirectories))" />
  </ItemGroup>

이것은 저에게 큰 도움이되었습니다. 몇 단계 깊이의 여러 디렉토리와 자동 포함되기를 원하는 많은 파일이 있으며 이로 인해 모든 콘텐츠가 하나로 바뀌 었습니다. 감사!
Jay Otterbein

2
나는 이것을 좀 더 실험 해 보았고 이것은 Include="**\*.ext"와일드 카드와 동일한 제한이 있음이 밝혀졌습니다 .
Steven Liekens 2015 년

프로젝트 파일에 run powershell이 ​​포함되어 있습니까? 샌드 박스가 전혀 없나요? 그것은 일어나기를 기다리는 익스플로잇입니다.
Brain2000 19'19-09-23

PowerShell이 ​​아닙니다. MSBuild에는 정적 메서드를 호출하기위한 자체 구문이 있습니다. 문서에 따르면 이것은 시스템 클래스로 제한됩니다. docs.microsoft.com/en-us/visualstudio/msbuild/… 아무 인수와도 <Exec> powershell을 사용할 수 있다고 확신하지만 ...
Steven Liekens

3

작은 powershell 스크립트로 만든 콘텐츠 포함을 얻을 수있는 방법을 작성했습니다.

$folders = Get-ChildItem .\ -r -Directory
$filtered = $folders |Select-Object @{Name='FullName';Expression={$_.fullname.replace($pwd,'')}}, @{Name='FolderDepth';Expression={($_.fullname.Split('\').Count) - ($Pwd.Path.split('\').count)}} | Sort-Object -Descending FullName,folderDepth 
$basefolders = $filtered | Where-Object{$_.folderdepth -eq 1}
$basefoldersobj = @()
foreach($basefolder in $basefolders)
{
  $basefoldername =$baseFolder.fullname
  $filteredbase = $filtered -match "\$basefoldername\\" | Sort-Object -Descending FolderDepth | Select-Object -first 1
  if($filteredbase -eq $null)
  {
    $filteredbase = $filtered -match "\$basefoldername" | Sort-Object -Descending FolderDepth | Select-Object -first 1
  }
  $obj = New-Object psobject
  Add-Member -InputObject $obj -MemberType NoteProperty -Name 'Folder' -Value $basefolder.fullname.trim('\')
  Add-member -InputObject $obj -MemberType NoteProperty -Name 'DeepestPath' -Value $filteredbase.folderDepth
  $basefoldersobj += $obj
}
$include = '*.*'
foreach($bfolderObj in $basefoldersobj)
{
  $includecount = ''
  $includecount = "\$include" * ($bfolderObj.Deepestpath)
  Write-Output "<content Include=`"$($bfolderObj.folder)$includecount`" /> "
}

이것은 powershell 프롬프트에서 필요한 include 문을 생성해야합니다.


2

다음과 같은 링크가있는 파일을 추가 할 수 있습니다. 파일은 검색 가능하고 볼 수 있지만 변경하려고하면 체크 아웃하지 않으며 Visual Studio는 와일드 카드를 그대로 둡니다.

  <ItemGroup>
    <Content Include="..\Database Schema\Views\*.sql">
      <Link>Views\*.sql</Link>
    </Content>
  </ItemGroup>

이것은 .proj 파일에 들어갑니다.


1
나는 이것을 시도했고 VS는 VS를 사용하여 파일을 추가하거나 제거 할 때 와일드 카드를 개별 파일로 대체합니다.
carlin.scott

이것은 매우 우아하지만 링크 대상에서 와일드 카드를 제거해야합니다
SimSimY

1

내 지식이 아닙니다. 그러나 내 제안은 기본적으로 포함되므로 프로젝트에 붙여 넣는 것입니다. 따라서 탐색기를 통해 디렉터리에 붙여 넣는 대신 Visual Studio를 사용하여 파일을 폴더에 붙여 넣습니다.


-1

이에 대한 최선의 해결책은 파일을 하나씩 수동으로 추가하는 것임을 깨달았습니다. 내가 한 것처럼 수백 개가 있다면 몇 시간 만에 끝났습니다. VS 2015가있는 2016 년에도이 심각한 문제가 아직 해결되지 않았다는 사실이 재밌습니다. 아, 내가 Xcode를 얼마나 좋아하는지.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.