convert api

This commit is contained in:
thororen1234 2025-11-27 20:14:05 -05:00
parent 0b23e7c802
commit 8f8b8e2633
No known key found for this signature in database
14 changed files with 113 additions and 45 deletions

37
i18n/en/api.json Normal file
View file

@ -0,0 +1,37 @@
{
"commands": {
"errorExecuting": "An Error occurred while executing command \"{name}\""
},
"notifications": {
"dismissNotification": "Dismiss Notification",
"noNotifications": "No notifications yet",
"notificationLog": "Notification Log",
"notificationSettings": "Notification Settings",
"logs": {
"title": "Are you sure?",
"body_zero": "No notification selected.",
"body_one": "This will permanently remove {count} notification. This action cannot be undone.",
"body_other": "This will permanently remove {count} notifications. This action cannot be undone.",
"confirm": "Do it!",
"cancel": "Nevermind",
"clearNotificationLog": "Clear Notification Log"
},
"missedNotifications": {
"title": "While you were away",
"body_one": "{count} notification received",
"body_other": "{count} notifications received"
}
},
"memberListDecorators": {
"fallback": "Failed to render {key} Member List Decorator"
},
"messageAccessories": {
"fallback": "Failed to render {key} Message Accessory"
},
"messageDecorations": {
"fallback": "Failed to render {key} Message Decoration"
},
"notices": {
"fallback": "Error Showing Notice"
}
}

View file

@ -25,13 +25,35 @@
"cloud": {
"integrations": {
"header": "Cloud Integrations",
"reauthenticateOtherClient": "We've noticed you have cloud integrations enabled in another client! Due to limitations, you will need to re-authenticate to continue using them. Click here to go to the settings page to do so!"
"reauthenticateOtherClient": "We've noticed you have cloud integrations enabled in another client! Due to limitations, you will need to re-authenticate to continue using them. Click here to go to the settings page to do so!",
"failedToRetrieveOAuth": "Setup failed (couldn't retrieve OAuth configuration).",
"enabled": "Cloud integrations enabled!",
"noSecret": "Setup failed (no secret returned?).",
"error": "Setup failed ({e})"
},
"settings": {
"header": "Cloud Settings",
"updatedRemote": "Your settings have been updated! Click here to restart to fully apply changes!"
"updatedRemote": "Your settings have been updated! Click here to restart to fully apply changes!",
"apiReject": "Could not synchronize settings to cloud (API returned {e}).",
"success": "Synchronized settings to the cloud!",
"failedToSync": "Could not synchronize settings to the cloud ({e}).",
"accountChanged": "Cloud sync was disabled because this account isn't connected to the cloud App. You can enable it again by connecting this account in Cloud Settings. (note: it will store your preferences separately)",
"noSettings": "There are no settings in the cloud.",
"upToDate": "Your settings are up to date.",
"newerThanCloud": "Your local settings are newer than the cloud ones.",
"updated": "Your settings have been updated! Click here to restart to fully apply changes!",
"syncFromCloud": "Could not synchronize settings from the cloud ({e}).",
"apiDelete": "Could not delete settings (API returned {e}).",
"deleted": "Settings deleted from cloud!",
"failedToDelete": "Could not delete settings ({e}).",
"apiEraseAll": "Could not erase all data (API returned {e}), please contact support.",
"erased": "Successfully erased all data."
}
},
"settingsSync": {
"imported": "Settings successfully imported. Restart to apply changes!",
"failedToImport": "Failed to import settings: {e}"
},
"contributorCard": {
"contributionsButton": "See what you've contributed to",
"description": "Since you've contributed to Equicord you now have a cool new badge!",
@ -42,7 +64,7 @@
"donated": {
"vencordDescription": "All Vencord users can see your badge! You can manage your perks by messaging @{v}.",
"equicordDescription": "All Equicord users can see your badge! You can manage your perks by making a ticket in Equicord's server.",
"description": "All Vencord users can see your Vencord donor badge, and Equicord users can see your Equicord donor badge. To change your Vencord donor badge, contact @vending.machine. For your Equicord donor badge, make a ticket in Equicord's server..",
"description": "All Vencord users can see your Vencord donor badge, and Equicord users can see your Equicord donor badge. To change your Vencord donor badge, contact @vending.machine. For your Equicord donor badge, make a ticket in Equicord's server.",
"subtitle": "Thank you for donating!",
"title": "Donations"
},

View file

@ -18,6 +18,7 @@
import { Logger } from "@utils/Logger";
import { makeCodeblock } from "@utils/text";
import { t } from "@utils/translation";
import { CommandArgument, CommandContext, CommandOption } from "@vencord/discord-types";
import { sendBotMessage } from "./commandHelpers";
@ -68,7 +69,7 @@ export const _handleCommand = function (cmd: VencordCommand, args: CommandArgume
const handleError = (err: any) => {
// TODO: cancel send if cmd.inputType === BUILT_IN_TEXT
const msg = `An Error occurred while executing command "${cmd.name}"`;
const msg = t("api.commands.errorExecuting", { name: cmd.name });
const reason = err instanceof Error ? err.stack || err.message : String(err);
console.error(msg, err);

View file

@ -17,6 +17,7 @@
*/
import ErrorBoundary from "@components/ErrorBoundary";
import { t } from "@utils/translation";
import { Channel, User } from "@vencord/discord-types";
import { JSX } from "react";
@ -50,7 +51,7 @@ export function __getDecorators(props: DecoratorProps, type: "guild" | "dm"): JS
return null;
return (
<ErrorBoundary noop key={key} message={`Failed to render ${key} Member List Decorator`}>
<ErrorBoundary noop key={key} message={t("api.memberListDecorators.fallback", { key: key })}>
<Decorator {...props} type={type} />
</ErrorBoundary>
);

View file

@ -17,6 +17,7 @@
*/
import ErrorBoundary from "@components/ErrorBoundary";
import { t } from "@utils/translation";
import { JSX, ReactNode } from "react";
export type MessageAccessoryFactory = (props: Record<string, any>) => ReactNode;
@ -48,7 +49,7 @@ export function _modifyAccessories(
) {
for (const [key, accessory] of accessories.entries()) {
const res = (
<ErrorBoundary noop message={`Failed to render ${key} Message Accessory`} key={key}>
<ErrorBoundary noop message={t("api.messageAccessories.fallback", { key: key })} key={key}>
<accessory.render {...props} />
</ErrorBoundary>
);

View file

@ -17,6 +17,7 @@
*/
import ErrorBoundary from "@components/ErrorBoundary";
import { t } from "@utils/translation";
import { Channel, Message } from "@vencord/discord-types";
import { JSX } from "react";
@ -62,7 +63,7 @@ export function __addDecorationsToMessage(props: MessageDecorationProps): JSX.El
const decorations = Array.from(
decorationsFactories.entries(),
([key, Decoration]) => (
<ErrorBoundary noop message={`Failed to render ${key} Message Decoration`} key={key}>
<ErrorBoundary noop message={t("api.messageDecorations.fallback", { key: key })} key={key}>
<Decoration {...props} />
</ErrorBoundary>
)

View file

@ -18,6 +18,7 @@
import ErrorBoundary from "@components/ErrorBoundary";
import { isPrimitiveReactNode } from "@utils/react";
import { t } from "@utils/translation";
import { waitFor } from "@webpack";
import { ReactNode } from "react";
@ -42,7 +43,7 @@ export function nextNotice() {
export function showNotice(message: ReactNode, buttonText: string, onOkClick: () => void) {
const notice = isPrimitiveReactNode(message)
? message
: <ErrorBoundary fallback={() => "Error Showing Notice"}>{message}</ErrorBoundary>;
: <ErrorBoundary fallback={() => t("api.notices.fallback")}>{message}</ErrorBoundary>;
noticesQueue.push(["GENERIC", notice, buttonText, onOkClick]);
if (!currentNotice) nextNotice();

View file

@ -21,6 +21,7 @@ import "./styles.css";
import { useSettings } from "@api/Settings";
import ErrorBoundary from "@components/ErrorBoundary";
import { classes } from "@utils/misc";
import { t } from "@utils/translation";
import { React, useEffect, useRef, useState } from "@webpack/common";
import { NotificationData } from "./Notifications";
@ -111,7 +112,7 @@ export default ErrorBoundary.wrap(function NotificationComponent({
role="img"
aria-labelledby="vc-notification-dismiss-title"
>
<title id="vc-notification-dismiss-title">Dismiss Notification</title>
<title id="vc-notification-dismiss-title">{t("api.notifications.dismissNotification")}</title>
<path fill="currentColor" d="M18.4 4L12 10.4L5.6 4L4 5.6L10.4 12L4 18.4L5.6 20L12 13.6L18.4 20L20 18.4L13.6 12L20 5.6L18.4 4Z" />
</svg>
</button>

View file

@ -18,6 +18,7 @@
import { Settings } from "@api/Settings";
import { Queue } from "@utils/Queue";
import { t } from "@utils/translation";
import { createRoot, WindowStore } from "@webpack/common";
import type { ReactNode } from "react";
import type { Root } from "react-dom/client";
@ -36,8 +37,8 @@ window.addEventListener("focus", () => {
if (!missed) return;
if (missedCount > 0 && timeout > 0 && useNative === "never") {
showNotification({
title: "While you were away",
body: `${missedCount} notifications received`,
title: t("api.notifications.missedNotifications.title"),
body: t("api.notifications.missedNotifications.body", { count: missedCount }),
onClick: () => openNotificationLogModal(),
});
missedCount = 0;

View file

@ -25,6 +25,7 @@ import { Paragraph } from "@components/Paragraph";
import { openNotificationSettingsModal } from "@components/settings/tabs/vencord/NotificationSettings";
import { closeModal, ModalCloseButton, ModalFooter, ModalHeader, ModalProps, ModalRoot, ModalSize, openModal } from "@utils/modal";
import { useAwaiter } from "@utils/react";
import { t } from "@utils/translation";
import { Alerts, Button, ListScrollerThin, React, Timestamp, useEffect, useReducer, useState } from "@webpack/common";
import { nanoid } from "nanoid";
import type { DispatchWithoutAction } from "react";
@ -135,7 +136,7 @@ export function NotificationLog({ log, pending }: { log: PersistentNotificationD
<div className={cl("container")}>
<div className={cl("empty")} />
<Paragraph style={{ textAlign: "center" }}>
No notifications yet
{t("api.notifications.noNotifications")}
</Paragraph>
</div>
);
@ -158,7 +159,7 @@ function LogModal({ modalProps, close }: { modalProps: ModalProps; close(): void
return (
<ModalRoot {...modalProps} size={ModalSize.LARGE} className={cl("modal")}>
<ModalHeader>
<BaseText size="lg" weight="semibold" style={{ flexGrow: 1 }}>Notification Log</BaseText>
<BaseText size="lg" weight="semibold" style={{ flexGrow: 1 }}>{t("api.notifications.notificationLog")}</BaseText>
<ModalCloseButton onClick={close} />
</ModalHeader>
@ -169,7 +170,7 @@ function LogModal({ modalProps, close }: { modalProps: ModalProps; close(): void
<ModalFooter>
<Flex>
<Button onClick={openNotificationSettingsModal}>
Notification Settings
{t("api.notifications.notificationSettings")}
</Button>
<Button
@ -177,19 +178,19 @@ function LogModal({ modalProps, close }: { modalProps: ModalProps; close(): void
color={Button.Colors.RED}
onClick={() => {
Alerts.show({
title: "Are you sure?",
body: `This will permanently remove ${log.length} notification${log.length === 1 ? "" : "s"}. This action cannot be undone.`,
title: t("api.notifications.logs.title"),
body: t("api.notifications.logs.body", { count: log.length }),
async onConfirm() {
await DataStore.set(KEY, []);
signals.forEach(x => x());
},
confirmText: "Do it!",
confirmText: t("api.notifications.logs.confirm"),
confirmColor: "vc-notification-log-danger-btn",
cancelText: "Nevermind"
cancelText: t("api.notifications.cancel")
});
}}
>
Clear Notification Log
{t("api.notifications.clearNotificationLog")}
</Button>
</Flex>
</ModalFooter>

View file

@ -147,7 +147,6 @@ export function subscribePluginFluxEvents(p: Plugin, fluxDispatcher: typeof Flux
logger.debug("Subscribing to flux events of plugin", p.name);
for (const [event, handler] of Object.entries(p.flux)) {
const wrappedHandler = p.flux[event] = function () {
if (p.name === "Encryptcord" && event === "MESSAGE_CREATE") return;
try {
const res = handler!.apply(p, arguments as any);
return res instanceof Promise

View file

@ -9,6 +9,7 @@ import { showNotification } from "@api/Notifications";
import { Settings } from "@api/Settings";
import { Logger } from "@utils/Logger";
import { openModal } from "@utils/modal";
import { t } from "@utils/translation";
import { OAuth2AuthorizeModal, UserStore } from "@webpack/common";
export const logger = new Logger("SettingsSync:CloudSetup", "#39b7e0");
@ -71,8 +72,8 @@ export async function authorizeCloud() {
var { clientId, redirectUri } = await oauthConfiguration.json();
} catch {
showNotification({
title: "Cloud Integration",
body: "Setup failed (couldn't retrieve OAuth configuration)."
title: t("vencord.cloud.integrations.header"),
body: t("vencord.cloud.integrations.failedToRetrieveOAuth")
});
Settings.cloud.authenticated = false;
return;
@ -101,22 +102,22 @@ export async function authorizeCloud() {
logger.info("Authorized with secret");
await setAuthorization(secret);
showNotification({
title: "Cloud Integration",
body: "Cloud integrations enabled!"
title: t("vencord.cloud.integrations.header"),
body: t("vencord.cloud.integrations.enabled")
});
Settings.cloud.authenticated = true;
} else {
showNotification({
title: "Cloud Integration",
body: "Setup failed (no secret returned?)."
title: t("vencord.cloud.integrations.header"),
body: t("vencord.cloud.integrations.noSecret")
});
Settings.cloud.authenticated = false;
}
} catch (e: any) {
logger.error("Failed to authorize", e);
showNotification({
title: "Cloud Integration",
body: `Setup failed (${e.toString()}).`
title: t("vencord.cloud.integrations.header"),
body: t("vencord.cloud.integrations.error", { e: e.toString() })
});
Settings.cloud.authenticated = false;
}

View file

@ -34,7 +34,7 @@ export async function putCloudSettings(manual?: boolean) {
logger.error(`Failed to sync up, API returned ${res.status}`);
showNotification({
title: t("vencord.cloud.settings.header"),
body: `Could not synchronize settings to cloud (API returned ${res.status}).`,
body: t("vencord.cloud.settings.apiReject", { e: res.status }),
color: "var(--red-360)"
});
return;
@ -49,7 +49,7 @@ export async function putCloudSettings(manual?: boolean) {
if (manual) {
showNotification({
title: t("vencord.cloud.settings.header"),
body: "Synchronized settings to the cloud!",
body: t("vencord.cloud.settings.success"),
noPersist: true,
});
}
@ -57,7 +57,7 @@ export async function putCloudSettings(manual?: boolean) {
logger.error("Failed to sync up", e);
showNotification({
title: t("vencord.cloud.settings.header"),
body: `Could not synchronize settings to the cloud (${e.toString()}).`,
body: t("vencord.cloud.settings.faildToSync", { e: e.toString() }),
color: "var(--red-360)"
});
}
@ -78,7 +78,7 @@ export async function getCloudSettings(shouldNotify = true, force = false) {
// User switched to an account that isn't connected to cloud
showNotification({
title: t("vencord.cloud.settings.header"),
body: "Cloud sync was disabled because this account isn't connected to the cloud App. You can enable it again by connecting this account in Cloud Settings. (note: it will store your preferences separately)",
body: t("vencord.cloud.settings.accountChanged"),
color: "var(--yellow-360)",
onClick: () => SettingsRouter.open("VencordCloud")
});
@ -92,7 +92,7 @@ export async function getCloudSettings(shouldNotify = true, force = false) {
if (shouldNotify)
showNotification({
title: t("vencord.cloud.settings.header"),
body: "There are no settings in the cloud.",
body: t("vencord.cloud.settings.noSettings"),
noPersist: true
});
return false;
@ -103,7 +103,7 @@ export async function getCloudSettings(shouldNotify = true, force = false) {
if (shouldNotify)
showNotification({
title: t("vencord.cloud.settings.header"),
body: "Your settings are up to date.",
body: t("vencord.cloud.settings.upToDate"),
noPersist: true
});
return false;
@ -113,7 +113,7 @@ export async function getCloudSettings(shouldNotify = true, force = false) {
logger.error(`Failed to sync down, API returned ${res.status}`);
showNotification({
title: t("vencord.cloud.settings.header"),
body: `Could not synchronize settings from the cloud (API returned ${res.status}).`,
body: t("vencord.cloud.settings.apiReject", { e: res.status }),
color: "var(--red-360)"
});
return false;
@ -127,7 +127,7 @@ export async function getCloudSettings(shouldNotify = true, force = false) {
if (shouldNotify)
showNotification({
title: t("vencord.cloud.settings.header"),
body: "Your local settings are newer than the cloud ones.",
body: t("vencord.cloud.settings.newerThanCloud"),
noPersist: true,
});
return;
@ -146,7 +146,7 @@ export async function getCloudSettings(shouldNotify = true, force = false) {
if (shouldNotify)
showNotification({
title: t("vencord.cloud.settings.header"),
body: "Your settings have been updated! Click here to restart to fully apply changes!",
body: t("vencord.cloud.settings.updated"),
color: "var(--green-360)",
onClick: IS_WEB ? () => location.reload() : relaunch,
noPersist: true
@ -157,7 +157,7 @@ export async function getCloudSettings(shouldNotify = true, force = false) {
logger.error("Failed to sync down", e);
showNotification({
title: t("vencord.cloud.settings.header"),
body: `Could not synchronize settings from the cloud (${e.toString()}).`,
body: t("vencord.cloud.settings.syncFromCloud", { e: e.toString() }),
color: "var(--red-360)"
});
@ -176,7 +176,7 @@ export async function deleteCloudSettings() {
logger.error(`Failed to delete, API returned ${res.status}`);
showNotification({
title: t("vencord.cloud.settings.header"),
body: `Could not delete settings (API returned ${res.status}).`,
body: t("vencord.cloud.settings.apiDelete", { e: res.status }),
color: "var(--red-360)"
});
return;
@ -185,14 +185,14 @@ export async function deleteCloudSettings() {
logger.info("Settings deleted from cloud successfully");
showNotification({
title: t("vencord.cloud.settings.header"),
body: "Settings deleted from cloud!",
body: t("vencord.cloud.settings.deleted"),
color: "var(--green-360)"
});
} catch (e: any) {
logger.error("Failed to delete", e);
showNotification({
title: t("vencord.cloud.settings.header"),
body: `Could not delete settings (${e.toString()}).`,
body: t("vencord.cloud.settings.failedToDelete", { e: e.toString() }),
color: "var(--red-360)"
});
}
@ -208,7 +208,7 @@ export async function eraseAllCloudData() {
logger.error(`Failed to erase data, API returned ${res.status}`);
showNotification({
title: t("vencord.cloud.integrations.header"),
body: `Could not erase all data (API returned ${res.status}), please contact support.`,
body: t("vencord.cloud.settings.apiEraseAll", { e: res.status }),
color: "var(--red-360)"
});
return;
@ -219,7 +219,7 @@ export async function eraseAllCloudData() {
showNotification({
title: t("vencord.cloud.integrations.header"),
body: "Successfully erased all data.",
body: t("vencord.cloud.settings.erased"),
color: "var(--green-360)"
});
}

View file

@ -6,6 +6,7 @@
import { PlainSettings } from "@api/Settings";
import { Logger } from "@utils/Logger";
import { t } from "@utils/translation";
import { chooseFile, saveFile } from "@utils/web";
import { moment, Toasts } from "@webpack/common";
@ -19,10 +20,10 @@ const toast = (type: string, message: string) =>
});
const toastSuccess = () =>
toast(Toasts.Type.SUCCESS, "Settings successfully imported. Restart to apply changes!");
toast(Toasts.Type.SUCCESS, t("vencord.settingsSync.imported"));
const toastFailure = (err: any) =>
toast(Toasts.Type.FAILURE, `Failed to import settings: ${String(err)}`);
toast(Toasts.Type.FAILURE, t("vencord.settingsSync.failedToImport", { e: String(err) }));
const logger = new Logger("SettingsSync:Offline", "#39b7e0");