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

.NET Core 3.1迁移后调用Process.Start启动Word报目录名无效错误

错误原因

核心是从.NET Framework迁移到.NET Core 3.1后Process类的行为变更导致的:

  1. 当你显式将UseShellExecute = false时,.NET Core 3.x会强制校验ProcessStartInfo.WorkingDirectory属性对应的目录是否合法、当前进程是否有访问权限;而.NET Framework在相同场景下不会做这个校验,会自动使用目标exe所在目录作为工作目录兜底。这里报错的目录并不是你传入的Word exe所在目录,而是未显式赋值的WorkingDirectory默认继承的当前进程工作目录,所以你去检查Word路径会完全正常,和错误提示不符。
  2. 你的代码里没有给ProcessStartInfo.WorkingDirectory显式赋值,默认会继承当前.NET进程的工作目录。如果应用运行过程中工作目录被意外修改(比如弹出过系统文件选择对话框、操作过临时目录后目录被删除、应用从网络位置启动后网络临时中断、部分用户权限配置导致无法访问默认工作目录),就会触发目录名无效的报错,这就解释了错误偶发、不同用户出现频率不一致、重启应用/系统可能恢复的现象。
  3. 补充次要原因:部分场景下从注册表读取到的Office路径是8.3格式短路径(比如你示例里的C:\PROGRA~2\MICROS~1\Office14\WINWORD.EXE),.NET Core在UseShellExecute=false场景下对短路径的兼容性也弱于.NET Framework,偶尔会出现路径解析失败的问题。

解决方案

方案1:显式设置工作目录(最推荐,完全解决问题)

启动进程前,先从你拿到的Word exe路径中提取所在目录,赋值给ProcessStartInfo.WorkingDirectory即可,修改后的StartMsOfficeAppExe代码如下:

public void StartMsOfficeAppExe(
    string msOfficeAppExePath,
    string startArguments,
    bool hidden)
{
    // 提取exe所在目录作为工作目录
    var workingDir = Path.GetDirectoryName(msOfficeAppExePath);
    ProcessStartInfo startInfo = new ProcessStartInfo(
        msOfficeAppExePath,
        startArguments)
    {
        UseShellExecute = false,
        WorkingDirectory = workingDir, // 新增这行,显式指定工作目录
        WindowStyle = hidden ? ProcessWindowStyle.Hidden : ProcessWindowStyle.Normal
    };
    Process.Start(startInfo);
}

这个方案从根源上避免了当前进程工作目录被修改带来的影响,也兼容短路径、长路径两种格式的Word路径。

方案2:优化注册表路径读取逻辑,返回长路径

修改GetWordExePathFromWindowsRegistry方法,对读取到的短路径做一次转换,转成长路径再返回,避免路径解析异常:
首先声明Windows API用于短路径转长路径:

[DllImport("kernel32.dll", CharSet = CharSet.Auto)]
private static extern int GetLongPathName(string shortPath, StringBuilder longPath, int longPathLength);

public static string ConvertShortPathToLongPath(string shortPath)
{
    var builder = new StringBuilder(255);
    GetLongPathName(shortPath, builder, builder.Capacity);
    return builder.ToString();
}

然后在原方法匹配到路径后先转成长路径再返回:

if (!string.IsNullOrEmpty(fullWordPath))
    if (exePathRegex.IsMatch(fullWordPath))
        return ConvertShortPathToLongPath(fullWordPath);

临时排查方案

如果需要先定位用户侧的具体原因,可以在报错时额外打印当前进程的工作目录(Directory.GetCurrentDirectory()),确认是否是目录不存在、无权限的问题。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.29 21:06:01