恢復 YouTube 評論名稱

此腳本將 YouTube 評論部分中的“handle”替換為用戶名

目前為 2024-02-05 提交的版本,檢視 最新版本

您需要先安裝使用者腳本管理器擴展,如 TampermonkeyGreasemonkeyViolentmonkey 之後才能安裝該腳本。

You will need to install an extension such as Tampermonkey to install this script.

您需要先安裝使用者腳本管理器擴充功能,如 TampermonkeyViolentmonkey 後才能安裝該腳本。

您需要先安裝使用者腳本管理器擴充功能,如 TampermonkeyUserscripts 後才能安裝該腳本。

你需要先安裝一款使用者腳本管理器擴展,比如 Tampermonkey,才能安裝此腳本

您需要先安裝使用者腳本管理器擴充功能後才能安裝該腳本。

(我已經安裝了使用者腳本管理器,讓我安裝!)

你需要先安裝一款使用者樣式管理器擴展,比如 Stylus,才能安裝此樣式

你需要先安裝一款使用者樣式管理器擴展,比如 Stylus,才能安裝此樣式

你需要先安裝一款使用者樣式管理器擴展,比如 Stylus,才能安裝此樣式

你需要先安裝一款使用者樣式管理器擴展後才能安裝此樣式

你需要先安裝一款使用者樣式管理器擴展後才能安裝此樣式

你需要先安裝一款使用者樣式管理器擴展後才能安裝此樣式

(我已經安裝了使用者樣式管理器,讓我安裝!)

// ==UserScript==
// @name Return YouTube Comment Username
// @name:ja YouTubeコメント欄の名前を元に戻す
// @name:zh-CN 恢復 YouTube 评论用户名
// @name:zh-TW 恢復 YouTube 評論名稱
// @version 0.4.1
// @author yakisova41
// @license MIT
// @icon data:image/png;base64,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
// @namespace https://yt-returnname-api.pages.dev/extension/
// @description This script replaces the "handle" in the YouTube comments section to user name
// @description:ja YouTubeのコメント欄の名前をハンドル(@...)からユーザー名に書き換えます。
// @description:zh-TW 此腳本將 YouTube 評論部分中的“handle”替換為用戶名
// @description:zh-CN 此脚本将 YouTube 评论部分中的“handle”替换为用户名
// @match https://www.youtube.com/*
// @grant unsafeWindow
// @run-at document-end
// ==/UserScript==

const inject = ()=>{// src/utils/isCommentRenderer.ts
function isCommentRenderer(continuationItems) {
  if (continuationItems.length > 0) {
    if ("commentThreadRenderer" in continuationItems[0]) {
      return false;
    }
    if ("commentRenderer" in continuationItems[0]) {
      return true;
    }
  }
  return false;
}
function isCommentRendererV2(continuationItems) {
  if (continuationItems.length > 0) {
    if ("commentThreadRenderer" in continuationItems[0]) {
      return false;
    }
    if ("commentViewModel" in continuationItems[0]) {
      return true;
    }
  }
  return false;
}

// src/utils/debugLog.ts
function debugLog(message, value = "") {
  console.log(`[rycu] ${message} %c${value}`, "color:cyan;");
}
function debugErr(message) {
  console.error(`[rycu] ${message}`);
}

// src/utils/findElementByTrackingParams.ts
function findElementByTrackingParams(trackingParams, elementSelector) {
  let returnElement = null;
  let errorAlerted = false;
  const elems = document.querySelectorAll(elementSelector);
  for (let i = 0; i < elems.length; i++) {
    if (elems[i]?.trackedParams === void 0 && elems[i]?.controllerProxy?.trackedParams === void 0) {
      debugErr("TrackdParams property is not found");
    }
    if (elems[i].trackedParams === trackingParams) {
      returnElement = elems[i];
      break;
    } else if (elems[i]?.controllerProxy?.trackedParams === trackingParams) {
      returnElement = elems[i];
      break;
    } else {
      if (!errorAlerted) {
        void searchTrackedParamsByObject(trackingParams, elems[i]);
        errorAlerted = true;
      }
    }
  }
  return returnElement;
}
async function reSearchElement(trackingParams, selector) {
  return await new Promise((resolve) => {
    let isFinding = true;
    const search = () => {
      const el = findElementByTrackingParams(trackingParams, selector);
      if (el !== null) {
        resolve(el);
        isFinding = false;
      }
      if (isFinding) {
        setTimeout(() => {
          search();
        }, 100);
      }
    };
    search();
  });
}
function findElementAllByCommentId(commnetId, elementSelector) {
  const returnElements = [];
  const elems = document.querySelectorAll(elementSelector);
  for (let i = 0; i < elems.length; i++) {
    if (elems[i] !== void 0) {
      if (elems[i]?.__data?.data?.commentId === void 0 && elems[i]?.controllerProxy?.__data?.data?.commentId === void 0) {
        debugErr("Reply CommentId is not found");
        console.log(elems[i]);
      } else if (elems[i]?.__data?.data?.commentId !== void 0 && elems[i].__data.data.commentId === commnetId) {
        returnElements.push(elems[i]);
      } else if (elems[i]?.controllerProxy?.__data?.data?.commentId !== void 0 && elems[i].controllerProxy.__data.data.commentId === commnetId) {
        returnElements.push(elems[i]);
      }
    }
  }
  return returnElements;
}
async function reSearchElementAllByCommentId(commnetId, selector) {
  return await new Promise((resolve) => {
    let isFinding = true;
    const search = () => {
      const el = findElementAllByCommentId(commnetId, selector);
      if (el !== null) {
        resolve(el);
        isFinding = false;
      }
      if (isFinding) {
        setTimeout(() => {
          search();
        }, 100);
      }
    };
    search();
  });
}
async function searchTrackedParamsByObject(param, elem) {
  const elemObj = Object(elem);
  const search = (obj, history) => {
    Object.keys(obj).forEach((k) => {
      if (typeof obj[k] === "object") {
        search(obj[k], [...history, k]);
      } else if (obj[k] === param) {
        history.push(k);
        alert(
          `[Return YouTube Comment Username] Unknown Object format!
"${history.join(
            ">"
          )}"`
        );
      }
    });
  };
  search(elemObj, []);
}

// src/types/AppendContinuationItemsAction.ts
function isReplyContinuationItemsV1(obj) {
  return Object.hasOwn(obj[0], "commentRenderer");
}
function isReplyContinuationItemsV2(obj) {
  return Object.hasOwn(obj[0], "commentViewModel");
}
function isConfinuationItemV2(obj) {
  return Object.hasOwn(obj, "commentViewModel");
}
function isConfinuationItemV1(obj) {
  return Object.hasOwn(obj, "comment");
}

// src/utils/getShadyChildren.ts
function getShadyChildren(parentElement, index, id) {
  let returnElem;
  const child = parentElement.__shady_native_children[index];
  if (child === null || child.id !== id) {
    returnElem = parentElement.querySelector(`#${id}`);
    console.log(
      `%cReturn YouTube Comment Username Warning%c %cChildren Cannot Get by Index!%c
%cid of element attempting to retrieve: ${id}
If you find this debug log, please report it to the github issue%c`,
      "background:#f0e68c; color:#000;font-size:20px;",
      "",
      "color:#00c72e;font-size:16px;",
      "",
      "color: #13ebdc;",
      "",
      "\nhttps://github.com/yakisova41/return-youtube-comment-username/issues/new?assignees=&labels=bug&projects=&template=bug_report.yaml&title=%5BBug%5D%3A+Children%20Cannot%20Get%20by%20Index"
    );
  } else {
    returnElem = child;
  }
  return returnElem;
}

// src/utils/escapeString.ts
function escapeString(text) {
  return text.replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, `&quot;`).replace(/'/g, `&#39;`).replace(/&/g, `&amp;`);
}
function decodeString(text) {
  return text.replace(/&lt;/g, "<").replace(/&gt;/g, ">").replace(/&quot;/g, `"`).replace(/&#39;/g, `'`).replace(/&amp;/g, `&`);
}

// src/utils/getUserName.ts
var isUseFeed = true;
async function getUserName(id) {
  return new Promise((resolve) => {
    if (isUseFeed) {
      debugLog("Get name by Feed");
      fetchFeed(id).then((name) => {
        resolve(name);
      }).catch(() => {
        isUseFeed = false;
        debugErr("Catch Feed API Error");
        fetchBrowse(id).then((name) => {
          resolve(name);
        });
      });
    } else {
      debugLog("Get name by Browse");
      fetchBrowse(id).then((name) => {
        resolve(name);
      });
    }
  });
}
async function fetchFeed(id) {
  return await fetch(
    `https://www.youtube.com/feeds/videos.xml?channel_id=${id}`,
    {
      method: "GET",
      cache: "default",
      keepalive: true
    }
  ).then(async (res) => {
    if (res.status !== 200)
      throw new Error(`Feed API Error
status: ${res.status}`);
    return await res.text();
  }).then((text) => {
    const match = text.match("<title>([^<].*)</title>");
    if (match !== null) {
      return decodeString(match[1]);
    } else {
      debugErr("XML title not found");
      return "";
    }
  });
}
async function fetchBrowse(id) {
  return await fetch(
    `https://www.youtube.com/youtubei/v1/browse?key=AIzaSyAO_FJ2SlqU8Q4STEHLGCilw_Y9_11qcW8&prettyPrint=false`,
    {
      method: "POST",
      headers: {
        cache: "default",
        accept: "*/*",
        "accept-encoding": "gzip, deflate, br",
        "accept-language": "en",
        "content-type": "application/json",
        dnt: "1",
        referer: `https://www.youtube.com/channel/${id}`
      },
      body: JSON.stringify({
        context: {
          client: {
            hl: window.yt.config_.HL,
            gl: window.yt.config_.GL,
            clientName: "WEB",
            clientVersion: "2.20230628.01.00",
            platform: "DESKTOP",
            acceptHeader: "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7"
          },
          user: { lockedSafetyMode: false },
          request: {
            useSsl: true
          }
        },
        browseId: id,
        params: "EgVhYm91dPIGBAoCEgA%3D"
      })
    }
  ).then(async (res) => {
    if (res.status !== 200)
      throw new Error(`Browse API Error
status: ${res.status}`);
    return await res.json();
  }).then((text) => {
    const name = text.header.c4TabbedHeaderRenderer.title;
    return decodeString(name);
  });
}

// src/rewrites/rewriteOfCommentRenderer/nameRewriteOfCommentRenderer.ts
function nameRewriteOfCommentRenderer(commentRenderer, isNameContainerRender, userId) {
  const commentRendererBody = getShadyChildren(
    commentRenderer,
    2,
    "body"
  );
  if (commentRendererBody === null) {
    throw new Error("[rycu] comment renderer body is null");
  }
  let nameElem = commentRendererBody.querySelector(
    "#main > #header > #header-author > h3 > a > yt-formatted-string"
  );
  if (isNameContainerRender) {
    const containerMain = getShadyChildren(commentRendererBody, 1, "main");
    if (containerMain !== null) {
      nameElem = containerMain.querySelector(
        "#header > #header-author > #author-comment-badge > ytd-author-comment-badge-renderer > a > #channel-name > #container > #text-container > yt-formatted-string"
      );
    }
  }
  void getUserName(userId).then((name) => {
    if (nameElem !== null) {
      if (nameElem.getAttribute("is-empty") !== null) {
        nameElem.removeAttribute("is-empty");
        console.log("false");
      }
      if (isNameContainerRender) {
        nameElem.__shady_native_innerHTML = escapeString(name);
      } else {
        nameElem.textContent = name;
      }
    } else {
      debugErr("Name element is null");
    }
  }).catch((e) => {
    debugErr(e);
  });
}

// src/rewrites/rewriteOfCommentRenderer/mentionRewriteOfCommentRenderer.ts
function mentionRewriteOfCommentRenderer(commentRenderer) {
  const commentRendererBody = getShadyChildren(commentRenderer, 2, "body");
  const main2 = commentRendererBody?.querySelector("#main");
  if (main2 !== void 0 && main2 !== null) {
    const aTags = main2.querySelectorAll(
      "#comment-content > ytd-expander > #content > #content-text > a"
    );
    for (let i = 0; i < aTags.length; i++) {
      if (aTags[i].getAttribute("href")?.match("/channel/.*") !== null) {
        const href = aTags[i].getAttribute("href");
        if (href !== null) {
          void getUserName(href.split("/")[2]).then((name) => {
            aTags[i].textContent = `@${name} `;
          }).catch((e) => {
            debugErr(e);
          });
        } else {
          debugErr("Mention Atag is have not Href attr");
        }
      }
    }
  }
}

// src/rewrites/rewriteOfCommentRenderer/nameRewriteOfCommentViewModel.ts
function nameRewriteOfCommentViewModel(commentRenderer) {
  const commentRendererBody = getShadyChildren(
    commentRenderer,
    2,
    "body"
  );
  if (commentRendererBody === null) {
    throw new Error("[rycu] comment renderer body is null");
  }
  if (!commentRendererBodyGuard(commentRendererBody)) {
    throw new Error(
      "[rycu] The object format of comment renderer body is invalid."
    );
  }
  const isNameContainerRender = commentRendererBody.__dataHost.$["author-text"].__dataHost.__data.authorCommentBadge !== null;
  let nameElem = commentRendererBody.querySelector(
    "#main > #header > #header-author > h3 > a > span"
  );
  const userId = commentRendererBody.__dataHost.$["author-text"].__dataHost.__data.authorEndpoint.browseEndpoint.browseId;
  if (isNameContainerRender) {
    const containerMain = getShadyChildren(commentRendererBody, 1, "main");
    if (containerMain !== null) {
      nameElem = containerMain.querySelector(
        "#header > #header-author > #author-comment-badge > ytd-author-comment-badge-renderer > a > #channel-name > #container > #text-container > yt-formatted-string"
      );
    }
  }
  void getUserName(userId).then((name) => {
    if (nameElem !== null) {
      if (nameElem.getAttribute("is-empty") !== null) {
        nameElem.removeAttribute("is-empty");
      }
      if (isNameContainerRender) {
        nameElem.__shady_native_innerHTML = escapeString(name);
      } else {
        nameElem.textContent = name;
      }
    } else {
      debugErr("Name element is null");
    }
  }).catch((e) => {
    debugErr(e);
  });
}
function commentRendererBodyGuard(elem) {
  return Object.hasOwn(elem, "__dataHost");
}

// src/rewrites/rewriteOfCommentRenderer/mentionRewriteOfCommentRendererV2.ts
function mentionRewriteOfCommentRendererV2(commentRenderer) {
  const commentRendererBody = getShadyChildren(commentRenderer, 2, "body");
  const main2 = commentRendererBody?.querySelector("#main");
  if (main2 !== void 0 && main2 !== null) {
    const aTags = main2.querySelectorAll(
      "#expander > #content > #content-text > span > span > a"
    );
    for (let i = 0; i < aTags.length; i++) {
      if (aTags[i].getAttribute("href")?.match("/channel/.*") !== null) {
        const href = aTags[i].getAttribute("href");
        if (href !== null) {
          void getUserName(href.split("/")[2]).then((name) => {
            aTags[i].textContent = `@${name} `;
          }).catch((e) => {
            debugErr(e);
          });
        } else {
          debugErr("Mention Atag is have not Href attr");
        }
      }
    }
  }
}

// src/rewrites/reply.ts
function rewriteReplytNameFromContinuationItems(continuationItems) {
  debugLog("Reply Rewrite");
  if (isReplyContinuationItemsV1(continuationItems)) {
    debugLog("Reply continuationItems V1");
    for (let i = 0; i < continuationItems.length; i++) {
      const { commentRenderer } = continuationItems[i];
      if (commentRenderer !== void 0) {
        void getReplyElem(commentRenderer.trackingParams, "V1").then(
          (replyElem) => {
            reWriteReplyElem(replyElem, commentRenderer);
          }
        );
      }
    }
  }
  if (isReplyContinuationItemsV2(continuationItems)) {
    debugLog("Reply continuationItems V2");
    for (let i = 0; i < continuationItems.length; i++) {
      const { commentViewModel } = continuationItems[i];
      if (commentViewModel !== void 0) {
        void getReplyElem(
          commentViewModel.rendererContext.loggingContext.loggingDirectives.trackingParams,
          "V2"
        ).then((replyElem) => {
          reWriteReplyElemV2(replyElem);
        });
      }
    }
  }
}
function reWriteReplyElem(replyElem, rendererData) {
  let isContainer = rendererData.authorIsChannelOwner;
  if (rendererData.authorCommentBadge !== void 0) {
    isContainer = true;
  }
  nameRewriteOfCommentRenderer(
    replyElem,
    isContainer,
    rendererData.authorEndpoint.browseEndpoint.browseId
  );
  mentionRewriteOfCommentRenderer(replyElem);
  replyInputRewrite(replyElem);
}
function reWriteReplyElemV2(replyElem) {
  nameRewriteOfCommentViewModel(replyElem);
  mentionRewriteOfCommentRendererV2(replyElem);
  replyInputRewrite(replyElem);
}
async function getReplyElem(trackedParams, version) {
  return await new Promise((resolve) => {
    const selector = "#replies > ytd-comment-replies-renderer > #expander > #expander-contents > #contents > " + (version === "V1" ? "ytd-comment-renderer" : "ytd-comment-view-model");
    const commentRenderer = findElementByTrackingParams(
      trackedParams,
      selector
    );
    if (commentRenderer !== null) {
      resolve(commentRenderer);
    } else {
      void reSearchElement(trackedParams, selector).then((commentRenderer2) => {
        resolve(commentRenderer2);
      });
    }
  });
}
function rewriteTeaserReplytNameFromContinuationItems(continuationItems) {
  debugLog("Teaser Reply Rewrite");
  for (let i = 0; i < continuationItems.length; i++) {
    const { commentRenderer } = continuationItems[i];
    if (commentRenderer !== void 0) {
      void reSearchElementAllByCommentId(
        commentRenderer.commentId,
        "ytd-comment-replies-renderer > #teaser-replies > ytd-comment-renderer"
      ).then((replyElems) => {
        replyElems.forEach((replyElem) => {
          reWriteReplyElem(replyElem, commentRenderer);
        });
      });
      void reSearchElementAllByCommentId(
        commentRenderer.commentId,
        "ytd-comment-replies-renderer > #expander > #expander-contents > #contents > ytd-comment-renderer"
      ).then((replyElems) => {
        replyElems.forEach((replyElem) => {
          reWriteReplyElem(replyElem, commentRenderer);
        });
      });
    }
  }
}
function replyInputRewrite(replyElem) {
  const replyToReplyBtn = replyElem.querySelector(
    "#reply-button-end > ytd-button-renderer"
  );
  const replyToReplyHander = () => {
    const replyLink = replyElem.querySelector("#contenteditable-root > a");
    const href = replyLink?.getAttribute("href");
    const channelId = href?.split("/")[2];
    if (channelId !== void 0 && replyLink !== null) {
      void getUserName(channelId).then((name) => {
        replyLink.textContent = ` @${name}`;
      });
    }
    replyToReplyBtn?.removeEventListener("click", replyToReplyHander);
  };
  replyToReplyBtn?.addEventListener("click", replyToReplyHander);
  document.addEventListener("rycu-pagechange", () => {
    replyToReplyBtn?.removeEventListener("click", replyToReplyHander);
  });
}

// src/rewrites/comment.ts
function rewriteCommentNameFromContinuationItems(continuationItems) {
  debugLog("Comment Rewrite");
  for (let i = 0; i < continuationItems.length; i++) {
    if (continuationItems[i].commentThreadRenderer !== void 0) {
      void getCommentElem(
        continuationItems[i].commentThreadRenderer.trackingParams
      ).then((commentElem) => {
        reWriteCommentElem(
          commentElem,
          continuationItems[i].commentThreadRenderer
        );
      });
      const teaserContents = continuationItems[i].commentThreadRenderer.replies?.commentRepliesRenderer.teaserContents;
      if (teaserContents !== void 0) {
        rewriteTeaserReplytNameFromContinuationItems(teaserContents);
      }
    }
  }
}
function reWriteCommentElem(commentElem, commentThreadRenderer) {
  const commentRenderer = getShadyChildren(commentElem, 1, "comment");
  if (commentRenderer !== null && commentRenderer !== void 0) {
    if (isConfinuationItemV1(commentThreadRenderer)) {
      debugLog("Comment continuationItems V1");
      let isContainer = commentThreadRenderer.comment.commentRenderer.authorIsChannelOwner;
      if (commentThreadRenderer.comment.commentRenderer.authorCommentBadge !== void 0) {
        isContainer = true;
      }
      nameRewriteOfCommentRenderer(
        commentRenderer,
        isContainer,
        commentThreadRenderer.comment.commentRenderer.authorEndpoint.browseEndpoint.browseId
      );
    }
    if (isConfinuationItemV2(commentThreadRenderer)) {
      debugLog("Comment continuationItems V2");
      nameRewriteOfCommentViewModel(commentRenderer);
    }
  }
}
async function getCommentElem(trackingParams) {
  return await new Promise((resolve) => {
    const commentElem = findElementByTrackingParams(
      trackingParams,
      "#comments > #sections > #contents > ytd-comment-thread-renderer"
    );
    if (commentElem !== null) {
      resolve(commentElem);
    } else {
      void reSearchElement(trackingParams, "ytd-comment-thread-renderer").then((commentElem2) => {
        resolve(commentElem2);
      }).catch((e) => {
        debugErr(e);
      });
    }
  });
}

// src/handlers/handleYtAppendContinuationItemsAction.ts
function handleYtAppendContinuationItemsAction(detail) {
  const continuationItems = detail.args[0].appendContinuationItemsAction.continuationItems;
  if (isCommentRenderer(continuationItems) || isCommentRendererV2(continuationItems)) {
    const replyDetail = detail;
    setTimeout(() => {
      rewriteReplytNameFromContinuationItems(
        replyDetail.args[0].appendContinuationItemsAction.continuationItems
      );
    }, 100);
  } else {
    const commentDetail = detail;
    setTimeout(() => {
      rewriteCommentNameFromContinuationItems(
        commentDetail.args[0].appendContinuationItemsAction.continuationItems
      );
    }, 400);
  }
}

// src/handlers/handleYtCreateCommentAction.ts
function handleYtCreateCommentAction(detail) {
  const createCommentDetail = detail;
  const continuationItems = [
    {
      commentThreadRenderer: createCommentDetail.args[0].createCommentAction.contents.commentThreadRenderer
    }
  ];
  setTimeout(() => {
    rewriteCommentNameFromContinuationItems(continuationItems);
  }, 100);
}

// src/handlers/handleYtCreateCommentReplyAction.ts
function handleYtCreateCommentReplyAction(detail) {
  const createReplyDetail = detail;
  const continuationItems = [
    {
      commentRenderer: createReplyDetail.args[0].createCommentReplyAction.contents.commentRenderer
    }
  ];
  setTimeout(() => {
    rewriteTeaserReplytNameFromContinuationItems(continuationItems);
  }, 100);
}

// src/rewrites/highlightedReply.ts
function rewriteHighlightedReply(trackedParams, isContainer, userId) {
  const elem = findElementByTrackingParams(
    trackedParams,
    "ytd-comment-renderer"
  );
  const rewriteHighlightedReplyElem = (elem2) => {
    nameRewriteOfCommentRenderer(elem2, isContainer, userId);
    replyInputRewrite(elem2);
  };
  if (elem === null) {
    void reSearchElement(trackedParams, "ytd-comment-renderer").then((elem2) => {
      rewriteHighlightedReplyElem(elem2);
    });
  } else {
    rewriteHighlightedReplyElem(elem);
  }
}

// src/handlers/handleYtGetMultiPageMenuAction.ts
function handleYtGetMultiPageMenuAction(detail) {
  const getMultiPageMenuDetail = detail;
  const continuationItems = getMultiPageMenuDetail.args[0].getMultiPageMenuAction.menu.multiPageMenuRenderer.sections[1].itemSectionRenderer?.contents;
  const highLightedTeaserContents = getMultiPageMenuDetail.args[0]?.getMultiPageMenuAction?.menu?.multiPageMenuRenderer.sections[1].itemSectionRenderer?.contents[0]?.commentThreadRenderer.replies?.commentRepliesRenderer?.teaserContents;
  if (continuationItems !== void 0) {
    setTimeout(() => {
      rewriteCommentNameFromContinuationItems(continuationItems);
      if (highLightedTeaserContents !== void 0) {
        const highLightedReplyRenderer = highLightedTeaserContents[0]?.commentRenderer;
        let isContainer = highLightedReplyRenderer.authorIsChannelOwner;
        if (highLightedReplyRenderer.authorCommentBadge !== void 0) {
          isContainer = true;
        }
        rewriteHighlightedReply(
          highLightedReplyRenderer.trackingParams,
          isContainer,
          highLightedReplyRenderer.authorEndpoint.browseEndpoint.browseId
        );
      }
    }, 100);
  }
}

// src/handlers/handleYtHistory.ts
function handleYtHistory(detail) {
  const historyDetail = detail;
  const continuationItems = historyDetail.args[1].historyEntry?.rootData.response.contents.twoColumnWatchNextResults?.results?.results?.contents[3]?.itemSectionRenderer?.contents;
  if (continuationItems !== void 0) {
    setTimeout(() => {
      rewriteCommentNameFromContinuationItems(continuationItems);
    }, 100);
  }
}

// src/handlers/handleYtReloadContinuationItemsCommand.ts
function handleYtReloadContinuationItemsCommand(detail) {
  const reloadDetail = detail;
  const { slot } = reloadDetail.args[0].reloadContinuationItemsCommand;
  if (slot === "RELOAD_CONTINUATION_SLOT_BODY") {
    const continuationItems = reloadDetail.args[0].reloadContinuationItemsCommand.continuationItems;
    if (continuationItems !== void 0) {
      setTimeout(() => {
        rewriteCommentNameFromContinuationItems(continuationItems);
      }, 100);
    }
  }
}

// src/index.ts
function main() {
  debugLog("Script start");
  const handleYtAction = (e) => {
    switch (e.detail.actionName) {
      case "yt-append-continuation-items-action":
        handleYtAppendContinuationItemsAction(e.detail);
        break;
      case "yt-reload-continuation-items-command":
        handleYtReloadContinuationItemsCommand(e.detail);
        break;
      case "yt-history-load":
        handleYtHistory(e.detail);
        break;
      case "yt-get-multi-page-menu-action":
        handleYtGetMultiPageMenuAction(e.detail);
        break;
      case "yt-create-comment-action":
        handleYtCreateCommentAction(e.detail);
        break;
      case "yt-create-comment-reply-action":
        handleYtCreateCommentReplyAction(e.detail);
        break;
    }
  };
  document.addEventListener("yt-action", handleYtAction);
  document.addEventListener("yt-navigate-finish", () => {
    document.dispatchEvent(new Event("rycu-pagechange"));
  });
}

// node_modules/ts-extension-builder/tmp/entry.ts
var args = {};
if (typeof GM_info !== "undefined" && GM_info.script.grant !== void 0) {
  GM_info.script.grant.forEach((propatyName) => {
    let keyName = propatyName.split("GM_")[1];
    if (keyName === "xmlhttpRequest") {
      keyName = "xmlHttpRequest";
    }
    args[propatyName] = GM[keyName];
  });
}
main(args);
}
const script = document.createElement("script");
script.innerHTML = `(${inject.toString()})()`
unsafeWindow.document.body.appendChild(script)