From a2f74ac13f31cd00a7ee78c1f7cc36dab822e536 Mon Sep 17 00:00:00 2001 From: thePR0M3TH3AN <53631862+PR0M3TH3AN@users.noreply.github.com> Date: Mon, 20 Oct 2025 19:59:12 -0400 Subject: [PATCH] Handle trusted hide moderation state --- js/app.js | 115 ++++++++ js/ui/components/VideoCard.js | 381 ++++++++++++++++++++++++--- tests/moderation/video-card.test.mjs | 15 +- 3 files changed, 468 insertions(+), 43 deletions(-) diff --git a/js/app.js b/js/app.js index 947ad27d..dafa855c 100644 --- a/js/app.js +++ b/js/app.js @@ -5148,15 +5148,71 @@ class Application { const computedBlockAutoplay = trustedCount >= thresholds.autoplayBlockThreshold; const computedBlurThumbnail = trustedCount >= thresholds.blurThreshold; + const muteHideThreshold = Number.isFinite(thresholds.trustedMuteHideThreshold) + ? Math.max(0, Math.floor(thresholds.trustedMuteHideThreshold)) + : Number.POSITIVE_INFINITY; + const reportHideThreshold = Number.isFinite(thresholds.trustedSpamHideThreshold) + ? Math.max(0, Math.floor(thresholds.trustedSpamHideThreshold)) + : Number.POSITIVE_INFINITY; + + const existingHideReason = + typeof existingModeration.hideReason === "string" + ? existingModeration.hideReason.trim() + : ""; + const existingHideBypass = + typeof existingModeration.hideBypass === "string" + ? existingModeration.hideBypass.trim() + : ""; + const existingHideCounts = + existingModeration.hideCounts && typeof existingModeration.hideCounts === "object" + ? existingModeration.hideCounts + : null; + + let hideReason = ""; + let hideTriggered = false; + + if (trustedMuted && trustedMuteCount >= muteHideThreshold) { + hideReason = "trusted-mute-hide"; + hideTriggered = true; + } else if (trustedCount >= reportHideThreshold) { + hideReason = "trusted-report-hide"; + hideTriggered = true; + } else if (existingHideReason && existingHideCounts) { + hideReason = existingHideReason; + hideTriggered = true; + } + + const hideCounts = hideTriggered + ? { + trustedMuteCount, + trustedReportCount: trustedCount, + } + : null; + + let hideBypass = hideTriggered ? existingHideBypass : ""; + const computedHidden = hideTriggered && !hideBypass; + const overrideEntry = getModerationOverride(video.id); const overrideActive = overrideEntry?.showAnyway === true; const overrideUpdatedAt = Number.isFinite(overrideEntry?.updatedAt) ? Math.floor(overrideEntry.updatedAt) : Date.now(); + const originalHideCounts = hideCounts + ? { + trustedMuteCount: Math.max(0, Math.floor(hideCounts.trustedMuteCount)), + trustedReportCount: Math.max(0, Math.floor(hideCounts.trustedReportCount)), + } + : null; + const originalState = { blockAutoplay: computedBlockAutoplay, blurThumbnail: computedBlurThumbnail, + hidden: computedHidden, + hideReason: hideTriggered ? hideReason : "", + hideCounts: originalHideCounts, + hideBypass, + hideTriggered, }; const decoratedModeration = { @@ -5173,12 +5229,27 @@ class Application { original: { blockAutoplay: originalState.blockAutoplay, blurThumbnail: originalState.blurThumbnail, + hidden: originalState.hidden, + hideReason: originalState.hideReason, + hideCounts: originalState.hideCounts, + hideBypass: originalState.hideBypass, + hideTriggered: originalState.hideTriggered, }, }; if (overrideActive) { decoratedModeration.blockAutoplay = false; decoratedModeration.blurThumbnail = false; + decoratedModeration.hidden = false; + if (decoratedModeration.hideReason) { + delete decoratedModeration.hideReason; + } + if (decoratedModeration.hideCounts) { + delete decoratedModeration.hideCounts; + } + if (decoratedModeration.hideBypass) { + delete decoratedModeration.hideBypass; + } decoratedModeration.viewerOverride = { showAnyway: true, updatedAt: overrideUpdatedAt, @@ -5186,6 +5257,22 @@ class Application { } else { decoratedModeration.blockAutoplay = originalState.blockAutoplay; decoratedModeration.blurThumbnail = originalState.blurThumbnail; + decoratedModeration.hidden = originalState.hidden; + if (originalState.hideReason) { + decoratedModeration.hideReason = originalState.hideReason; + } else if (decoratedModeration.hideReason) { + delete decoratedModeration.hideReason; + } + if (originalState.hideCounts) { + decoratedModeration.hideCounts = { ...originalState.hideCounts }; + } else if (decoratedModeration.hideCounts) { + delete decoratedModeration.hideCounts; + } + if (originalState.hideBypass) { + decoratedModeration.hideBypass = originalState.hideBypass; + } else if (decoratedModeration.hideBypass) { + delete decoratedModeration.hideBypass; + } if (decoratedModeration.viewerOverride) { delete decoratedModeration.viewerOverride; } @@ -5214,10 +5301,38 @@ class Application { const target = storedVideo || video; if (target) { + if (target.moderation && typeof target.moderation === "object") { + if (target.moderation.hidden) { + delete target.moderation.hidden; + } + if (target.moderation.hideReason) { + delete target.moderation.hideReason; + } + if (target.moderation.hideCounts) { + delete target.moderation.hideCounts; + } + if (target.moderation.hideBypass) { + delete target.moderation.hideBypass; + } + } this.decorateVideoModeration(target); } if (this.currentVideo && this.currentVideo.id === video.id) { + if (this.currentVideo.moderation && typeof this.currentVideo.moderation === "object") { + if (this.currentVideo.moderation.hidden) { + delete this.currentVideo.moderation.hidden; + } + if (this.currentVideo.moderation.hideReason) { + delete this.currentVideo.moderation.hideReason; + } + if (this.currentVideo.moderation.hideCounts) { + delete this.currentVideo.moderation.hideCounts; + } + if (this.currentVideo.moderation.hideBypass) { + delete this.currentVideo.moderation.hideBypass; + } + } this.decorateVideoModeration(this.currentVideo); } diff --git a/js/ui/components/VideoCard.js b/js/ui/components/VideoCard.js index 1a905c66..cbf5001c 100644 --- a/js/ui/components/VideoCard.js +++ b/js/ui/components/VideoCard.js @@ -114,6 +114,7 @@ export class VideoCard { this.moderationActionButton = null; this.moderationBadgeId = ""; this.badgesContainerEl = null; + this.hiddenSummaryEl = null; this.boundShowAnywayHandler = (event) => this.handleShowAnywayClick(event); this.root = null; @@ -425,6 +426,7 @@ export class VideoCard { this.applyPlaybackDatasets(); this.bindEvents(); + this.refreshModerationUi(); } setCardBackdropImage(src) { @@ -975,6 +977,50 @@ export class VideoCard { ? moderation.original : {}; + const activeHidden = moderation?.hidden === true; + const originalHidden = original.hidden === true; + const hideReasonActive = + typeof moderation?.hideReason === "string" ? moderation.hideReason.trim() : ""; + const hideBypassActive = + typeof moderation?.hideBypass === "string" ? moderation.hideBypass.trim() : ""; + const originalHideReason = + typeof original.hideReason === "string" ? original.hideReason.trim() : ""; + const originalHideBypass = + typeof original.hideBypass === "string" ? original.hideBypass.trim() : ""; + const originalHideTriggered = original.hideTriggered === true; + + const normalizeHideCounts = (input) => { + if (!input || typeof input !== "object") { + return null; + } + const normalized = {}; + let hasValue = false; + if (Number.isFinite(input.trustedMuteCount)) { + normalized.trustedMuteCount = Math.max(0, Math.floor(input.trustedMuteCount)); + hasValue = true; + } + if (Number.isFinite(input.trustedReportCount)) { + normalized.trustedReportCount = Math.max(0, Math.floor(input.trustedReportCount)); + hasValue = true; + } + return hasValue ? normalized : null; + }; + + const baseHideCounts = { + trustedMuteCount, + trustedReportCount: trustedCount, + }; + + const activeHideCounts = + normalizeHideCounts(moderation?.hideCounts) || + (activeHidden || hideReasonActive ? { ...baseHideCounts } : null); + const originalHideCounts = + normalizeHideCounts(original?.hideCounts) || + (originalHideTriggered ? { ...baseHideCounts } : null); + + const effectiveHideReason = hideReasonActive || originalHideReason; + const effectiveHideCounts = activeHideCounts || originalHideCounts; + const context = { reportType, friendlyType: reportType ? reportType.replace(/[_-]+/g, " ").trim() : "", @@ -988,6 +1034,17 @@ export class VideoCard { activeBlur: moderation?.blurThumbnail === true, activeBlockAutoplay: moderation?.blockAutoplay === true, overrideActive: moderation?.viewerOverride?.showAnyway === true, + activeHidden, + originalHidden, + originalHideTriggered, + hideReason: hideReasonActive, + hideCounts: activeHideCounts, + hideBypass: hideBypassActive, + originalHideReason, + originalHideCounts, + originalHideBypass, + effectiveHideReason, + effectiveHideCounts, }; context.shouldShow = @@ -995,9 +1052,13 @@ export class VideoCard { context.originalBlockAutoplay || context.trustedCount > 0 || context.trustedMuted || - context.overrideActive; + context.overrideActive || + context.originalHidden || + context.activeHidden || + context.originalHideTriggered; - context.allowOverride = context.originalBlur || context.originalBlockAutoplay; + context.allowOverride = + context.originalBlur || context.originalBlockAutoplay || context.originalHidden; return context; } @@ -1032,19 +1093,82 @@ export class VideoCard { return combined.charAt(0).toUpperCase() + combined.slice(1); } + buildHiddenSummaryLabel(context) { + if (!context) { + return ""; + } + + const reason = context.effectiveHideReason; + if (!reason) { + return ""; + } + + const countsSource = + context.effectiveHideCounts || context.originalHideCounts || context.hideCounts || null; + const getCount = (key, fallback) => { + if (countsSource && Number.isFinite(countsSource[key])) { + return Math.max(0, Number(countsSource[key])); + } + if (Number.isFinite(context[key])) { + return Math.max(0, Number(context[key])); + } + return Math.max(0, Number(fallback) || 0); + }; + + if (reason === "trusted-mute-hide") { + const count = getCount("trustedMuteCount", context.trustedMuteCount || 0); + if (count > 0) { + const label = count === 1 ? "trusted mute" : "trusted mutes"; + return `${count} ${label}`; + } + return "trusted mute"; + } + + if (reason === "trusted-report-hide") { + const count = getCount("trustedReportCount", context.trustedCount || 0); + const type = typeof context.friendlyType === "string" ? context.friendlyType.trim() : ""; + const normalizedType = type ? type.toLowerCase() : ""; + if (count > 0) { + const label = count === 1 ? "report" : "reports"; + if (normalizedType) { + return `${count} trusted ${normalizedType} ${label}`; + } + const base = count === 1 ? "trusted report" : "trusted reports"; + return `${count} ${base}`; + } + if (normalizedType) { + return `trusted ${normalizedType} reports`; + } + return "trusted reports"; + } + + return ""; + } + buildModerationBadgeText(context) { if (!context) { return ""; } + const hiddenLabel = this.buildHiddenSummaryLabel(context); const reason = this.buildModerationReasonText(context); if (context.overrideActive) { + if (hiddenLabel) { + return `Showing despite ${hiddenLabel}`; + } if (reason) { return `Showing despite ${reason}`; } return "Showing despite reports"; } + if (context.activeHidden || (context.originalHidden && !context.overrideActive)) { + if (hiddenLabel) { + return `Hidden ยท ${hiddenLabel}`; + } + return "Hidden"; + } + const parts = []; if (context.originalBlur) { parts.push("Blurred"); @@ -1157,8 +1281,7 @@ export class VideoCard { }); } - buildModerationBadge() { - const context = this.getModerationContext(); + buildModerationBadge(context = this.getModerationContext()) { if (!context.shouldShow) { this.moderationBadgeEl = null; this.moderationBadgeTextEl = null; @@ -1177,12 +1300,18 @@ export class VideoCard { }); badge.dataset.variant = context.overrideActive ? "neutral" : "warning"; badge.dataset.moderationBadge = "true"; + const hiddenActive = context.activeHidden && !context.overrideActive; const state = context.overrideActive ? "override" - : context.trustedMuted - ? "trusted-mute" - : "blocked"; + : hiddenActive + ? "hidden" + : context.trustedMuted + ? "trusted-mute" + : "blocked"; badge.dataset.moderationState = state; + if (hiddenActive && context.effectiveHideReason) { + badge.dataset.moderationHideReason = context.effectiveHideReason; + } const badgeId = this.getModerationBadgeId(); badge.id = badgeId; @@ -1248,9 +1377,9 @@ export class VideoCard { return badge; } - updateModerationBadge() { - const context = this.getModerationContext(); + updateModerationBadge(context = this.getModerationContext()) { const badge = this.moderationBadgeEl; + const hiddenActive = context.activeHidden && !context.overrideActive; if (!context.shouldShow) { if (badge && badge.parentElement) { @@ -1265,32 +1394,42 @@ export class VideoCard { this.moderationBadgeEl = null; this.moderationBadgeTextEl = null; this.moderationActionButton = null; + if (this.hiddenSummaryEl && this.hiddenSummaryEl.parentElement === this.root) { + this.hiddenSummaryEl.remove(); + } this.updateModerationAria(); return; } if (!badge) { - const nextBadge = this.buildModerationBadge(); + const nextBadge = this.buildModerationBadge(context); if (nextBadge) { - if (!this.badgesContainerEl) { - this.badgesContainerEl = this.createElement("div", { - classNames: ["flex", "flex-wrap", "items-center", "gap-sm"], - }); - if (this.contentEl) { - if ( - this.discussionCountEl && - this.discussionCountEl.parentElement === this.contentEl - ) { - this.contentEl.insertBefore( - this.badgesContainerEl, - this.discussionCountEl, - ); - } else { - this.contentEl.appendChild(this.badgesContainerEl); + if (hiddenActive) { + const container = this.ensureHiddenSummaryContainer(); + if (container) { + container.appendChild(nextBadge); + } + } else { + if (!this.badgesContainerEl) { + this.badgesContainerEl = this.createElement("div", { + classNames: ["flex", "flex-wrap", "items-center", "gap-sm"], + }); + if (this.contentEl) { + if ( + this.discussionCountEl && + this.discussionCountEl.parentElement === this.contentEl + ) { + this.contentEl.insertBefore( + this.badgesContainerEl, + this.discussionCountEl, + ); + } else { + this.contentEl.appendChild(this.badgesContainerEl); + } } } + this.badgesContainerEl.appendChild(nextBadge); } - this.badgesContainerEl.appendChild(nextBadge); } this.updateModerationAria(); return; @@ -1299,10 +1438,17 @@ export class VideoCard { badge.dataset.variant = context.overrideActive ? "neutral" : "warning"; const state = context.overrideActive ? "override" - : context.trustedMuted - ? "trusted-mute" - : "blocked"; + : hiddenActive + ? "hidden" + : context.trustedMuted + ? "trusted-mute" + : "blocked"; badge.dataset.moderationState = state; + if (hiddenActive && context.effectiveHideReason) { + badge.dataset.moderationHideReason = context.effectiveHideReason; + } else if (badge.dataset.moderationHideReason) { + delete badge.dataset.moderationHideReason; + } const textContent = this.buildModerationBadgeText(context); if (this.moderationBadgeTextEl) { @@ -1347,6 +1493,33 @@ export class VideoCard { badge.setAttribute("aria-label", `${textContent}.`); } + if (hiddenActive) { + const container = this.ensureHiddenSummaryContainer(); + if (container && badge.parentElement !== container) { + if (badge.parentElement) { + badge.parentElement.removeChild(badge); + } + container.appendChild(badge); + } + } else if (this.badgesContainerEl) { + if (!this.badgesContainerEl.parentElement && this.contentEl) { + if ( + this.discussionCountEl && + this.discussionCountEl.parentElement === this.contentEl + ) { + this.contentEl.insertBefore(this.badgesContainerEl, this.discussionCountEl); + } else { + this.contentEl.appendChild(this.badgesContainerEl); + } + } + if (badge.parentElement !== this.badgesContainerEl) { + if (badge.parentElement) { + badge.parentElement.removeChild(badge); + } + this.badgesContainerEl.appendChild(badge); + } + } + if (context.overrideActive || !context.allowOverride) { if (this.moderationActionButton) { this.moderationActionButton.removeEventListener( @@ -1366,6 +1539,87 @@ export class VideoCard { } } + ensureHiddenSummaryContainer() { + if (!this.root) { + return null; + } + + if (!this.hiddenSummaryEl) { + this.hiddenSummaryEl = this.createElement("div", { + classNames: ["p-md", "bv-stack", "bv-stack--tight"], + }); + this.hiddenSummaryEl.dataset.moderationHiddenContainer = "true"; + this.hiddenSummaryEl.setAttribute("role", "group"); + this.hiddenSummaryEl.setAttribute("aria-live", "polite"); + } + + const container = this.hiddenSummaryEl; + container.hidden = false; + container.removeAttribute("aria-hidden"); + + const referenceNode = this.anchorEl && this.anchorEl.parentElement === this.root ? this.anchorEl : this.root.firstChild; + if (referenceNode && referenceNode.parentElement === this.root) { + if (container.parentElement !== this.root || container.nextSibling !== referenceNode) { + this.root.insertBefore(container, referenceNode); + } + } else if (container.parentElement !== this.root) { + this.root.appendChild(container); + } + + const badgeId = this.getModerationBadgeId(); + if (badgeId) { + container.setAttribute("aria-labelledby", badgeId); + } else { + container.removeAttribute("aria-labelledby"); + } + + return container; + } + + updateHiddenState(context = this.getModerationContext()) { + const hiddenActive = context.activeHidden && !context.overrideActive; + const container = this.hiddenSummaryEl; + + if (hiddenActive) { + if (this.anchorEl) { + this.anchorEl.setAttribute("hidden", ""); + this.anchorEl.setAttribute("aria-hidden", "true"); + } + if (this.contentEl) { + this.contentEl.setAttribute("hidden", ""); + this.contentEl.setAttribute("aria-hidden", "true"); + } + + const summaryContainer = this.ensureHiddenSummaryContainer(); + if (summaryContainer) { + const description = this.buildModerationBadgeText(context); + if (description) { + summaryContainer.setAttribute("aria-label", description); + } else { + summaryContainer.removeAttribute("aria-label"); + } + } + } else { + if (this.anchorEl) { + this.anchorEl.removeAttribute("hidden"); + this.anchorEl.removeAttribute("aria-hidden"); + } + if (this.contentEl) { + this.contentEl.removeAttribute("hidden"); + this.contentEl.removeAttribute("aria-hidden"); + } + if (container) { + container.hidden = true; + container.setAttribute("aria-hidden", "true"); + container.removeAttribute("aria-labelledby"); + container.removeAttribute("aria-label"); + if (container.parentElement === this.root) { + this.root.removeChild(container); + } + } + } + } + updateModerationAria() { const badgeId = this.moderationBadgeEl ? this.getModerationBadgeId() : ""; const elements = [this.anchorEl, this.titleEl].filter(Boolean); @@ -1388,8 +1642,10 @@ export class VideoCard { } refreshModerationUi() { - this.applyModerationDatasets(); - this.updateModerationBadge(); + const context = this.getModerationContext(); + this.applyModerationDatasets(context); + this.updateModerationBadge(context); + this.updateHiddenState(context); this.updateModerationAria(); } @@ -1837,38 +2093,36 @@ export class VideoCard { updateVideoCardSourceVisibility(this.root); } - applyModerationDatasets() { + applyModerationDatasets(context = this.getModerationContext()) { if (!this.root) { return; } - const moderationContext = this.getModerationContext(); - - if (moderationContext.originalBlockAutoplay && !moderationContext.overrideActive) { + if (context.originalBlockAutoplay && !context.overrideActive) { this.root.dataset.autoplayPolicy = "blocked"; } else if (this.root.dataset.autoplayPolicy) { delete this.root.dataset.autoplayPolicy; } - if (moderationContext.overrideActive) { + if (context.overrideActive) { this.root.dataset.moderationOverride = "show-anyway"; } else if (this.root.dataset.moderationOverride) { delete this.root.dataset.moderationOverride; } if (this.thumbnailEl && !this.shouldMaskNsfwForOwner) { - if (moderationContext.activeBlur) { + if (context.activeBlur) { this.thumbnailEl.dataset.thumbnailState = "blurred"; } else if (this.thumbnailEl.dataset.thumbnailState === "blurred") { delete this.thumbnailEl.dataset.thumbnailState; } } - const reportCount = Math.max(0, Number(moderationContext.trustedCount) || 0); + const reportCount = Math.max(0, Number(context.trustedCount) || 0); if (reportCount > 0) { this.root.dataset.moderationReportCount = String(reportCount); - if (moderationContext.reportType) { - this.root.dataset.moderationReportType = moderationContext.reportType; + if (context.reportType) { + this.root.dataset.moderationReportType = context.reportType; } else if (this.root.dataset.moderationReportType) { delete this.root.dataset.moderationReportType; } @@ -1881,9 +2135,9 @@ export class VideoCard { } } - if (moderationContext.trustedMuted) { + if (context.trustedMuted) { this.root.dataset.moderationTrustedMute = "true"; - const muteCount = Math.max(0, Number(moderationContext.trustedMuteCount) || 0); + const muteCount = Math.max(0, Number(context.trustedMuteCount) || 0); if (muteCount > 0) { this.root.dataset.moderationTrustedMuteCount = String(muteCount); } else if (this.root.dataset.moderationTrustedMuteCount) { @@ -1897,6 +2151,49 @@ export class VideoCard { delete this.root.dataset.moderationTrustedMuteCount; } } + + if (context.activeHidden && !context.overrideActive) { + this.root.dataset.moderationHidden = "true"; + const reason = context.effectiveHideReason || context.hideReason; + if (reason) { + this.root.dataset.moderationHideReason = reason; + } else if (this.root.dataset.moderationHideReason) { + delete this.root.dataset.moderationHideReason; + } + + const counts = context.hideCounts || context.effectiveHideCounts || null; + const muteCount = counts && Number.isFinite(counts.trustedMuteCount) + ? Math.max(0, Number(counts.trustedMuteCount)) + : null; + const reportCountHide = counts && Number.isFinite(counts.trustedReportCount) + ? Math.max(0, Number(counts.trustedReportCount)) + : null; + + if (muteCount !== null) { + this.root.dataset.moderationHideTrustedMuteCount = String(muteCount); + } else if (this.root.dataset.moderationHideTrustedMuteCount) { + delete this.root.dataset.moderationHideTrustedMuteCount; + } + + if (reportCountHide !== null) { + this.root.dataset.moderationHideTrustedReportCount = String(reportCountHide); + } else if (this.root.dataset.moderationHideTrustedReportCount) { + delete this.root.dataset.moderationHideTrustedReportCount; + } + } else { + if (this.root.dataset.moderationHidden) { + delete this.root.dataset.moderationHidden; + } + if (this.root.dataset.moderationHideReason) { + delete this.root.dataset.moderationHideReason; + } + if (this.root.dataset.moderationHideTrustedMuteCount) { + delete this.root.dataset.moderationHideTrustedMuteCount; + } + if (this.root.dataset.moderationHideTrustedReportCount) { + delete this.root.dataset.moderationHideTrustedReportCount; + } + } } applyPlaybackDatasets() { diff --git a/tests/moderation/video-card.test.mjs b/tests/moderation/video-card.test.mjs index 2969cb1d..80f6cf39 100644 --- a/tests/moderation/video-card.test.mjs +++ b/tests/moderation/video-card.test.mjs @@ -137,7 +137,14 @@ test("VideoCard renders moderation badges and respects viewer override", async ( assert.equal(card.thumbnailEl.dataset.thumbnailState, "blurred"); assert.equal(card.getRoot().dataset.moderationReportCount, "3"); assert.ok(card.moderationBadgeEl); - assert.equal(card.moderationBadgeEl.dataset.moderationState, "blocked"); + assert.equal(card.moderationBadgeEl.dataset.moderationState, "hidden"); + assert.equal(card.getRoot().dataset.moderationHidden, "true"); + assert.equal(card.getRoot().dataset.moderationHideReason, "trusted-report-hide"); + assert.equal(card.getRoot().dataset.moderationHideTrustedReportCount, "3"); + assert.ok(card.hiddenSummaryEl); + assert.equal(card.hiddenSummaryEl.parentElement, card.getRoot()); + assert.equal(card.anchorEl.hasAttribute("hidden"), true); + assert.equal(card.contentEl.hasAttribute("hidden"), true); assert.ok(card.moderationActionButton); card.onModerationOverride = ({ video: overrideVideo }) => { @@ -160,5 +167,11 @@ test("VideoCard renders moderation badges and respects viewer override", async ( assert.equal(card.getRoot().dataset.moderationOverride, "show-anyway"); assert.equal(card.thumbnailEl.dataset.thumbnailState, undefined); assert.equal(card.moderationBadgeEl.dataset.moderationState, "override"); + assert.equal(card.getRoot().dataset.moderationHidden, undefined); + assert.equal(card.getRoot().dataset.moderationHideReason, undefined); + assert.equal(card.getRoot().dataset.moderationHideTrustedReportCount, undefined); + assert.equal(card.anchorEl.hasAttribute("hidden"), false); + assert.equal(card.contentEl.hasAttribute("hidden"), false); + assert.ok(!card.hiddenSummaryEl || card.hiddenSummaryEl.parentElement !== card.getRoot()); assert.ok(card.moderationBadgeEl.textContent.includes("Showing despite")); });