有没有人有办法克服MSBuild工具的260个字符限制,从命令行构建Visual Studio项目和解决方案?我正在尝试使用CruiseControl自动构建构建(CruiseControl.NET不是一个选项,所以我试图将它绑定到正常的ant脚本中)并且我继续遇到路径长度的问题。为了澄清,问题在于解决方案文件中引用的项目的路径长度,因为该工具不会正确地折叠路径:(
我也尝试过使用DevEnv,它有时会工作,有时会抛出异常,这对于在单独的机器上进行自动构建是不利的。所以请不要建议将其作为替代品。
最重要的是,通过普通IDE使用Visual Studio时,项目构建正常。
答案 0 :(得分:8)
似乎是MSBuild的限制。我们遇到了同样的问题,最后,我们不得不缩短路径,因为没有找到任何其他正常工作的解决方案。
答案 1 :(得分:8)
似乎存在SUBST command个剧照,因此如果Judah Himango的解决方案不合适,将构建文件夹的根目录重新映射到驱动器号可能会节省一些字符。
答案 2 :(得分:5)
我通过调整CSPROJ文件解决了类似的问题:
<BaseIntermediateOutputPath>$([System.IO.Path]::GetFullPath('$(MSBuildProjectDirectory)\..\..\..\Intermediate\$(AssemblyName)_$(ProjectGuid)\'))</BaseIntermediateOutputPath>
编译过程中的结果CSC.EXE收到完整路径而不是相对路径。
感谢harrydev了解CSC.EXE如何使用路径进行操作。
答案 3 :(得分:2)
有两种与构建相关的长路径问题。一个是不太长的路径,但其中有很多“..”。通常,这些是引用的HintPath值。 MSBuild应将这些路径规范化为低于最大限制,以便它们可以正常工作。
另一种道路显然太长了。对不起,但这些都行不通。在仔细研究之后,问题是对长路径没有足够的API支持。 BCL团队(见他们的博客)也有类似的问题。只有部分Win32 API支持\?\格式。任意构建工具,可能有98%的应用程序没有;更糟糕的是可能表现得很糟糕(想想所有为MAX_PATH设计的缓冲区)。
我们得出的结论是,为了使长路径工作有一个很大的生态系统努力,或者Windows提出了一些巧妙的方法来使它们无论如何都能工作(比如短路径变形?)长路径是不可能的MSBuild支持。解决方法包括subst,正如您所发现的那样;但如果您的树只是太深,您唯一的选择是将它构建成片段,或者缩短文件夹名称。遗憾。
丹/ MSBuild的
答案 4 :(得分:1)
我发现问题是当调用C#编译器(csc.exe)时,它将项目目录路径PROJECTDIRECTORY与输出路径OUTPUTPATH一起使用,只需将它们附加为:
PROJECTDIRECTORY + OUTPUTPATH
但是,如果OUTPUTPATH是相对的,即“.. \ .. \ Build \ ProjectName \ AnyCPU_Debug_Bin \”且项目目录很长,那么总长度超过259个字符,因为路径将是:
PROJECTPATH + “.. \ .. \构建\项目名\ AnyCPU_Debug_Bin \”
而不是绝对路径。
如果csc.exe在调用Win32函数之前创建一个绝对路径,这将起作用。因为在我们的例子中,绝对路径长度小于160个字符。
出于某种原因,来自visual studio的csc.exe调用与MSBuild不同,而不是来自visual studio。不知道为什么。
在任何情况下,都可以通过更改PROJECTDIRECTORY和/或OUTPUTPATH路径之一来解决问题。
答案 5 :(得分:0)
您是否尝试过DOS路径?或者\\?\前缀? .NET BCL team blog有更多信息。
答案 6 :(得分:0)
如果路径长度为260,则存在警告解析参考,不会发生此错误的259或261。我认为有msbuild错误。
答案 7 :(得分:0)
我知道已经有一个已接受的答案,但是在使用msbuild
给我相同的错误输出时我遇到了一个不同的问题,并引导我进行循环的野鹅追逐。所以,对于未来的googlers,请点击:
我们有一个调用msbuild
的批处理文件,但由于构建计算机可以为多个版本的Visual Studio构建,因此每个批处理文件在运行vcvarsall.bat
之前调用msbuild
。这有一个令人讨厌的副作用,一遍又一遍地填充完全相同的路径。当它填满时,您会收到上述问题中显示的错误:The input line is too long.
简单的Google搜索可能会让您认为msbuild
的路径突然过长。
在我的情况下,它就像杀死cmd.exe
的会话并重新启动一样简单,因为这会将环境变量恢复为其本机状态。