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

登录时Toast提示不显示问题:TypeError读取null的classList

问题根源

登录时调用showToast时,Toast的DOM结构还未加载完成,导致getElementById("liveToast")和getElementById("toastBody")返回null,进而触发TypeError: Cannot read properties of null (reading 'classList')错误。

核心原因:

  • 你通过jQuery的$("#alert").load("/staticHtml/toast.html")异步加载Toast的DOM,这个操作不会阻塞后续代码执行
  • 登录逻辑绑定在DOMContentLoaded事件中,该事件触发时,异步加载toast.html的请求可能还未完成,Toast元素还未插入到页面中
  • 退出登录时,页面已经完全加载完成,toast.html早已加载完毕,所以调用showToast能正常找到元素
解决方案

方案1:将登录逻辑放到Toast加载完成的回调中

修改load方法,添加回调函数,确保Toast DOM加载完成后再执行登录相关逻辑:

<script>
  $("#alert").load("/staticHtml/toast.html", function() {
    // Toast加载完成后触发自定义事件
    document.dispatchEvent(new CustomEvent('toastReady'));
  });
</script>
<script>
  // 监听Toast加载完成事件,再执行登录逻辑
  document.addEventListener('toastReady', async () => {
    try {
      const queryString = window.location.search;
      const urlParams = new URLSearchParams(queryString);
      const token = urlParams.get("token");

      if (token) {
        const id = urlParams.get("id");
        const username = urlParams.get("username");

        let params = {
          _id: id,
          username,
          token,
        };

        showToast("text-bg-success", `${username}, you have successfully signed in! Check out your <a href="/profile/${username}">profile</a>!`);
        localStorage.setItem("user", JSON.stringify(params));
      }
    } catch (err) {
      console.log(err)
      showToast("text-bg-danger", "Something went wrong");
    }
  });
</script>

方案2:内嵌Toast DOM到页面中

直接将toast.html的内容内嵌到页面的#alert容器中,避免异步加载的时序问题:

<div id="alert">
  <div class="toast-container position-fixed bottom-0 end-0 p-3">
    <div id="liveToast" class="toast align-items-center" role="alert" aria-live="assertive" aria-atomic="true">
      <div class="d-flex">
        <div class="toast-body" id="toastBody">Hello, world! This is a toast message.</div>
        <i class="fa fa-times me-2 m-auto" data-bs-dismiss="toast" aria-hidden="true"></i>
      </div>
    </div>
  </div>
</div>

同时移除原来的$("#alert").load("/staticHtml/toast.html")代码。

方案3:在showToast中添加元素存在校验(兜底方案)

如果无法修改加载时序,可以在showToast函数中添加重试逻辑,确保元素存在后再执行操作:

function showToast(toastType, message) {
  function attemptShow() {
    const toastLiveExample = document.getElementById("liveToast");
    const toastBody = document.getElementById("toastBody");
    
    if (!toastLiveExample || !toastBody) {
      // 元素未加载完成,100ms后重试
      setTimeout(attemptShow, 100);
      return;
    }

    const toastBootstrap = bootstrap.Toast.getOrCreateInstance(toastLiveExample);
    toastLiveExample.classList.add(toastType);
    toastBody.innerHTML = message;
    toastBootstrap.show();
  }
  
  attemptShow();
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.24 21:00:29