diff --git a/components/DropLogo.vue b/components/DropLogo.vue index 7dde7006..383a228a 100644 --- a/components/DropLogo.vue +++ b/components/DropLogo.vue @@ -10,6 +10,16 @@ d="M4 13.5C4 11.0008 5.38798 8.76189 7.00766 7C8.43926 5.44272 10.0519 4.25811 11.0471 3.5959C11.6287 3.20893 12.3713 3.20893 12.9529 3.5959C13.9481 4.25811 15.5607 5.44272 16.9923 7C18.612 8.76189 20 11.0008 20 13.5C20 17.9183 16.4183 21.5 12 21.5C7.58172 21.5 4 17.9183 4 13.5Z" stroke="currentColor" stroke-width="2" + stroke-dasharray="100" + :stroke-dashoffset="dashArray" /> + + diff --git a/components/LogLine.vue b/components/LogLine.vue new file mode 100644 index 00000000..64fbf2fc --- /dev/null +++ b/components/LogLine.vue @@ -0,0 +1,27 @@ + + + diff --git a/components/TaskWidget.vue b/components/TaskWidget.vue new file mode 100644 index 00000000..3738e109 --- /dev/null +++ b/components/TaskWidget.vue @@ -0,0 +1,55 @@ + + + diff --git a/i18n/locales/en_us.json b/i18n/locales/en_us.json index 7cb3bb24..2356acb9 100644 --- a/i18n/locales/en_us.json +++ b/i18n/locales/en_us.json @@ -137,6 +137,10 @@ "usernameTaken": "Username already taken." }, "backHome": "{arrow} Back to home", + "externalUrl": { + "subtitle": "This message is only visible to admins.", + "title": "Accessing over different EXTERNAL_URL. Please check the docs." + }, "game": { "banner": { "description": "Drop failed to update the banner image: {0}", @@ -212,10 +216,6 @@ "desc": "Drop encountered an error while updating the version: {error}", "title": "There an error while updating the version order" } - }, - "externalUrl": { - "title": "Accessing over different EXTERNAL_URL. Please check the docs.", - "subtitle": "This message is only visible to admins." } }, "footer": { @@ -327,6 +327,7 @@ "description": "Companies organize games by who they were developed or published by.", "editor": { "action": "Add Game {plus}", + "descriptionPlaceholder": "{'<'}description{'>'}", "developed": "Developed", "libraryDescription": "Add, remove, or customise what this company has developed and/or published.", "libraryTitle": "Game Library", @@ -334,25 +335,23 @@ "published": "Published", "uploadBanner": "Upload banner", "uploadIcon": "Upload icon", - "descriptionPlaceholder": "{'<'}description{'>'}", "websitePlaceholder": "{'<'}website{'>'}" }, "modals": { + "createDescription": "Create a company to further organize your games.", + "createFieldDescription": "Company Description", + "createFieldDescriptionPlaceholder": "A small indie studio that...", + "createFieldName": "Company Name", + "createFieldNamePlaceholder": "My New Company...", + "createFieldWebsite": "Company Website", + "createFieldWebsitePlaceholder": "https://example.com/", + "createTitle": "Create a company", "nameDescription": "Edit the company's name. Used to match to new game imports.", "nameTitle": "Edit company name", "shortDeckDescription": "Edit the company's description. Doesn't affect long (markdown) description.", "shortDeckTitle": "Edit company description", "websiteDescription": "Edit the company's website. Note: this will be a link, and won't have redirect protection.", - "websiteTitle": "Edit company website", - - "createTitle": "Create a company", - "createDescription": "Create a company to further organize your games.", - "createFieldName": "Company Name", - "createFieldNamePlaceholder": "My New Company...", - "createFieldDescription": "Company Description", - "createFieldDescriptionPlaceholder": "A small indie studio that...", - "createFieldWebsite": "Company Website", - "createFieldWebsitePlaceholder": "https://example.com/" + "websiteTitle": "Edit company website" }, "noCompanies": "No companies", "noGames": "No games", @@ -373,6 +372,8 @@ }, "metadataProvider": "Metadata provider", "noGames": "No games imported", + "libraryHint": "No libraries configured.", + "libraryHintDocsLink": "What does this mean? {arrow}", "offline": "Drop couldn't access this game.", "offlineTitle": "Game offline", "openEditor": "Open in Editor {arrow}", @@ -382,12 +383,15 @@ "create": "Create source", "createDesc": "Drop will use this source to access your game library, and make them available.", "desc": "Configure your library sources, where Drop will look for new games and versions to import.", + "documentationLink": "Documentation {arrow}", "edit": "Edit source", "fsDesc": "Imports games from a path on disk. Requires version-based folder structure, and supports archived games.", "fsFlatDesc": "Imports games from a path on disk, but without a separate version subfolder. Useful when migrating an existing library to Drop.", + "fsFlatTitle": "Compatibility", "fsPath": "Path", "fsPathDesc": "An absolute path to your game library.", "fsPathPlaceholder": "/mnt/games", + "fsTitle": "Drop-style", "link": "Sources {arrow}", "nameDesc": "The name of your source, for reference.", "namePlaceholder": "My New Source", @@ -514,13 +518,13 @@ "images": "Game Images", "lookAt": "Check it out", "noDevelopers": "No developers", - "noGame": "NO GAME", "noFeatured": "NO FEATURED GAMES", - "openFeatured": "Star games in Admin Library {arrow}", + "noGame": "NO GAME", "noImages": "No images", "noPublishers": "No publishers.", "noTags": "No tags", "openAdminDashboard": "Open in Admin Dashboard", + "openFeatured": "Star games in Admin Library {arrow}", "platform": "Platform | Platform | Platforms", "publishers": "Publishers | Publisher | Publishers", "rating": "Rating", @@ -560,7 +564,9 @@ "cleanupSessionsName": "Clean up sessions." }, "viewTask": "View {arrow}", - "weeklyScheduledTitle": "Weekly scheduled tasks" + "weeklyScheduledTitle": "Weekly scheduled tasks", + "progress": "{0}%", + "execute": "{arrow} Execute" } }, "title": "Drop", @@ -585,7 +591,6 @@ "admin": { "adminHeader": "Admin?", "adminUserLabel": "Admin user", - "authLink": "Authentication {arrow}", "authentication": { "configure": "Configure", "description": "Drop supports a variety of \"authentication mechanisms\". As you enable or disable them, they are shown on the sign in screen for users to select from. Click the dot menu to configure the authentication mechanism.", @@ -597,6 +602,7 @@ "srOpenOptions": "Open options", "title": "Authentication" }, + "authLink": "Authentication {arrow}", "authoptionsHeader": "Auth Options", "delete": "Delete", "deleteUser": "Delete user {0}", @@ -609,7 +615,7 @@ "createInvitation": "Create invitation", "description": "Simple authentication uses a system of 'invitations' to create users. You can create an invitation, and optionally specify a username or email for the user, and then it will generate a magic URL that can be used to create an account.", "expires": "Expires: {expiry}", - "invitationTitle": "invitations", + "invitationTitle": "Invitations", "invite3Days": "3 days", "invite6Months": "6 months", "inviteAdminSwitchDescription": "Create this user as an administrator", diff --git a/package.json b/package.json index 3a68d92b..9eb9722c 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "drop", - "version": "0.3.1", + "version": "0.3.2", "private": true, "type": "module", "license": "AGPL-3.0-or-later", @@ -21,7 +21,7 @@ }, "dependencies": { "@discordapp/twemoji": "^16.0.1", - "@drop-oss/droplet": "2.3.0", + "@drop-oss/droplet": "2.3.1", "@headlessui/vue": "^1.7.23", "@heroicons/vue": "^2.1.5", "@lobomfz/prismark": "0.0.3", diff --git a/pages/admin/library/index.vue b/pages/admin/library/index.vue index f1135099..cae78173 100644 --- a/pages/admin/library/index.vue +++ b/pages/admin/library/index.vue @@ -242,11 +242,40 @@ {{ $t("common.noResults") }}

{{ $t("library.admin.noGames") }}

+

+ {{ + $t("library.admin.libraryHint") + }} + + + + + + +

@@ -256,7 +285,11 @@ import { ExclamationTriangleIcon, ExclamationCircleIcon, } from "@heroicons/vue/16/solid"; -import { InformationCircleIcon, StarIcon } from "@heroicons/vue/20/solid"; +import { + ArrowTopRightOnSquareIcon, + InformationCircleIcon, + StarIcon, +} from "@heroicons/vue/20/solid"; import { MagnifyingGlassIcon } from "@heroicons/vue/24/outline"; const { t } = useI18n(); diff --git a/pages/admin/library/sources/index.vue b/pages/admin/library/sources/index.vue index d7b6c14a..77870014 100644 --- a/pages/admin/library/sources/index.vue +++ b/pages/admin/library/sources/index.vue @@ -64,8 +64,14 @@ > {{ source.name }} - - {{ source.backend }} + + + {{ optionsMetadata[source.backend].title }} {{ source }}{{ metadata.title }} + {{ + source + }} + - {{ metadata.description }} + + + + + {{ task.name }} -
+
+ +
+
-
- -
-
{{
-          formatLine(line)
-        }}
+ {{ + $t("tasks.admin.progress", [Math.round(task.progress * 10) / 10]) + }}
@@ -90,11 +97,6 @@ const taskId = route.params.id.toString(); const task = useTask(taskId); -function formatLine(line: string): string { - const res = parseTaskLog(line); - return `[${res.timestamp}] ${res.message}`; -} - definePageMeta({ layout: "admin", }); diff --git a/pages/admin/task/index.vue b/pages/admin/task/index.vue index b9f3f6ce..22068de0 100644 --- a/pages/admin/task/index.vue +++ b/pages/admin/task/index.vue @@ -13,62 +13,7 @@ :key="task.value?.id" class="col-span-1 divide-y divide-gray-200 rounded-lg bg-zinc-800 border border-zinc-700 shadow-sm" > -
-
-
-
- - -
-
-

- {{ task.value.name }} -

-
-

- {{ task.value.id }} -

-
-
-
-

- {{ parseTaskLog(task.value.log.at(-1)).message }} -

- - - - - -
-
-
- -
+
-
-
-
-
- - -
-
-

- {{ task.name }} -

- -
-

- {{ task.id }} -

-

- {{ parseTaskLog(task.log.at(-1)).message }} -

- - - - - -
-
+
@@ -157,6 +58,21 @@

{{ scheduledTasks[task].description }}

+
@@ -180,6 +96,21 @@

{{ scheduledTasks[task].description }}

+
@@ -189,7 +120,7 @@
diff --git a/server/api/v1/admin/library/index.get.ts b/server/api/v1/admin/library/index.get.ts index d0a00473..5df358be 100644 --- a/server/api/v1/admin/library/index.get.ts +++ b/server/api/v1/admin/library/index.get.ts @@ -7,8 +7,9 @@ export default defineEventHandler(async (h3) => { const unimportedGames = await libraryManager.fetchUnimportedGames(); const games = await libraryManager.fetchGamesWithStatus(); + const libraries = await libraryManager.fetchLibraries(); // Fetch other library data here - return { unimportedGames, games }; + return { unimportedGames, games, hasLibraries: libraries.length > 0 }; }); diff --git a/server/api/v1/admin/task/index.get.ts b/server/api/v1/admin/task/index.get.ts index a81492cd..690dce82 100644 --- a/server/api/v1/admin/task/index.get.ts +++ b/server/api/v1/admin/task/index.get.ts @@ -1,5 +1,6 @@ import aclManager from "~/server/internal/acls"; import prisma from "~/server/internal/db/database"; +import type { TaskMessage } from "~/server/internal/tasks"; import taskHandler from "~/server/internal/tasks"; export default defineEventHandler(async (h3) => { @@ -13,7 +14,7 @@ export default defineEventHandler(async (h3) => { }); const runningTasks = (await taskHandler.runningTasks()).map((e) => e.id); - const historicalTasks = await prisma.task.findMany({ + const historicalTasks = (await prisma.task.findMany({ where: { OR: [ { @@ -28,7 +29,7 @@ export default defineEventHandler(async (h3) => { ended: "desc", }, take: 10, - }); + })) as Array; const dailyTasks = await taskHandler.dailyTasks(); const weeklyTasks = await taskHandler.weeklyTasks(); diff --git a/server/api/v1/admin/task/index.post.ts b/server/api/v1/admin/task/index.post.ts new file mode 100644 index 00000000..dc281908 --- /dev/null +++ b/server/api/v1/admin/task/index.post.ts @@ -0,0 +1,31 @@ +import { type } from "arktype"; +import { readDropValidatedBody, throwingArktype } from "~/server/arktype"; +import aclManager from "~/server/internal/acls"; +import taskHandler from "~/server/internal/tasks"; +import type { TaskGroup } from "~/server/internal/tasks/group"; +import { taskGroups } from "~/server/internal/tasks/group"; + +const StartTask = type({ + taskGroup: type("string"), +}).configure(throwingArktype); + +export default defineEventHandler(async (h3) => { + const allowed = await aclManager.allowSystemACL(h3, ["task:start"]); + if (!allowed) throw createError({ statusCode: 403 }); + + const body = await readDropValidatedBody(h3, StartTask); + const taskGroup = body.taskGroup as TaskGroup; + if (!taskGroups[taskGroup]) + throw createError({ + statusCode: 400, + statusMessage: "Invalid task group.", + }); + + const task = await taskHandler.runTaskGroupByName(taskGroup); + if (!task) + throw createError({ + statusCode: 500, + statusMessage: "Could not start task.", + }); + return { id: task }; +}); diff --git a/server/internal/library/index.ts b/server/internal/library/index.ts index ce9f6caf..0a74dfe6 100644 --- a/server/internal/library/index.ts +++ b/server/internal/library/index.ts @@ -116,7 +116,11 @@ class LibraryManager { async fetchGamesWithStatus() { const games = await prisma.game.findMany({ include: { - versions: true, + versions: { + select: { + versionName: true, + }, + }, library: true, }, orderBy: { diff --git a/server/internal/tasks/group.ts b/server/internal/tasks/group.ts index d95db5ed..f914272a 100644 --- a/server/internal/tasks/group.ts +++ b/server/internal/tasks/group.ts @@ -14,6 +14,9 @@ export const taskGroups = { "import:game": { concurrency: true, }, + debug: { + concurrency: true, + }, } as const; export type TaskGroup = keyof typeof taskGroups; diff --git a/server/internal/tasks/index.ts b/server/internal/tasks/index.ts index f6f93fe7..54433a99 100644 --- a/server/internal/tasks/index.ts +++ b/server/internal/tasks/index.ts @@ -53,6 +53,7 @@ class TaskHandler { "cleanup:invitations", "cleanup:sessions", "check:update", + "debug", ]; private weeklyScheduledTasks: TaskGroup[] = ["cleanup:objects"]; @@ -62,6 +63,7 @@ class TaskHandler { this.saveScheduledTask(cleanupSessions); this.saveScheduledTask(checkUpdate); this.saveScheduledTask(cleanupObjects); + //this.saveScheduledTask(debug); } /** @@ -162,6 +164,13 @@ class TaskHandler { // You can configure timestamp, level, etc. here timestamp: pino.stdTimeFunctions.isoTime, base: null, // Remove pid/hostname if not needed + formatters: { + level(label) { + return { + level: label, + }; + }, + }, }, logStream, ); @@ -339,13 +348,15 @@ class TaskHandler { return this.weeklyScheduledTasks; } - runTaskGroupByName(name: TaskGroup) { - const task = this.taskCreators.get(name); - if (!task) { + async runTaskGroupByName(name: TaskGroup) { + const taskConstructor = this.taskCreators.get(name); + if (!taskConstructor) { logger.warn(`No task found for group ${name}`); return; } - this.create(task()); + const task = taskConstructor(); + await this.create(task); + return task.id; } /** @@ -444,7 +455,7 @@ export type TaskMessage = { name: string; success: boolean; progress: number; - error: undefined | { title: string; description: string }; + error: null | undefined | { title: string; description: string }; log: string[]; reset?: boolean; }; @@ -470,6 +481,7 @@ interface DropTask { export const TaskLog = type({ timestamp: "string", message: "string", + level: "string", }); // /** @@ -499,8 +511,6 @@ export const TaskLog = type({ // } export function defineDropTask(buildTask: BuildTask): DropTask { - // TODO: only let one task with the same taskGroup run at the same time if specified - return { taskGroup: buildTask.taskGroup, build: () => ({ diff --git a/server/internal/tasks/registry/debug.ts b/server/internal/tasks/registry/debug.ts new file mode 100644 index 00000000..9cd8a4a2 --- /dev/null +++ b/server/internal/tasks/registry/debug.ts @@ -0,0 +1,18 @@ +import { defineDropTask } from ".."; + +export default defineDropTask({ + buildId: () => `debug:${new Date().toISOString()}`, + name: "Debug Task", + acls: ["system:maintenance:read"], + taskGroup: "debug", + async run({ progress, logger }) { + const amount = 1000; + for (let i = 0; i < amount; i++) { + progress((i / amount) * 100); + logger.info(`dajksdkajd ${i}`); + logger.warn("warning"); + logger.error("error\nmultiline and stuff\nwoah more lines"); + await new Promise((r) => setTimeout(r, 1500)); + } + }, +}); diff --git a/utils/parseTaskLog.ts b/utils/parseTaskLog.ts index 4cc0b4f6..93f1e21f 100644 --- a/utils/parseTaskLog.ts +++ b/utils/parseTaskLog.ts @@ -1,13 +1,31 @@ import type { TaskLog } from "~/server/internal/tasks"; +const labelNumberMap = { + 100: "silent", + 60: "fatal", + 50: "error", + 40: "warn", + 30: "info", + 20: "debug", + 10: "trace", + 0: "off", +}; + export function parseTaskLog( logStr?: string | undefined, ): typeof TaskLog.infer { - if (!logStr) return { message: "", timestamp: "" }; + if (!logStr) return { message: "", timestamp: "", level: "" }; const log = JSON.parse(logStr); + if (typeof log.level === "number") { + log.level = labelNumberMap[ + log.level as keyof typeof labelNumberMap + ] as string; + } + return { message: log.msg, timestamp: log.time, + level: log.level, }; } diff --git a/yarn.lock b/yarn.lock index 7d3f9a90..9aad4fa6 100644 --- a/yarn.lock +++ b/yarn.lock @@ -342,71 +342,71 @@ jsonfile "^5.0.0" universalify "^0.1.2" -"@drop-oss/droplet-darwin-arm64@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-darwin-arm64/-/droplet-darwin-arm64-2.3.0.tgz#f4f0ded9c9f5b5cac25dd56f59817e1c13e865ab" - integrity sha512-5k1VwGZTFc61FvKyL4cvYxFYB7aCY5cWCo0Q7yTkkj+KR+ewH6ucylU8kDG7M+aBLvbC/zbntXUp4RtYZi4AZQ== +"@drop-oss/droplet-darwin-arm64@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-darwin-arm64/-/droplet-darwin-arm64-2.3.1.tgz#ee1c32b4f180fd40bde57b4d428bdf51119cf6c8" + integrity sha512-s0qORIlGTyjnDL2W6Eljoz8yloBXVTpuyiEqnOCVTTtse3uLgqG+78wF2sVhiCKKCNuNwELv5icomJ2k4w2K5w== -"@drop-oss/droplet-darwin-universal@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-darwin-universal/-/droplet-darwin-universal-2.3.0.tgz#1d8659bc2869e5d30308622bcc6cb230030d738e" - integrity sha512-4V/HMnNtmHgn156pTpa3mVTAwTmO9jqtZrDcVko7PdSotEbXiwBpTFzbgb4bPafbPmkSNoRh4G9d3BLQCh4mgw== +"@drop-oss/droplet-darwin-universal@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-darwin-universal/-/droplet-darwin-universal-2.3.1.tgz#c6529184bd959d326c85ed97c7e8d2b07529abbb" + integrity sha512-L1fZjj2LQpLAesNtP3s0PzFPsJ77nVbyXbBeQGaoaq5kF0/npO4NYQ/7flkllGhIlJf/OQENWcARvfablM/G8g== -"@drop-oss/droplet-darwin-x64@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-darwin-x64/-/droplet-darwin-x64-2.3.0.tgz#c7ff5dae8ba520866b7cd49714625ada8fa0a7c2" - integrity sha512-PUcNjE09N7qEFsbssKxL8rjmCt9AUYPz1yK34d8N2W9DboS1KI+PShWdd/NOk4GYzTJQuJhMp8wNcUrljfqXmQ== +"@drop-oss/droplet-darwin-x64@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-darwin-x64/-/droplet-darwin-x64-2.3.1.tgz#711855d85821080ac11e80b81ec91df1eaa23405" + integrity sha512-4UvveQRCq10iEoVfArdCeBuQg51jbn5tkW68LXRoFWzicQz6MFhbowVmzz5RbjYcT5kYwI4c7jBZgeKBGOvc+g== -"@drop-oss/droplet-linux-arm64-gnu@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-arm64-gnu/-/droplet-linux-arm64-gnu-2.3.0.tgz#8819b34c5ff8bd8182c5cd0c3f1784dc2afd9507" - integrity sha512-6VyOwYu9sMrCL82UZOvvjU9G/4wHdA8P6q3+EDIVdABg5jVEYZsxkrT0Kp/5h9Xs0mPFNB/su8ZwB9FRQ63o1w== +"@drop-oss/droplet-linux-arm64-gnu@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-arm64-gnu/-/droplet-linux-arm64-gnu-2.3.1.tgz#f3a3a00239a9063bba1fbcb2209303b337cd862d" + integrity sha512-URlpIZZDG/u2pwxM+PaWK240+Phr4RETzwcUQyERAPv22vTjl4l/s4sYa4o4fHX/eosgNLncO+jYgO0f9FS3kg== -"@drop-oss/droplet-linux-arm64-musl@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-arm64-musl/-/droplet-linux-arm64-musl-2.3.0.tgz#06601aa8af4bffeb26956ff79ed494265e313342" - integrity sha512-2BZreAg1XOBxr+iY2hFcX4x6bFC7AKXkIHa9130rmStH/HxnGq6K5H49eJd6ezzNMH/lQ7Sm7uJP2+sH8mjeCw== +"@drop-oss/droplet-linux-arm64-musl@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-arm64-musl/-/droplet-linux-arm64-musl-2.3.1.tgz#8743132ad2fb050ef5f3cd5ddbe93b1b35ebda73" + integrity sha512-+m5IVmD4J979KggUSpyrE4PD4mjHAnvJ8EY2AOMSxmCu3JmONMIKHNmx1TA/k9PlesGKe6GjAs2WGlxwZRCZ2g== -"@drop-oss/droplet-linux-riscv64-gnu@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-riscv64-gnu/-/droplet-linux-riscv64-gnu-2.3.0.tgz#6d5629631aeeceadb292998e21b6e2b2cf839bdc" - integrity sha512-E7i86Q8IU7rh2FVtXa0NxoGRhB7AZU+AWPumTAuDQS3xPg3sj+c3q/A7YI1Ay4lnvzR/fevP2p/7iSJUEDcchQ== +"@drop-oss/droplet-linux-riscv64-gnu@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-riscv64-gnu/-/droplet-linux-riscv64-gnu-2.3.1.tgz#d7f03d78f107a04f952c8958a024c27df6ad9818" + integrity sha512-AkSbSjt8nvcuxJYBeEvGGh6HaQSPO+OeLYUjc4pBZDACUOULHLWnZ5LdD/GUN97JcZOfq+BYfP50mz/1BvWoSA== -"@drop-oss/droplet-linux-x64-gnu@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-x64-gnu/-/droplet-linux-x64-gnu-2.3.0.tgz#a924aada38dbc54f6967b17435c10bf3b6e6ffb0" - integrity sha512-eIHhhoSgpvMAc9tn/K0ldZRXvDe1Xyd9okSSqaclCEKjdVfWU8UMycUz1SzQH9YefiqEB4Qjd3y1iRgaEa8niA== +"@drop-oss/droplet-linux-x64-gnu@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-x64-gnu/-/droplet-linux-x64-gnu-2.3.1.tgz#7deff7a3de0697de13685c81ec4e9c8e6186ed0a" + integrity sha512-jaswkLtTJ4U5GhyBn+86r7cEf8dnHQmcklxomEA8P/DWTHkab1g23XlgaSGHX/FaiRpKAxXGNLTPyY8lR6wePQ== -"@drop-oss/droplet-linux-x64-musl@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-x64-musl/-/droplet-linux-x64-musl-2.3.0.tgz#4eb71112f7641e1fad3b53f5f8d1b98b9cb84bf0" - integrity sha512-0taR945NvK+xNBicSYriKDJgBxpcozzgcALDp/cX2UaYV9cb5PF/xw80DArCyUDvKOfRzeFALx4KRC2ghPr6tw== +"@drop-oss/droplet-linux-x64-musl@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-linux-x64-musl/-/droplet-linux-x64-musl-2.3.1.tgz#31a2f5107817a59ff5a516cd1912261c85b2e0c7" + integrity sha512-xn+W31FOnPVvkoxks104QusnHS1/J0V4Lwzegu3hPjPpZnc0YqFEo74pcxb2VfltgjMTtBOmzyKaApt9Snhd8Q== -"@drop-oss/droplet-win32-arm64-msvc@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-win32-arm64-msvc/-/droplet-win32-arm64-msvc-2.3.0.tgz#36568f87024eb48ce7e82d76ea83a2c6ec25a856" - integrity sha512-5HkO98h/PboM+/wPulKVGFTklijlqht8w13iW1ipUcRFsOHmS1o8nejjLL7KEr2X8G4JwYOqBeX8tY3OhaU9bw== +"@drop-oss/droplet-win32-arm64-msvc@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-win32-arm64-msvc/-/droplet-win32-arm64-msvc-2.3.1.tgz#4cf431b654b33c58df4cef256e84881b0556a046" + integrity sha512-MwDz/4SfFSCEYzGCsptVD38amB18c2MSheJM+mV7Y8qjVDfjzAGrdX9923e8BYIm8eY8ypnOQBTy4/qae8+3uw== -"@drop-oss/droplet-win32-x64-msvc@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet-win32-x64-msvc/-/droplet-win32-x64-msvc-2.3.0.tgz#e794ea7cfdc0ea148707e4f3e60f2aa547328c03" - integrity sha512-6lNXOMyy9sPaO4wbklOIr2jbuvZHIVrd+dXu2UOI2YqFlHdxiDD1sZnqSZmlfCP58yeA+SpTfhxDHwUHJTFI/g== +"@drop-oss/droplet-win32-x64-msvc@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet-win32-x64-msvc/-/droplet-win32-x64-msvc-2.3.1.tgz#01b33c5241cca9aa026605cbb18027d82f57cc6f" + integrity sha512-5FRfblFZBI9jpLNS0z+QSqYzxpDg3YSTP/2LvEqI2Z7ZYC02j4SKnW/+C4zzblNuR3e/igfaP0I9yBv4uIb6ew== -"@drop-oss/droplet@2.3.0": - version "2.3.0" - resolved "https://registry.yarnpkg.com/@drop-oss/droplet/-/droplet-2.3.0.tgz#eb2891346cf7fadcc847d5dee37674fc1106d2fc" - integrity sha512-ffEoS3LYBfPm0++p7f7F/NkYH5PfauQzuj1gTz7qVWZOSP5VQWYhOc9BEg0fsCCzTB/mct0jwOsK92URmthpxA== +"@drop-oss/droplet@2.3.1": + version "2.3.1" + resolved "https://registry.yarnpkg.com/@drop-oss/droplet/-/droplet-2.3.1.tgz#664e42bf0b205ffa06f5d5f48f0080012145d8c2" + integrity sha512-oar7wvwMC1Evau4lXYcGerFcK/HqTi2Fn/4mcBldIF7B33NhsXhg4RncSNGS5J0WfwG4rkbI249nbs4aDeIrFg== optionalDependencies: - "@drop-oss/droplet-darwin-arm64" "2.3.0" - "@drop-oss/droplet-darwin-universal" "2.3.0" - "@drop-oss/droplet-darwin-x64" "2.3.0" - "@drop-oss/droplet-linux-arm64-gnu" "2.3.0" - "@drop-oss/droplet-linux-arm64-musl" "2.3.0" - "@drop-oss/droplet-linux-riscv64-gnu" "2.3.0" - "@drop-oss/droplet-linux-x64-gnu" "2.3.0" - "@drop-oss/droplet-linux-x64-musl" "2.3.0" - "@drop-oss/droplet-win32-arm64-msvc" "2.3.0" - "@drop-oss/droplet-win32-x64-msvc" "2.3.0" + "@drop-oss/droplet-darwin-arm64" "2.3.1" + "@drop-oss/droplet-darwin-universal" "2.3.1" + "@drop-oss/droplet-darwin-x64" "2.3.1" + "@drop-oss/droplet-linux-arm64-gnu" "2.3.1" + "@drop-oss/droplet-linux-arm64-musl" "2.3.1" + "@drop-oss/droplet-linux-riscv64-gnu" "2.3.1" + "@drop-oss/droplet-linux-x64-gnu" "2.3.1" + "@drop-oss/droplet-linux-x64-musl" "2.3.1" + "@drop-oss/droplet-win32-arm64-msvc" "2.3.1" + "@drop-oss/droplet-win32-x64-msvc" "2.3.1" "@emnapi/core@^1.4.3": version "1.4.5"