我正在尝试使用Kestrel在DNX上为ASP.NET vNext运行HelloWeb sample的修改版本。我知道这是在最前沿,但我希望ASP.NET团队至少保持最简单的Web应用程序工作:)
环境:
Startup.cs
中的“Web应用程序”代码:
using Microsoft.AspNet.Builder;
public class Startup
{
public void Configure(IApplicationBuilder app)
{
app.UseWelcomePage();
}
}
项目配置,在project.json
:
{
"dependencies": {
"Kestrel": "1.0.0-beta4",
"Microsoft.AspNet.Diagnostics": "1.0.0-beta4",
"Microsoft.AspNet.Hosting": "1.0.0-beta4",
"Microsoft.AspNet.Server.WebListener": "1.0.0-beta4",
"Microsoft.AspNet.StaticFiles": "1.0.0-beta4",
"Microsoft.Framework.Runtime": "1.0.0-beta4",
"Microsoft.Framework.Runtime.Common": "1.0.0-beta4",
"Microsoft.Framework.Runtime.Loader": "1.0.0-beta4",
"Microsoft.Framework.Runtime.Interfaces": "1.0.0-beta4",
},
"commands": {
"kestrel": "Microsoft.AspNet.Hosting --server Kestrel --server.urls http://localhost:5004"
},
"frameworks": {
"dnx451": {}
}
}
kpm restore
似乎工作正常。
然而,当我试图跑步时,我得到一个例外,表明找不到Microsoft.Framework.Runtime.IApplicationEnvironment
。命令行和错误(有些重新格式化)
.../HelloWeb$ dnx . kestrel
System.IO.FileNotFoundException: Could not load file or assembly
'Microsoft.Framework.Runtime.IApplicationEnvironment,
Version=0.0.0.0, Culture=neutral, PublicKeyToken=null'
or one of its dependencies.
File name: 'Microsoft.Framework.Runtime.IApplicationEnvironment,
Version=0.0.0.0, Culture=neutral, PublicKeyToken=null'
at (wrapper managed-to-native) System.Reflection.MonoMethod:InternalInvoke
(System.Reflection.MonoMethod,object,object[],System.Exception&)
at System.Reflection.MonoMethod.Invoke
(System.Object obj, BindingFlags invokeAttr, System.Reflection.Binder binder,
System.Object[] parameters, System.Globalization.CultureInfo culture)
[0x00000] in <filename unknown>:0
显然,我最迫切的需要是解决这个问题,我也很欣赏有关如何确定问题的建议,以便我将来能够自行解决类似的问题。 (这也可能使这个问题对其他人更有用。)
我在Microsoft.Framework.Runtime.IApplicationEnvironment
找到了Microsoft.Framework.Runtime.Interfaces
assembly source,而且最近似乎没有改变。目前尚不清楚为什么异常将名称显示为整个程序集本身,而不仅仅是另一个程序集中的接口。
我猜这可能是由于assembly neutral interfaces,但从错误中不清楚。
([AssemblyNeutral]
is dead, so that's not it...)
好问题。对于您的特定问题,您似乎在已解决的依赖项中存在不匹配。当这样的事情发生时,可能是因为你在不兼容的dnx上运行你的应用程序。我们仍在进行非常大的突破性更改,所以如果你看到缺少类型丢失的方法,你很可能最终运行betaX
包和betaY
dnx,反之亦然。
更具体地说,Assembly Neutral Interfaces在beta4中删除了,但看起来你正在运行的应用程序仍在使用它们。
我们计划将其设置为使包可以标记运行所需的最小dnx,以使错误消息更加清晰。随着时间的推移,破裂的变化将会消失。
总的来说,我觉得是时候编写一本关于如何在使用dnx时诊断这样的问题的指南(因为它与现有的.NET非常不同)。
您放入project.json
的依赖关系仅限顶级。版本也总是最小的(它就像一个NuGet包)。这意味着当你指定Foo 1.0.0-beta4
时,你真的指定了Foo >= 1.0.0-beta4
。这意味着如果您要求MVC 0.0.1
并且您配置的Feed上的最低版本是MVC 3.0.0
,那么您将获得该版本。除非您指定,否则我们也永远不会浮动您的版本。如果你要求1.0.0并且它存在,即使存在更新的版本,你也会获得1.0.0。指定空版本总是很糟糕,在以后的版本中将不允许这样做。
我们正在向nuget推出一个名为浮动版本的新功能。今天它只适用于预发布标签,但在下一个版本中,它将适用于该版本的更多部分。这类似于npm和gem语法,用于在包规范文件中指定版本范围。
1.0.0-*
- 手段给我匹配前缀的最高版本(根据semantic versioning rules)或者如果没有匹配该前缀的版本,使用正常行为并获得最低版本> =指定版本。
在最新版本中运行还原时,它将写出一个名为project.lock.json
的文件。该文件将具有project.json
中定义的所有目标框架的依赖关系的传递闭包。
当这样的事情失败时,您可以执行以下操作:
使用kpm list
查看已解析的依赖项。这将显示项目引用的软件包的已解析版本以及将其引入的依赖项。如果A - > B,它会显示:
A -> B B ->
实际KPM列表输出:
列出ClassLibrary39的依赖项(C:\ Users \ davifowl \ Documents \ Visual Studio 14 \ Projects \ ClassLibrary39 \ src \ ClassLibrary39 \ project.json)
[Target framework DNX,Version=v4.5.1 (dnx451)]
framework/Microsoft.CSharp 4.0.0.0
-> ClassLibrary39 1.0.0
framework/mscorlib 4.0.0.0
-> ClassLibrary39 1.0.0
framework/System 4.0.0.0
-> ClassLibrary39 1.0.0
framework/System.Core 4.0.0.0
-> ClassLibrary39 1.0.0
*Newtonsoft.Json 6.0.1
-> ClassLibrary39 1.0.0
[Target framework DNXCore,Version=v5.0 (dnxcore50)]
*Newtonsoft.Json 6.0.1
-> ClassLibrary39 1.0.0
System.Runtime 4.0.20-beta-22709
-> ClassLibrary39 1.0.0
*表示直接依赖。
如果你有一个工作的visual studio(现在它与DNX打破),你可以查看references节点。它具有相同的视觉数据:
让我们看一下依赖失败的样子:
这是project.json
{
"version": "1.0.0-*",
"dependencies": {
"Newtonsoft.Json": "8.0.0"
},
"frameworks" : {
"dnx451" : {
"dependencies": {
}
},
"dnxcore50" : {
"dependencies": {
"System.Runtime": "4.0.20-beta-22709"
}
}
}
}
Newtonsoft.Json 8.0.0
不存在。所以运行kpm restore会显示以下内容:
在诊断恢复可能失败的时候,查看发出的HTTP请求,它们会告诉您kpm查找的配置包源。请注意,在上图中,有一个CACHE
请求。这是基于资源类型(nupkg或nuspec)的内置缓存,并具有可配置的TTL(查看kpm restore --help
)。如果要强制kpm
命中远程NuGet源,请使用--no-cache
标志:
这些错误也会在包管理器日志输出窗口中显示在Visual Studio中:
边注!
我将描述NuGet.config现在的工作方式(将来可能会改变)。默认情况下,您有一个NuGet.config,其中包含在%appdata%\NuGet\NuGet.Config
中全局配置的默认NuGet.org源。您可以在visual studio中或使用NuGet命令行工具管理这些全局源。在尝试诊断故障时,您应该始终查看有效源(kpm输出中列出的源)。
阅读更多关于NuGet.config here的信息
回到现实:
当依赖关系未解析时,运行应用程序将为您提供:
> dnx . run
System.InvalidOperationException: Failed to resolve the following dependencies for target framework 'DNX,Version=v4.5.1':
Newtonsoft.Json 8.0.0
Searched Locations:
C:\Users\davifowl\Documents\Visual Studio 14\Projects\ClassLibrary39\src\{name}\project.json
C:\Users\davifowl\Documents\Visual Studio 14\Projects\ClassLibrary39\test\{name}\project.json
C:\Users\davifowl\.dnx\packages\{name}\{version}\{name}.nuspec
C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\{name}.dll
C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\Facades\{name}.dll
C:\WINDOWS\Microsoft.NET\assembly\GAC_32\{name}\{version}\{name}.dll
C:\WINDOWS\Microsoft.NET\assembly\GAC_64\{name}\{version}\{name}.dll
C:\WINDOWS\Microsoft.NET\assembly\GAC_MSIL\{name}\{version}\{name}.dll
Try running 'kpm restore'.
at Microsoft.Framework.Runtime.DefaultHost.GetEntryPoint(String applicationName)
at Microsoft.Framework.ApplicationHost.Program.ExecuteMain(DefaultHost host, String applicationName, String[] args)
at Microsoft.Framework.ApplicationHost.Program.Main(String[] args)
运行时基本上尝试在尝试运行之前验证整个依赖关系图是否已解析。如果它建议运行kpm restore
它是因为它找不到列出的依赖项。
你可能会遇到这个错误的另一个原因是你运行了错误的dnx风格。如果您的应用程序仅指定dnx451并且您尝试运行CoreCLR dnx,则可能会看到类似的问题。密切注意错误消息中的目标框架:
用于运行:
dnx4x - runs on dnx-clr-{etc}
dnxcore50 - runs on dnx-coreclr-{etc}
当你试图跑步时,你应该记住从你的project.json
中定义的clr到目标框架的心理映射。
这也显示在引用节点下的Visual Studio中:
标记为黄色的节点未解析。
这些也显示在错误列表中:
构建时也会出现这些错误。从命令行构建时,输出非常详细,在诊断问题时非常有用:
> kpm build
Building ClassLibrary39 for DNX,Version=v4.5.1
Using Project dependency ClassLibrary39 1.0.0
Source: C:\Users\davifowl\Documents\Visual Studio 14\Projects\ClassLibrary39\src\ClassLibrary39\project.json
Using Assembly dependency framework/mscorlib 4.0.0.0
Source: C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\mscorlib.dll
Using Assembly dependency framework/System 4.0.0.0
Source: C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\System.dll
Using Assembly dependency framework/System.Core 4.0.0.0
Source: C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\System.Core.dll
Using Assembly dependency framework/Microsoft.CSharp 4.0.0.0
Source: C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\Microsoft.CSharp.dll
Building ClassLibrary39 for DNXCore,Version=v5.0
Using Project dependency ClassLibrary39 1.0.0
Source: C:\Users\davifowl\Documents\Visual Studio 14\Projects\ClassLibrary39\src\ClassLibrary39\project.json
Using Package dependency System.Console 4.0.0-beta-22709
Source: C:\Users\davifowl\.dnx\packages\System.Console\4.0.0-beta-22709
File: lib\contract\System.Console.dll
Using Package dependency System.IO 4.0.10-beta-22231
Source: C:\Users\davifowl\.dnx\packages\System.IO\4.0.10-beta-22231
File: lib\contract\System.IO.dll
Using Package dependency System.Runtime 4.0.20-beta-22231
Source: C:\Users\davifowl\.dnx\packages\System.Runtime\4.0.20-beta-22231
File: lib\contract\System.Runtime.dll
Using Package dependency System.Text.Encoding 4.0.10-beta-22231
Source: C:\Users\davifowl\.dnx\packages\System.Text.Encoding\4.0.10-beta-22231
File: lib\contract\System.Text.Encoding.dll
Using Package dependency System.Threading.Tasks 4.0.10-beta-22231
Source: C:\Users\davifowl\.dnx\packages\System.Threading.Tasks\4.0.10-beta-22231
File: lib\contract\System.Threading.Tasks.dll
输出显示从包和项目引用传递到编译器的所有程序集。当您开始获取构建失败时,查看此处以确保您使用的包实际上在该目标平台上工作是有用的。
这是一个在dnxcore50上不起作用的包的示例:
{
"version": "1.0.0-*",
"dependencies": {
"Microsoft.Owin.Host.SystemWeb": "3.0.0"
},
"frameworks": {
"dnx451": {
"dependencies": {
}
},
"dnxcore50": {
"dependencies": {
"System.Console": "4.0.0-beta-22709"
}
}
}
}
Microsoft.Owin.Host.SystemWeb版本3.0.0没有任何在dnxcore50上运行的程序集(请查看解压缩程序包的lib文件夹)。当我们运行kpm build
时:
注意它说“使用Package Microsoft.Owin.Host.SystemWeb”,但没有“File:”。这可能是构建失败的原因。
这结束了我的大脑转储
我仍然不完全知道出了什么问题,但我现在有一系列步骤,至少可以让它更容易尝试:
~/.config/NuGet.config
以确保您使用正确的NuGet源我最终使用以下命令行以一种相当干净的方式测试各种选项:
rm -rf ~/.dnx/packages && rm -rf ~/.dnx/runtimes && dnvm upgrade && kpm restore && dnx . kestrel
看起来我的问题确实是由于安装的依赖项版本错误。 "1.0.0-beta4"
的版本号显然与"1.0.0-beta4-*"
完全不同。例如,Kestrel
依赖安装版本1.0.0-beta4-11185,当时指定为1.0.0-beta4
,但版本1.0.0-beta4-11262,最后是-*
。我想明确指定beta4
以避免意外地使用beta3版本
以下项目配置工作正常:
{
"dependencies": {
"Kestrel": "1.0.0-beta4-*",
"Microsoft.AspNet.Diagnostics": "1.0.0-beta4-*",
"Microsoft.AspNet.Hosting": "1.0.0-beta4-*",
"Microsoft.AspNet.Server.WebListener": "1.0.0-beta4-*",
},
"commands": {
"kestrel": "Microsoft.AspNet.Hosting --server Kestrel --server.urls http://localhost:5004"
},
"frameworks": {
"dnx451": {}
}
}
您可以将名为DNX_TRACE
的env var设置为1
,以查看更多TON诊断信息。请注意,这是更多信息!
为了让它工作,我修改了我的project.json
..它现在看起来像:
{
"dependencies": {
"Kestrel": "1.0.0-*",
"Microsoft.AspNet.Diagnostics": "1.0.0-*",
"Microsoft.AspNet.Hosting": "1.0.0-*",
"Microsoft.AspNet.Server.WebListener": "1.0.0-*",
"Microsoft.AspNet.StaticFiles": "1.0.0-*"
},
"commands": {
"web": "Microsoft.AspNet.Hosting --server Microsoft.AspNet.Server.WebListener --server.urls http://localhost:5001",
"kestrel": "Microsoft.AspNet.Hosting --server Kestrel --server.urls http://localhost:5004"
},
"frameworks": {
}
}
关键似乎是框架部分。
重命名改变了k web
如何工作,以便它现在dnx . web
或dnx . kestrel
更新 - 更多信息
奇怪的是,在没有定义框架的情况下运行后,当我执行kpm restore
时,它得到了一堆额外的东西:
...
Installing Microsoft.Framework.Logging 1.0.0-beta4-11001
Installing Microsoft.Framework.Logging.Interfaces 1.0.0-beta4-11001
Installing Microsoft.Framework.DependencyInjection.Interfaces 1.0.0-beta4-11010
Installing Microsoft.Framework.DependencyInjection 1.0.0-beta4-11010
Installing Microsoft.Framework.ConfigurationModel 1.0.0-beta4-10976
Installing Microsoft.Framework.ConfigurationModel.Interfaces 1.0.0-beta4-10976
Installing Microsoft.AspNet.Hosting.Interfaces 1.0.0-beta4-11328
Installing Microsoft.AspNet.FeatureModel 1.0.0-beta4-11104
Installing Microsoft.AspNet.Http 1.0.0-beta4-11104
Installing Microsoft.AspNet.FileProviders.Interfaces 1.0.0-beta4-11006
Installing Microsoft.Framework.Caching.Interfaces 1.0.0-beta4-10981
Installing Microsoft.AspNet.FileProviders 1.0.0-beta4-11006
Installing Microsoft.AspNet.Http.Core 1.0.0-beta4-11104
Installing Microsoft.AspNet.WebUtilities 1.0.0-beta4-11104
Installing Microsoft.Net.Http.Headers 1.0.0-beta4-11104
Installing Microsoft.AspNet.Http.Interfaces 1.0.0-beta4-11104
Installing Microsoft.Framework.Runtime.Interfaces 1.0.0-beta4-11257
Installing Microsoft.AspNet.Server.Kestrel 1.0.0-beta4-11262
Installing Microsoft.Net.Http.Server 1.0.0-beta4-11698
Installing Microsoft.Net.WebSockets 1.0.0-beta4-11698
Installing Microsoft.Net.WebSocketAbstractions 1.0.0-beta4-10915
Installing Microsoft.Framework.WebEncoders 1.0.0-beta4-11104
Installing Microsoft.Framework.OptionsModel 1.0.0-beta4-10984
Installing Microsoft.AspNet.Http.Extensions 1.0.0-beta4-11104
Installing Microsoft.AspNet.Diagnostics.Interfaces 1.0.0-beta4-12451
Installing Microsoft.AspNet.RequestContainer 1.0.0-beta4-11328
..然后它运行良好。然后我切换回框架部分
"frameworks": {
"dnx451": {}
}
..它仍然有效,而在此之前它会引发错误!
很奇怪!
(我正在运行1.0.0-beta4-11257
)
进一步更新
我创建了一个新的Ubuntu实例,并得到了与你相同的错误。我的想法是这个问题可能是因为它只是试图从nuget.org
而不是myget.org
(它有更新的东西)获取包所以我放弃了NuGet.Config
成为项目的根源..
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<packageSources>
<add key="AspNetVNext" value="https://www.myget.org/F/aspnetvnext/" />
<add key="NuGet" value="https://nuget.org/api/v2/" />
</packageSources>
</configuration>
..这似乎已经通过获得正确的版本(在另一个kpm restore
之后)为我修复了它。
这些天,我所有的package.json
版本都以"-rc2-*"
结尾
(到目前为止我只看到的例外是Microsoft.Framework.Configuration
包,需要是"1.0.0-rc1-*"
或"1.0.0-*"
)
关于@davidfowl提到的“版本列车”,似乎很多痛苦在beta8和rc2之间消失了。
dnvm upgrade -u -arch x64 -r coreclr
我在coreclr
上用这两个NuGet提供了最多的运气:
"https://www.myget.org/F/aspnetvnext/"
"https://nuget.org/api/v2/"
当我确实缺少包裹问题时,90%的时间是这些相同的罪魁祸首:
Newtonsoft.Json
Ix-Async
Remotion.Linq
大多数时候,我可以通过强制主NuGet.org提要解决这些问题:
dnu restore;
dnu restore -s https://nuget.org/api/v2
这是我的工作config.json:
{
"dependencies": {
"Microsoft.AspNet.Diagnostics": "1.0.0-rc2-*",
"Microsoft.AspNet.Diagnostics.Entity": "7.0.0-rc2-*",
"Microsoft.AspNet.Hosting": "1.0.0-rc2-*",
"Microsoft.AspNet.Http": "1.0.0-rc2-*",
"Microsoft.AspNet.Http.Abstractions": "1.0.0-rc2-*",
"Microsoft.AspNet.Mvc.Core": "6.0.0-rc2-*",
"Microsoft.AspNet.Mvc.Razor": "6.0.0-rc2-*",
"Microsoft.AspNet.Owin": "1.0.0-rc2-*",
"Microsoft.AspNet.Routing": "1.0.0-rc2-*",
"Microsoft.AspNet.Server.Kestrel": "1.0.0-rc2-*",
"Microsoft.AspNet.Server.WebListener": "1.0.0-rc2-*",
"Microsoft.AspNet.Session": "1.0.0-rc2-*",
"Microsoft.AspNet.StaticFiles": "1.0.0-rc2-*",
"EntityFramework.Commands": "7.0.0-rc2-*",
"EntityFramework.Core": "7.0.0-rc2-*",
"EntityFramework.InMemory": "7.0.0-rc2-*",
"EntityFramework.MicrosoftSqlServer": "7.0.0-rc2-*",
"EntityFramework.MicrosoftSqlServer.Design": "7.0.0-rc2-*",
"EntityFramework.Relational": "7.0.0-rc2-*",
"EntityFramework7.Npgsql": "3.1.0-beta8-2",
"Microsoft.Extensions.Logging.Abstractions": "1.0.0-rc2-*",
"Microsoft.Extensions.Logging.Console": "1.0.0-rc2-*",
"Microsoft.Extensions.DependencyInjection": "1.0.0-rc2-*",
"Microsoft.Extensions.DependencyInjection.Abstractions": "1.0.0-rc2-*",
"Microsoft.Framework.Configuration.CommandLine": "1.0.0-*",
"Microsoft.Framework.Configuration.EnvironmentVariables": "1.0.0-*",
"Microsoft.Framework.Configuration.Json": "1.0.0-*"
},
"commands": {
"ef": "EntityFramework.Commands",
"dev": "Microsoft.AspNet.Hosting --ASPNET_ENV Development --server Microsoft.AspNet.Server.Kestrel --server.urls http://localhost:5004"
},
"frameworks": {
"dnxcore50": {}
}
}
尝试安抚dnxcore50和dnx451引用时,我依赖性缺失问题。
如果我理解这个正确的“依赖关系”:{}在框架之间共享。
然后“框架”中的“依赖关系”:{}特定于该框架。
dnxcore50是一个模块化运行时(自包含),因此它基本上包含运行程序所需的所有核心运行时,而不像经典的.net框架,其中核心依赖项分散在其他地方。
所以说,我想坚持最小的方法,因为我决定在某些时候主持mac或linux。
使用cshtml视图更新到奇怪的依赖性问题,现在只使用dnx451。
这是我的project.json
{
"webroot": "wwwroot",
"version": "1.0.0-*",
"dependencies": {
"System.Runtime": "4.0.10",
"Microsoft.AspNet.Hosting": "1.0.0-beta4",
"Microsoft.AspNet.Mvc": "6.0.0-beta4",
"Microsoft.AspNet.Server.IIS": "1.0.0-beta6-12075",
"Microsoft.AspNet.Server.WebListener": "1.0.0-beta6-12457",
"Microsoft.Framework.DependencyInjection": "1.0.0-beta4",
"Microsoft.Framework.DependencyInjection.Interfaces": "1.0.0-beta5"
},
"commands": {
"web": "Microsoft.AspNet.Hosting --server Microsoft.AspNet.Server.WebListener --server.urls http://admin.heartlegacylocal.com" },
"frameworks": {
"dnx451": { }
}
},
"publishExclude": [
"node_modules",
"bower_components",
"**.xproj",
"**.user",
"**.vspscc"
],
"exclude": [
"wwwroot",
"node_modules",
"bower_components"
]
}