You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

托管ASP.NET Web API中如何通过System.IO.File使用相对路径?

错误原因解析

1. 相对路径读取失败原因

本地运行时工作目录为项目根目录,你写的相对路径可以匹配到对应文件,但Azure App Service部署后,应用运行的根目录为C:\home\site\wwwroot,部署后的目录结构和本地项目结构不一致,硬写的相对路径无法匹配到正确位置。

2. 嵌入式资源读取失败原因

GetManifestResourceStream的入参不是文件路径,而是遵循{程序集默认命名空间}.{文件夹层级}.{文件名}规则的资源标识符,你传入路径格式的字符串自然找不到对应资源,返回null导致报错。

解决方案

方案一:直接读取部署目录文件(推荐,可在线修改文件无需重发布)

  • 第一步:右键点击项目里的loyalty-template.html文件,选择「属性」,将复制到输出目录设置为如果较新则复制,确保发布时文件会被同步到Azure部署目录。
  • 第二步:使用ASP.NET Core内置的IWebHostEnvironment获取根目录,动态拼接文件路径,示例代码如下:
private readonly IWebHostEnvironment _webHostEnvironment;

// 构造函数注入环境变量
public YourController(IWebHostEnvironment webHostEnvironment)
{
    _webHostEnvironment = webHostEnvironment;
}

// 业务逻辑中读取文件
public void YourEndpointLogic()
{
    var filePath = Path.Combine(_webHostEnvironment.ContentRootPath, "Assets", "loyalty-template.html");
    string body = File.ReadAllText(filePath);
}

方案二:嵌入式资源读取

  • 第一步:右键点击项目里的loyalty-template.html文件,选择「属性」,将生成操作设置为嵌入式资源。
  • 第二步:获取正确的资源标识符,可在本地调试时先运行如下代码打印所有嵌入资源名,找到对应文件的准确名称:
var allResourceNames = Assembly.GetExecutingAssembly().GetManifestResourceNames();
// 断点查看allResourceNames数组,匹配到loyalty-template.html对应的资源名
  • 第三步:修改读取代码,补充空判断避免报错:
// 替换为你实际拿到的资源名,示例:默认命名空间为TheFoodWorksWebAPI时的写法
var resourceName = "TheFoodWorksWebAPI.Assets.loyalty-template.html";
string body;
using (var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName))
{
    if (stream == null)
    {
        throw new FileNotFoundException("嵌入资源未找到", resourceName);
    }
    using var reader = new StreamReader(stream);
    body = reader.ReadToEnd();
}
方案选型建议
  • 如果模板文件需要频繁修改,选择方案一,修改后直接覆盖Azure上的对应文件即可生效,无需重新编译发布。
  • 如果模板文件改动少,想要避免部署时漏传文件的问题,选择方案二,文件会被打包到程序集内,不会出现找不到文件的情况。

内容的提问来源于stack exchange,提问作者SeventhWarhawk

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 17:36:00