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

使用React Hooks实现Bootstrap 5模态框报Cannot read 'show' of null错误

问题原因

你的代码核心错误有4个:

  • React的setState是异步更新的,同一渲染周期内调用setModal后,当前作用域下的modal变量还是初始的null值,不会立刻拿到更新后的Modal实例,因此调用modal.show()会直接报错。
  • Bootstrap Modal的配置参数传错了位置,你把{keyboard: false}作为setModal的第二个参数传入,没有任何作用,该配置应该作为第二个参数传给new Modal()构造函数。
  • useEffect依赖数组为空,后续props.json发生变化时不会重新触发逻辑,无法满足动态判断展示的需求。
  • 关闭按钮的回调没有做非空判断,Modal未初始化完成时点击关闭也会触发同类报错。

修复后的完整代码

import { Modal } from 'bootstrap';
import React, { useState, useEffect, useRef } from 'react';
import ParseExceptions from './ParseExceptions';

const ParseExceptionsModal = (props) => {
  // 用ref存Modal实例,不需要响应式更新,更适合存储第三方实例
  const modalRef = useRef(null);
  const parseExceptionModal = useRef();

  // 依赖添加props.json,json变化时重新触发逻辑
  useEffect(() => {
    // 仅初始化一次Modal实例
    if (!modalRef.current) {
      modalRef.current = new Modal(parseExceptionModal.current, {
        keyboard: false,
      });
    }
    // 满足条件直接调用show,不需要等state更新
    if (props.json.length > 0) {
      modalRef.current.show();
    }
  }, [props.json]);

  // 关闭逻辑封装,加非空判断
  const handleClose = () => {
    if (modalRef.current) {
      modalRef.current.hide();
    }
  };

  return (
    <>
      <div
        className="modal fade"
        tabIndex="-1"
        role="dialog"
        ref={parseExceptionModal}
        aria-labelledby="parseExceptionModal"
        aria-hidden="true">
        <div className="modal-dialog" role="document">
          <div className="modal-content">
            <div className="modal-header">
              <h5 className="modal-title">{props.title}</h5>
              <button type="button" className="btn-close" onClick={handleClose} aria-label="Close">
              </button>
            </div>
            <div className="modal-body">
              <ParseExceptions json={props.json} />
            </div>
            <div className="modal-footer">
              <button onClick={handleClose} type="button" className="btn btn-outline-secondary">
                Dismiss
              </button>
            </div>
          </div>
        </div>
      </div>
    </>
  );
};
export default ParseExceptionsModal;

核心修改说明

  • 用useRef存储Modal实例,不需要触发组件重新渲染,也避开了state异步更新的问题,实例初始化完成后可以直接调用方法。
  • 修正了Modal配置的传递位置,把{keyboard: false}传入Modal构造函数。
  • useEffect依赖数组添加props.json,后续json更新时可以重新判断是否需要展示模态框。
  • 封装关闭逻辑,增加非空判断,避免未初始化时调用方法报错。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.19 13:54:03