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

.NET 8 React SPA开发启动超时异常排查求助

.NET 8 React SPA开发环境启动TimeoutException问题解决

问题概述

开发环境启动.NET 8 React SPA应用时,触发TimeoutException,错误提示create-react-app服务器未在超时时间内监听请求。已将启动超时延长至300秒仍报错,.NET 6环境下相同配置可正常运行;前端可通过URL直接访问页面,但ReactDevelopmentServerMiddleware仍触发超时。

环境配置

  • .NET 8.0.204
  • React TypeScript 18.2.0
  • Node 18.20.0
  • Visual Studio 17.9.6
  • 使用Microsoft.AspNetCore.SpaServices.Extensions配置SPA

相关配置代码

builder.Services.AddSpaStaticFiles(configuration =>
{
    configuration.RootPath = "WebClient/dist";
});
.....
app.UseSpa(spa =>
{
    spa.Options.SourcePath = "WebClient";
    // Only in local development use npm start. Not in test/production.
    if (environment.IsDevelopment())
    {
        spa.Options.StartupTimeout = TimeSpan.FromSeconds(300);
        spa.UseReactDevelopmentServer(npmScript: "dev");
    }
});

完整错误日志

info: Microsoft.AspNetCore.SpaServices[0]
      Starting create-react-app server on port 51062...
info: Microsoft.AspNetCore.SpaServices[0]
      > paymentwebclient@0.0.0 dev

info: Microsoft.AspNetCore.SpaServices[0]
      > vite

info: Microsoft.AspNetCore.SpaServices[0]
      Port 5173 is in use, trying another one...

info: Microsoft.AspNetCore.SpaServices[0]
        VITE v5.1.6  ready in 1359 ms

info: Microsoft.AspNetCore.SpaServices[0]
        Γ₧£  Local:   http://localhost:5174/

info: Microsoft.AspNetCore.SpaServices[0]
        Γ₧£  Network: use --host to expose

dbug: Microsoft.Extensions.Hosting.Internal.Host[1]
      Hosting starting
warn: Microsoft.AspNetCore.StaticFiles.StaticFileMiddleware[16]
      The WebRootPath was not found: ****\wwwroot. Static files may be unavailable.
info: Microsoft.Hosting.Lifetime[14]
      Now listening on: https://localhost:7252
info: Microsoft.Hosting.Lifetime[14]
      Now listening on: http://localhost:5293
info: Microsoft.Hosting.Lifetime[0]
      Application started. Press Ctrl+C to shut down.
info: Microsoft.Hosting.Lifetime[0]
      Hosting environment: Development
info: Microsoft.Hosting.Lifetime[0]
      Content root path: ***
dbug: Microsoft.Extensions.Hosting.Internal.Host[2]
      Hosting started
fail: Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware[1]
      An unhandled exception has occurred while executing the request.
      System.TimeoutException: The create-react-app server did not start listening for requests within the timeout period of 120 seconds. Check the log output for error information.
         at Microsoft.AspNetCore.SpaServices.Extensions.Util.TaskTimeoutExtensions.WithTimeout[T](Task`1 task, TimeSpan timeoutDelay, String message)
         at Microsoft.AspNetCore.SpaServices.ReactDevelopmentServer.ReactDevelopmentServerMiddleware.<>c__DisplayClass2_0.<<Attach>b__0>d.MoveNext()
      --- End of stack trace from previous location ---
         at Microsoft.AspNetCore.SpaServices.Extensions.Proxy.SpaProxy.PerformProxyRequest(HttpContext context, HttpClient httpClient, Task`1 baseUriTask, CancellationToken applicationStoppingToken, Boolean proxy404s)
         at Microsoft.AspNetCore.Builder.SpaProxyingExtensions.<>c__DisplayClass2_0.<<UseProxyToSpaDevelopmentServer>b__0>d.MoveNext()
      --- End of stack trace from previous location ---
         at Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
         at Swashbuckle.AspNetCore.SwaggerUI.SwaggerUIMiddleware.Invoke(HttpContext httpContext)
         at Swashbuckle.AspNetCore.Swagger.SwaggerMiddleware.Invoke(HttpContext httpContext, ISwaggerProvider swaggerProvider)
         at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
         at Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddlewareImpl.Invoke(HttpContext context)
fail: Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware[1]
      An unhandled exception has occurred while executing the request.
      System.TimeoutException: The create-react-app server did not start listening for requests within the timeout period of 120 seconds. Check the log output for error information.
         at Microsoft.AspNetCore.SpaServices.Extensions.Util.TaskTimeoutExtensions.WithTimeout[T](Task`1 task, TimeSpan timeoutDelay, String message)
         at Microsoft.AspNetCore.SpaServices.ReactDevelopmentServer.ReactDevelopmentServerMiddleware.<>c__DisplayClass2_0.<<Attach>b__0>d.MoveNext()
      --- End of stack trace from previous location ---
         at Microsoft.AspNetCore.SpaServices.Extensions.Proxy.SpaProxy.PerformProxyRequest(HttpContext context, HttpClient httpClient, Task`1 baseUriTask, CancellationToken applicationStoppingToken, Boolean proxy404s)
         at Microsoft.AspNetCore.Builder.SpaProxyingExtensions.<>c__DisplayClass2_0.<<UseProxyToSpaDevelopmentServer>b__0>d.MoveNext()
      --- End of stack trace from previous location ---
         at Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
         at Swashbuckle.AspNetCore.SwaggerUI.SwaggerUIMiddleware.Invoke(HttpContext httpContext)
         at Swashbuckle.AspNetCore.Swagger.SwaggerMiddleware.Invoke(HttpContext httpContext, ISwaggerProvider swaggerProvider)
         at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
         at Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddlewareImpl.Invoke(HttpContext context)

问题原因

核心原因是.NET 8中ReactDevelopmentServerMiddleware的服务启动检测逻辑是针对传统create-react-app(基于Webpack)的日志输出设计的,而当前项目使用的是Vite作为构建工具,Vite的启动日志格式与Webpack不同,导致中间件无法识别服务已启动,最终触发超时。此外,日志中显示超时时间为120秒,说明手动设置的StartupTimeout未被中间件正确读取。

解决方案

方法一:固定Vite端口并手动配置代理

绕过ReactDevelopmentServerMiddleware的自动检测逻辑,直接将.NET请求代理到Vite服务端口:

  1. 修改Vite配置固定端口
    在前端项目的vite.config.ts中指定固定端口,避免动态端口带来的代理问题:
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'

export default defineConfig({
  plugins: [react()],
  server: {
    port: 5174 // 固定Vite服务端口
  }
})
  1. 修改.NET的SPA配置
    替换UseReactDevelopmentServer为UseProxyToSpaDevelopmentServer,直接指定代理地址:
app.UseSpa(spa =>
{
    spa.Options.SourcePath = "WebClient";

    if (environment.IsDevelopment())
    {
        // 直接代理到固定的Vite服务地址
        spa.UseProxyToSpaDevelopmentServer("http://localhost:5174");
    }
});
  1. 启动方式调整
    可以选择两种启动方式:
  • 先手动启动前端Vite服务(执行npm run dev),再启动.NET项目;
  • 保持.NET自动启动Vite,此时.NET会调用npm run dev启动服务,然后直接代理到固定端口。

方法二:升级SpaServices.Extensions包

确保项目中使用的Microsoft.AspNetCore.SpaServices.Extensions包是最新版本,新版本可能已修复Vite日志识别的问题。在NuGet包管理器中更新该包至最新稳定版。

方法三:自定义日志检测逻辑(进阶)

如果需要保留自动端口检测,可以自定义ReactDevelopmentServerMiddleware的日志解析逻辑,让其识别Vite的"ready"日志。但该方法需要编写自定义中间件,复杂度较高,推荐优先使用方法一。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.26 09:44:53