必须用 sdk 风格项目、显式声明 packageid 和 version、以 release 模式执行 dotnet pack,否则生成 unnamed.1.0.0.nupkg 或被 nuget.org 拒绝;nuget.exe push 须配 v3 源和正确权限的 api key。

能直接用 dotnet pack 打包并 nuget.exe push 发布,前提是项目是 SDK 风格、PackageId 和 Version 已显式声明、且构建配置为 Release ——漏掉任一环节,包名会变成 Unnamed.1.0.0.nupkg,上传直接被 nuget.org 拒绝。
用 dotnet new classlib 创建干净的 SDK 风格类库
VS 界面新建类库容易误选“.NET Framework Class Library”模板,导致 dotnet pack 报错或生成空包。命令行方式从源头规避:
- 终端执行
dotnet new classlib -n MyUtils -f net8.0(加-f显式指定框架,避免默认用最新版造成兼容问题) - 生成的
.csproj自带<sdk>Microsoft.NET.Sdk</sdk>,无需手动改OutputType或补TargetFramework - 若后续发现
bin/Release下没有.dll,先运行dotnet build -c Release -v minimal看输出路径——SDK 风格项目 DLL 一定在bin/Release/net8.0/MyUtils.dll这类子目录下,不是根目录
dotnet pack --configuration Release 必须加 --configuration Release
不加参数默认走 Debug,会导致两个严重后果:
- 生成的
.nupkg文件名含-dev后缀(如MyUtils.1.0.0-dev.nupkg),nuget.org拒绝预发布版本上传 - 包内可能包含调试符号(
.pdb)、未优化代码,体积大且不符合生产包规范 - 验证是否真打包成功:检查
bin/Release下是否有.nupkg文件,并用nuget list MyUtils -Source https://api.nuget.org/v3/index.json确认本地没同名缓存干扰
PackageId 和 Version 必须写在 .csproj 的 <propertygroup></propertygroup> 里
这两个字段不填,dotnet pack 不报错但生成无效包:
-
<packageid>my-utils</packageid>:必须全小写、用短横线分隔,不能有空格或下划线;大小写敏感,MyUtils和my-utils是不同包 -
<version>1.0.0</version>:别用1.0.0-ci、1.0.0-alpha直接推官方源;若需测试,先推到私有源或用--skip-duplicate跳过冲突 - 漏掉
<authors></authors>或<description></description>不影响上传,但包页空白,别人搜到也不知用途——建议一并补上
nuget.exe push 上传时权限和版本冲突最常踩坑
API Key 不是万能钥匙,细节错一个就卡住:
- Key 权限必须选
Push new packages,不是All packages;Glob pattern 填*才能推任意包名 - 报
403 Forbidden:包名已被他人注册,你不是所有者;报409 Conflict:同名同版本已存在,必须升版(如1.0.1)再推 - 命令要带完整路径或确保
nuget.exe在PATH中:nuget.exe push my-utils.1.0.0.nupkg -Source https://api.nuget.org/v3/index.json -ApiKey ABC123... - 上传后等 1–5 分钟,再用浏览器访问
https://www.nuget.org/packages/my-utils/确认页面可打开——别信 CLI 的 “push successful”,它只表示请求发出去了
真正麻烦的不是打包命令本身,而是元数据写在哪、版本号谁管、包名怎么和命名空间对齐——这些信息分散在 .csproj、Directory.Build.props、nuget.org 账户设置三处,改一处漏一处,包就废一半。










