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

Blazor无法识别独立JS文件中函数的问题求助

问题:Blazor JS互操作无法找到外部JS文件中的函数

创建了新的.js文件并关联到App.razor,但调用其中的getMessage函数时触发Microsoft.JSInterop.JSException,提示该函数未定义。但将函数直接写在App.razor的<script>标签内可正常运行。

错误日志

[2024-08-19T16:59:42.406Z] Error: Microsoft.JSInterop.JSException: Could not find 'getMessage' ('getMessage' was undefined).
Error: Could not find 'getMessage' ('getMessage' was undefined).
    at https://localhost:7151/_framework/blazor.web.js:1:734
    at Array.forEach (<anonymous>)
    at l.findFunction (https://localhost:7151/_framework/blazor.web.js:1:702)
    at b (https://localhost:7151/_framework/blazor.web.js:1:5445)
    at https://localhost:7151/_framework/blazor.web.js:1:3238
    at new Promise (<anonymous>)
    at y.beginInvokeJSFromDotNet (https://localhost:7151/_framework/blazor.web.js:1:3201)
    at gn._invokeClientMethod (https://localhost:7151/_framework/blazor.web.js:1:62841)
    at gn._processIncomingData (https://localhost:7151/_framework/blazor.web.js:1:60316)
    at connection.onreceive (https://localhost:7151/_framework/blazor.web.js:1:53957)
   at Microsoft.JSInterop.JSRuntime.InvokeAsync[TValue](Int64 targetInstanceId, String identifier, Object[] args)
   at BlazorApplication.Server.Components.ThemeButton.ChangeTheme()
   at Microsoft.AspNetCore.Components.ComponentBase.CallStateHasChangedOnAsyncCompletion(Task task)
   at Microsoft.AspNetCore.Components.RenderTree.Renderer.GetErrorHandledTask(Task taskToHandle, ComponentState owningComponentState)

相关代码示例

App.razor代码

<body>
    <Routes @rendermode="InteractiveServer" />
    <script>
         window.getMessage = () => {
             return "Hello, World!";
         };
    </script> <!-- 可正常运行 -->
    
    <script src="~/js/custom.js"></script> <!-- 无法运行,但包含相同函数 -->

    <script src="~/js/bootstrap.bundle.min.js"></script>
    <script src="_framework/blazor.web.js"></script>
</body>

JS互操作组件代码

@inject IJSRuntime JS

<button class="btn btn-outline-primary" @onclick="ChangeTheme">Change theme</button>
<br />

<span>Message: @Text</span>

@code {
    private string Text = "";

    private async Task ChangeTheme()
    {
        Text = await JS.InvokeAsync<string>("window.getMessage");
    }
}

解决方案

1. 确认JS文件路径与内容正确性

  • 确保custom.js存放在项目的wwwroot/js目录下(Blazor静态资源默认从wwwroot加载),路径改用绝对路径/js/custom.js避免解析问题。
  • 检查custom.js内的函数是否正确挂载到全局window对象,不能写成局部函数:
    window.getMessage = () => {
        return "Hello, World!";
    };
    

2. 验证脚本是否成功加载

打开浏览器开发者工具的Network标签,查看custom.js的请求状态:

  • 如果返回404,说明路径配置错误,需修正文件存放位置或引用路径。
  • 如果返回200但仍报错,检查文件内容是否与内嵌脚本完全一致。

3. 调整脚本加载时机

在InteractiveServer模式下,可将自定义脚本放在<head>标签内并添加defer属性,确保DOM加载完成后脚本才执行:

<head>
    <!-- 其他头部内容 -->
    <script src="/js/custom.js" defer></script>
</head>

4. 使用ES模块(推荐)

避免全局对象污染,将custom.js改为ES模块,通过模块导入方式调用:

  • custom.js内容:
    export function getMessage() {
        return "Hello, World!";
    }
    
  • 组件代码修改:
    @inject IJSRuntime JS
    @implements IDisposable
    
    <button class="btn btn-outline-primary" @onclick="ChangeTheme">Change theme</button>
    <br />
    
    <span>Message: @Text</span>
    
    @code {
        private string Text = "";
        private IJSObjectReference? _jsModule;
    
        protected override async Task OnAfterRenderAsync(bool firstRender)
        {
            if (firstRender)
            {
                _jsModule = await JS.InvokeAsync<IJSObjectReference>("import", "/js/custom.js");
            }
        }
    
        private async Task ChangeTheme()
        {
            if (_jsModule != null)
            {
                Text = await _jsModule.InvokeAsync<string>("getMessage");
            }
        }
    
        public void Dispose()
        {
            _jsModule?.DisposeAsync();
        }
    }
    

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.19 11:14:50