fix(sse): retire Microsoft Designer Web runtime (#11720)

Merged via /merge-batch (v3.8.51 provenance sweep). Boarded and validated together with the batch's other retirement PRs in a combined worktree — full gate suite green. This PR's own conflicts (against #11711's EdgeTTS retirement, both touching test-masking-allowlist.json and the "Image / video / audio generation" README bullet) were reconciled additively/subtractively (both retirements now correctly reflected), re-validated with this PR's own 62 focused tests, and pushed before merge. Thank you.
This commit is contained in:
Diego Rodrigues de Sa e Souza
2026-08-28 04:49:02 -03:00
committed by GitHub
parent dd8575eb2c
commit 890cbfbfde
47 changed files with 1032 additions and 1238 deletions

View File

@@ -0,0 +1,33 @@
export const RETIRED_MICROSOFT_DESIGNER_WEB_PROVIDER_IDS: ReadonlySet<string> = new Set([
"microsoft-designer-web",
"msdesigner",
]);
export const MICROSOFT_DESIGNER_WEB_RETIRED_MESSAGE =
"Provider has been retired from OmniRoute runtime.";
function normalizeProviderId(providerId: unknown): string {
return typeof providerId === "string" ? providerId.trim().toLowerCase() : "";
}
export function isMicrosoftDesignerWebRetiredProviderId(providerId: unknown): boolean {
return RETIRED_MICROSOFT_DESIGNER_WEB_PROVIDER_IDS.has(normalizeProviderId(providerId));
}
export function assertMicrosoftDesignerWebProviderAvailable(providerId: unknown): void {
if (!isMicrosoftDesignerWebRetiredProviderId(providerId)) return;
const error = new Error(MICROSOFT_DESIGNER_WEB_RETIRED_MESSAGE);
(error as Error & { status?: number }).status = 410;
throw error;
}
export function isMicrosoftDesignerWebProviderRetiredError(
error: unknown
): error is Error & { status: 410 } {
return (
error instanceof Error &&
(error as Error & { status?: number }).status === 410 &&
error.message === MICROSOFT_DESIGNER_WEB_RETIRED_MESSAGE
);
}

View File

@@ -156,19 +156,6 @@ export const WEB_COOKIE_PROVIDERS = {
subscriptionRisk: true,
riskNoticeVariant: "webCookie",
},
"microsoft-designer-web": {
id: "microsoft-designer-web",
alias: "msdesigner",
name: "Microsoft Designer (Image Generation)",
icon: "auto_awesome",
color: "#0078D4",
textIcon: "MSD",
website: "https://designer.microsoft.com",
authHint:
"Sign in at designer.microsoft.com, then open DevTools → Network, generate an image, and find the request to DallE.ashx?action=GetDallEImagesCogSci. Copy the value of its Authorization: Bearer header (the access_token — no 'Bearer ' prefix). The token is short-lived; this is an unofficial, reverse-engineered integration.",
subscriptionRisk: true,
riskNoticeVariant: "webCookie",
},
"t3-web": {
id: "t3-web",
alias: "t3chat",

View File

@@ -11,15 +11,21 @@
// provider (tokenrouter bug: "No active credentials for provider:
// tokenrouter" despite a fully configured compatible node).
//
// Semantics (mirror the original inline runtime guard exactly):
// - REGISTRY entry ids + aliases only. Manual alias ids outside REGISTRY
// (xiaomi/llamacpp/aq) do NOT intercept nodes at runtime and are therefore
// deliberately NOT reserved — including them would cause false-positive
// rejections.
// - Case-sensitive: mixed-case input like "TokenRouter" does not collide with
// the runtime lookup (`Set.has` is exact-match), so it stays allowed.
// Semantics:
// - Live REGISTRY entry ids + aliases, plus exact retired provider ids that
// must remain unavailable after their registry entries are removed. Manual
// aliases outside REGISTRY (xiaomi/llamacpp/aq) do NOT intercept nodes at
// runtime and are therefore deliberately NOT reserved — including them would
// cause false-positive rejections.
// - Live REGISTRY entries remain case-sensitive. Retired ids use their retirement
// normalizer (trim + lowercase), so casing cannot revive a removed provider.
import { REGISTRY } from "@omniroute/open-sse/config/providerRegistry.ts";
import {
isMicrosoftDesignerWebRetiredProviderId,
RETIRED_MICROSOFT_DESIGNER_WEB_PROVIDER_IDS,
} from "@/shared/constants/designerWebRetirement";
let _reserved: Set<string> | null = null;
function buildReservedProviderPrefixes(): Set<string> {
@@ -29,13 +35,16 @@ function buildReservedProviderPrefixes(): Set<string> {
if (entry?.id) reserved.add(entry.id);
if (entry?.alias) reserved.add(entry.alias);
}
for (const providerId of RETIRED_MICROSOFT_DESIGNER_WEB_PROVIDER_IDS) {
reserved.add(providerId);
}
_reserved = reserved;
return reserved;
}
/**
* All reserved provider prefixes (REGISTRY ids + aliases). Built lazily so the
* registry is only walked once per process.
* All canonical reserved provider prefixes (REGISTRY ids + aliases + retired ids).
* Built lazily so the registry is only walked once per process.
*/
export function getReservedProviderPrefixes(): ReadonlySet<string> {
return buildReservedProviderPrefixes();
@@ -58,7 +67,10 @@ export const RESERVED_PROVIDER_PREFIXES: ReadonlySet<string> = getReservedProvid
* reserved (mirrors the runtime guard's typeof check).
*/
export function isReservedProviderPrefix(value: unknown): boolean {
return typeof value === "string" && buildReservedProviderPrefixes().has(value);
return (
(typeof value === "string" && buildReservedProviderPrefixes().has(value)) ||
isMicrosoftDesignerWebRetiredProviderId(value)
);
}
/**

View File

@@ -163,13 +163,6 @@ export const WEB_SESSION_CREDENTIAL_REQUIREMENTS = {
acceptsFullCookieHeader: false,
storageKeys: ["token", "access_token", "accessToken"],
},
"microsoft-designer-web": {
kind: "token",
credentialName: "access_token",
placeholder: "access_token=... (Authorization: Bearer header from the DallE.ashx request)",
acceptsFullCookieHeader: false,
storageKeys: ["token", "access_token", "accessToken"],
},
"copilot-m365-web": {
kind: "token",
credentialName: "access_token + chathubPath",