Compare commits
21 Commits
alex/auth-
...
cal/dev-76
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
cf309fd641 | ||
|
|
ced073d26c | ||
|
|
cc34e69524 | ||
|
|
d4864deac5 | ||
|
|
125207880d | ||
|
|
a8f17f40f5 | ||
|
|
dbde3c4669 | ||
|
|
ba4fecb0cb | ||
|
|
ef04dcc37b | ||
|
|
65126b3a23 | ||
|
|
58495e6276 | ||
|
|
706976439d | ||
|
|
0a9ffd3dc8 | ||
|
|
fb30c0ba2b | ||
|
|
97e4d8e132 | ||
|
|
5bdff3929b | ||
|
|
a08562bfe2 | ||
|
|
2b4319ea55 | ||
|
|
c32405720d | ||
|
|
b9ba3cd3e8 | ||
|
|
31381c860b |
25
.github/CODEOWNERS
vendored
Normal file
25
.github/CODEOWNERS
vendored
Normal file
@@ -0,0 +1,25 @@
|
||||
/apps/frontend/ @modrinth/frontend
|
||||
/apps/app-frontend/ @modrinth/frontend
|
||||
/apps/daedalus_client/ @modrinth/backend
|
||||
/apps/docs/ @modrinth/support @modrinth/platform @modrinth/servers
|
||||
/apps/labrinth @modrinth/backend
|
||||
/apps/app @modrinth/backend
|
||||
|
||||
/packages/app-lib/ @modrinth/backend
|
||||
/packages/ariadne/ @modrinth/backend
|
||||
/packages/assets/ @modrinth/frontend
|
||||
/packages/daedalus/ @modrinth/backend
|
||||
/packages/eslint-config-custom/ @modrinth/frontend
|
||||
/packages/tsconfig/ @modrinth/frontend
|
||||
/packages/ui/ @modrinth/frontend
|
||||
/packages/utils/ @modrinth/frontend
|
||||
|
||||
README.md @modrinth/support
|
||||
|
||||
LICENSE @Geometrically @Prospector
|
||||
/COPYING.md @Geometrically @Prospector
|
||||
/apps/frontend/src/pages/legal/ @Geometrically @Prospector
|
||||
|
||||
/.github/ @Geometrically @Prospector
|
||||
|
||||
/docker-compose.yml @modrinth/backend
|
||||
@@ -16,7 +16,7 @@ serde_json.workspace = true
|
||||
serde = { workspace = true, features = ["derive"] }
|
||||
serde_with.workspace = true
|
||||
|
||||
tauri = { workspace = true, features = ["devtools", "macos-private-api", "protocol-asset", "unstable"] }
|
||||
tauri = { workspace = true, features = ["devtools", "macos-private-api", "protocol-asset"] }
|
||||
tauri-plugin-window-state.workspace = true
|
||||
tauri-plugin-deep-link.workspace = true
|
||||
tauri-plugin-os.workspace = true
|
||||
|
||||
@@ -85,11 +85,10 @@ During development, you might notice that changes made directly to entities in t
|
||||
|
||||
#### CDN options
|
||||
|
||||
`STORAGE_BACKEND`: Controls what storage backend is used. This can be either `local`, `backblaze`, or `s3`, but defaults to `local`
|
||||
`STORAGE_BACKEND`: Controls what storage backend is used. This can be either `local` or `s3`, but defaults to `local`
|
||||
|
||||
The Backblaze and S3 configuration options are fairly self-explanatory in name, so here's simply their names:
|
||||
`BACKBLAZE_KEY_ID`, `BACKBLAZE_KEY`, `BACKBLAZE_BUCKET_ID`
|
||||
`S3_ACCESS_TOKEN`, `S3_SECRET`, `S3_URL`, `S3_REGION`, `S3_BUCKET_NAME`
|
||||
The S3 configuration options are fairly self-explanatory in name, so here's simply their names:
|
||||
`S3_ACCESS_TOKEN`, `S3_SECRET`, `S3_URL`, `S3_REGION`, `S3_PUBLIC_BUCKET_NAME`, `S3_PRIVATE_BUCKET_NAME`, `S3_USES_PATH_STYLE_BUCKETS`
|
||||
|
||||
#### Search, OAuth, and miscellaneous options
|
||||
|
||||
|
||||
@@ -2,4 +2,3 @@ BASE_URL=http://127.0.0.1:8000/v2/
|
||||
BROWSER_BASE_URL=http://127.0.0.1:8000/v2/
|
||||
PYRO_BASE_URL=https://staging-archon.modrinth.com
|
||||
PROD_OVERRIDE=true
|
||||
|
||||
|
||||
@@ -1,46 +0,0 @@
|
||||
<template>
|
||||
<OmorphiaAvatar
|
||||
:src="src"
|
||||
:alt="alt"
|
||||
:size="size"
|
||||
:circle="circle"
|
||||
:no-shadow="noShadow"
|
||||
:loading="loading"
|
||||
:raised="raised"
|
||||
/>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { Avatar as OmorphiaAvatar } from "@modrinth/ui";
|
||||
|
||||
const props = defineProps({
|
||||
src: {
|
||||
type: String,
|
||||
default: null,
|
||||
},
|
||||
alt: {
|
||||
type: String,
|
||||
default: "",
|
||||
},
|
||||
size: {
|
||||
type: String,
|
||||
default: "2rem",
|
||||
},
|
||||
circle: {
|
||||
type: Boolean,
|
||||
default: false,
|
||||
},
|
||||
noShadow: {
|
||||
type: Boolean,
|
||||
default: false,
|
||||
},
|
||||
loading: {
|
||||
type: String,
|
||||
default: "eager",
|
||||
},
|
||||
raised: {
|
||||
type: Boolean,
|
||||
default: false,
|
||||
},
|
||||
});
|
||||
</script>
|
||||
@@ -1,131 +0,0 @@
|
||||
<template>
|
||||
<span
|
||||
:class="
|
||||
'badge flex items-center gap-1 font-semibold text-secondary ' + color + ' type--' + type
|
||||
"
|
||||
>
|
||||
<template v-if="color"> <span class="circle" /> {{ capitalizeString(type) }}</template>
|
||||
|
||||
<!-- User roles -->
|
||||
<template v-else-if="type === 'admin'"> <ModrinthIcon /> Modrinth Team</template>
|
||||
<template v-else-if="type === 'moderator'"> <ModeratorIcon /> Moderator</template>
|
||||
<template v-else-if="type === 'creator'"><CreatorIcon /> Creator</template>
|
||||
<template v-else-if="type === 'plus'"><PlusIcon /> Modrinth Plus</template>
|
||||
|
||||
<!-- Project statuses -->
|
||||
<template v-else-if="type === 'approved'"><GlobeIcon /> Public</template>
|
||||
<template v-else-if="type === 'approved-general'"><CheckIcon /> Approved</template>
|
||||
<template v-else-if="type === 'unlisted' || type === 'withheld'"
|
||||
><LinkIcon /> Unlisted</template
|
||||
>
|
||||
<template v-else-if="type === 'private'"><LockIcon /> Private</template>
|
||||
<template v-else-if="type === 'scheduled'"> <CalendarIcon /> Scheduled</template>
|
||||
<template v-else-if="type === 'draft'"><DraftIcon /> Draft</template>
|
||||
<template v-else-if="type === 'archived'"> <ArchiveIcon /> Archived</template>
|
||||
<template v-else-if="type === 'rejected'"><CrossIcon /> Rejected</template>
|
||||
<template v-else-if="type === 'processing'"> <ProcessingIcon /> Under review</template>
|
||||
|
||||
<!-- Team members -->
|
||||
<template v-else-if="type === 'accepted'"><CheckIcon /> Accepted</template>
|
||||
<template v-else-if="type === 'pending'"> <ProcessingIcon /> Pending </template>
|
||||
|
||||
<!-- Transaction statuses -->
|
||||
<template v-else-if="type === 'success'"><CheckIcon /> Success</template>
|
||||
|
||||
<!-- Report status -->
|
||||
<template v-else-if="type === 'closed'"> <CloseIcon /> Closed</template>
|
||||
|
||||
<!-- Other -->
|
||||
<template v-else> <span class="circle" /> {{ capitalizeString(type) }} </template>
|
||||
</span>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import {
|
||||
GlobeIcon,
|
||||
LinkIcon,
|
||||
ModrinthIcon,
|
||||
PlusIcon,
|
||||
ScaleIcon as ModeratorIcon,
|
||||
BoxIcon as CreatorIcon,
|
||||
FileTextIcon as DraftIcon,
|
||||
XIcon as CrossIcon,
|
||||
ArchiveIcon,
|
||||
UpdatedIcon as ProcessingIcon,
|
||||
CheckIcon,
|
||||
LockIcon,
|
||||
CalendarIcon,
|
||||
XCircleIcon as CloseIcon,
|
||||
} from "@modrinth/assets";
|
||||
import { capitalizeString } from "@modrinth/utils";
|
||||
|
||||
defineProps({
|
||||
type: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
color: {
|
||||
type: String,
|
||||
default: "",
|
||||
},
|
||||
});
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.badge {
|
||||
.circle {
|
||||
width: 0.5rem;
|
||||
height: 0.5rem;
|
||||
border-radius: 50%;
|
||||
display: inline-block;
|
||||
margin-right: 0.25rem;
|
||||
background-color: var(--badge-color);
|
||||
}
|
||||
|
||||
svg {
|
||||
vertical-align: -15%;
|
||||
width: 1em;
|
||||
height: 1em;
|
||||
}
|
||||
|
||||
&.type--closed,
|
||||
&.type--withheld,
|
||||
&.type--rejected,
|
||||
&.red {
|
||||
--badge-color: var(--color-red);
|
||||
}
|
||||
|
||||
&.type--pending,
|
||||
&.type--moderator,
|
||||
&.type--processing,
|
||||
&.type--scheduled,
|
||||
&.orange {
|
||||
--badge-color: var(--color-orange);
|
||||
}
|
||||
|
||||
&.type--accepted,
|
||||
&.type--admin,
|
||||
&.type--success,
|
||||
&.type--approved-general,
|
||||
&.green {
|
||||
--badge-color: var(--color-green);
|
||||
}
|
||||
|
||||
&.type--creator,
|
||||
&.blue {
|
||||
--badge-color: var(--color-blue);
|
||||
}
|
||||
|
||||
&.type--unlisted,
|
||||
&.type--plus,
|
||||
&.purple {
|
||||
--badge-color: var(--color-purple);
|
||||
}
|
||||
|
||||
&.type--private,
|
||||
&.type--approved,
|
||||
&.gray {
|
||||
--badge-color: var(--color-secondary);
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -1,75 +0,0 @@
|
||||
<template>
|
||||
<button class="code" :class="{ copied }" title="Copy code to clipboard" @click="copyText">
|
||||
<span>{{ text }}</span>
|
||||
<CheckIcon v-if="copied" />
|
||||
<ClipboardCopyIcon v-else />
|
||||
</button>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { CheckIcon, ClipboardCopyIcon } from "@modrinth/assets";
|
||||
|
||||
export default {
|
||||
components: {
|
||||
CheckIcon,
|
||||
ClipboardCopyIcon,
|
||||
},
|
||||
props: {
|
||||
text: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
copied: false,
|
||||
};
|
||||
},
|
||||
methods: {
|
||||
async copyText() {
|
||||
await navigator.clipboard.writeText(this.text);
|
||||
this.copied = true;
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.code {
|
||||
color: var(--color-text);
|
||||
display: inline-flex;
|
||||
grid-gap: 0.5rem;
|
||||
font-family: var(--mono-font);
|
||||
font-size: var(--font-size-sm);
|
||||
margin: 0;
|
||||
padding: 0.25rem 0.5rem;
|
||||
background-color: var(--color-code-bg);
|
||||
width: fit-content;
|
||||
border-radius: 10px;
|
||||
user-select: text;
|
||||
transition:
|
||||
opacity 0.5s ease-in-out,
|
||||
filter 0.2s ease-in-out,
|
||||
transform 0.05s ease-in-out,
|
||||
outline 0.2s ease-in-out;
|
||||
|
||||
span {
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
|
||||
svg {
|
||||
width: 1em;
|
||||
height: 1em;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
filter: brightness(0.85);
|
||||
}
|
||||
|
||||
&:active {
|
||||
transform: scale(0.95);
|
||||
filter: brightness(0.8);
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -654,11 +654,11 @@ For a brief rundown of how this works:
|
||||
{
|
||||
name: "Insufficient",
|
||||
resultingMessage: `## Insufficient Gallery Images
|
||||
We ask that projects like yours show off their content using images in the Gallery, or optionally in the Description, in order to effectively and clearly inform users of its content per section 2.1 of [Modrinth's content rules](https://modrinth.com/legal/rules#general-expectations).
|
||||
Keep in mind that you should:
|
||||
- Set a featured image that best represents your project.
|
||||
- Ensure all your images have titles that accurately label the image, and optionally, details on the contents of the image in the images Description.
|
||||
- Upload any relevant images in your Description to your Gallery tab for best results.`,
|
||||
We ask that projects like yours show off their content using images in the Gallery, or optionally in the Description, in order to effectively and clearly inform users of its content per section 2.1 of [Modrinth's content rules](https://modrinth.com/legal/rules#general-expectations).
|
||||
Keep in mind that you should:
|
||||
- Set a featured image that best represents your project.
|
||||
- Ensure all your images have titles that accurately label the image, and optionally, details on the contents of the image in the images Description.
|
||||
- Upload any relevant images in your Description to your Gallery tab for best results.`,
|
||||
},
|
||||
{
|
||||
name: "Not relevant",
|
||||
|
||||
@@ -104,13 +104,13 @@
|
||||
</nuxt-link>
|
||||
<template v-if="tags.rejectedStatuses.includes(notification.body.new_status)">
|
||||
has been
|
||||
<Badge :type="notification.body.new_status" />
|
||||
<ProjectStatusBadge :status="notification.body.new_status" />
|
||||
</template>
|
||||
<template v-else>
|
||||
updated from
|
||||
<Badge :type="notification.body.old_status" />
|
||||
<ProjectStatusBadge :status="notification.body.old_status" />
|
||||
to
|
||||
<Badge :type="notification.body.new_status" />
|
||||
<ProjectStatusBadge :status="notification.body.new_status" />
|
||||
</template>
|
||||
by the moderators.
|
||||
</template>
|
||||
@@ -331,16 +331,13 @@ import {
|
||||
XIcon,
|
||||
ExternalIcon,
|
||||
} from "@modrinth/assets";
|
||||
import { useRelativeTime } from "@modrinth/ui";
|
||||
import { Avatar, ProjectStatusBadge, CopyCode, useRelativeTime } from "@modrinth/ui";
|
||||
import ThreadSummary from "~/components/ui/thread/ThreadSummary.vue";
|
||||
import { getProjectLink, getVersionLink } from "~/helpers/projects.js";
|
||||
import { getUserLink } from "~/helpers/users.js";
|
||||
import { acceptTeamInvite, removeSelfFromTeam } from "~/helpers/teams.js";
|
||||
import { markAsRead } from "~/helpers/notifications.ts";
|
||||
import DoubleIcon from "~/components/ui/DoubleIcon.vue";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import CopyCode from "~/components/ui/CopyCode.vue";
|
||||
import Categories from "~/components/ui/search/Categories.vue";
|
||||
|
||||
const app = useNuxtApp();
|
||||
|
||||
@@ -1,5 +1,8 @@
|
||||
<template>
|
||||
<div class="vue-notification-group experimental-styles-within">
|
||||
<div
|
||||
class="vue-notification-group experimental-styles-within"
|
||||
:class="{ 'intercom-present': isIntercomPresent }"
|
||||
>
|
||||
<transition-group name="notifs">
|
||||
<div
|
||||
v-for="(item, index) in notifications"
|
||||
@@ -80,6 +83,8 @@ import {
|
||||
} from "@modrinth/assets";
|
||||
const notifications = useNotifications();
|
||||
|
||||
const isIntercomPresent = ref(false);
|
||||
|
||||
function stopTimer(notif) {
|
||||
clearTimeout(notif.timer);
|
||||
}
|
||||
@@ -106,6 +111,27 @@ const createNotifText = (notif) => {
|
||||
return text;
|
||||
};
|
||||
|
||||
function checkIntercomPresence() {
|
||||
isIntercomPresent.value = !!document.querySelector(".intercom-lightweight-app");
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
checkIntercomPresence();
|
||||
|
||||
const observer = new MutationObserver(() => {
|
||||
checkIntercomPresence();
|
||||
});
|
||||
|
||||
observer.observe(document.body, {
|
||||
childList: true,
|
||||
subtree: true,
|
||||
});
|
||||
|
||||
onBeforeUnmount(() => {
|
||||
observer.disconnect();
|
||||
});
|
||||
});
|
||||
|
||||
function copyToClipboard(notif) {
|
||||
const text = createNotifText(notif);
|
||||
|
||||
@@ -130,6 +156,10 @@ function copyToClipboard(notif) {
|
||||
bottom: 0.75rem;
|
||||
}
|
||||
|
||||
&.intercom-present {
|
||||
bottom: 5rem;
|
||||
}
|
||||
|
||||
.vue-notification-wrapper {
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
|
||||
@@ -57,7 +57,7 @@
|
||||
<div class="table-cell">
|
||||
<BoxIcon />
|
||||
<span>{{
|
||||
$formatProjectType(
|
||||
formatProjectType(
|
||||
$getProjectTypeForDisplay(
|
||||
project.project_types?.[0] ?? "project",
|
||||
project.loaders,
|
||||
@@ -111,6 +111,7 @@
|
||||
<script setup>
|
||||
import { BoxIcon, SettingsIcon, TransferIcon, XIcon } from "@modrinth/assets";
|
||||
import { Button, Modal, Checkbox, CopyCode, Avatar } from "@modrinth/ui";
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
|
||||
const modalOpen = ref(null);
|
||||
|
||||
|
||||
@@ -1,196 +0,0 @@
|
||||
<template>
|
||||
<div v-if="count > 1" class="columns paginates">
|
||||
<a
|
||||
:class="{ disabled: page === 1 }"
|
||||
:tabindex="page === 1 ? -1 : 0"
|
||||
class="left-arrow paginate has-icon"
|
||||
aria-label="Previous Page"
|
||||
:href="linkFunction(page - 1)"
|
||||
@click.prevent="page !== 1 ? switchPage(page - 1) : null"
|
||||
>
|
||||
<LeftArrowIcon />
|
||||
</a>
|
||||
<div
|
||||
v-for="(item, index) in pages"
|
||||
:key="'page-' + item + '-' + index"
|
||||
:class="{
|
||||
'page-number': page !== item,
|
||||
shrink: item > 99,
|
||||
}"
|
||||
class="page-number-container"
|
||||
>
|
||||
<div v-if="item === '-'" class="has-icon">
|
||||
<GapIcon />
|
||||
</div>
|
||||
<a
|
||||
v-else
|
||||
:class="{
|
||||
'page-number current': page === item,
|
||||
shrink: item > 99,
|
||||
}"
|
||||
:href="linkFunction(item)"
|
||||
@click.prevent="page !== item ? switchPage(item) : null"
|
||||
>
|
||||
{{ item }}
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<a
|
||||
:class="{
|
||||
disabled: page === pages[pages.length - 1],
|
||||
}"
|
||||
:tabindex="page === pages[pages.length - 1] ? -1 : 0"
|
||||
class="right-arrow paginate has-icon"
|
||||
aria-label="Next Page"
|
||||
:href="linkFunction(page + 1)"
|
||||
@click.prevent="page !== pages[pages.length - 1] ? switchPage(page + 1) : null"
|
||||
>
|
||||
<RightArrowIcon />
|
||||
</a>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { GapIcon, LeftArrowIcon, RightArrowIcon } from "@modrinth/assets";
|
||||
|
||||
export default {
|
||||
components: {
|
||||
GapIcon,
|
||||
LeftArrowIcon,
|
||||
RightArrowIcon,
|
||||
},
|
||||
props: {
|
||||
page: {
|
||||
type: Number,
|
||||
default: 1,
|
||||
},
|
||||
count: {
|
||||
type: Number,
|
||||
default: 1,
|
||||
},
|
||||
linkFunction: {
|
||||
type: Function,
|
||||
default() {
|
||||
return () => "/";
|
||||
},
|
||||
},
|
||||
},
|
||||
emits: ["switch-page"],
|
||||
computed: {
|
||||
pages() {
|
||||
let pages = [];
|
||||
|
||||
if (this.count > 7) {
|
||||
if (this.page + 3 >= this.count) {
|
||||
pages = [
|
||||
1,
|
||||
"-",
|
||||
this.count - 4,
|
||||
this.count - 3,
|
||||
this.count - 2,
|
||||
this.count - 1,
|
||||
this.count,
|
||||
];
|
||||
} else if (this.page > 5) {
|
||||
pages = [1, "-", this.page - 1, this.page, this.page + 1, "-", this.count];
|
||||
} else {
|
||||
pages = [1, 2, 3, 4, 5, "-", this.count];
|
||||
}
|
||||
} else {
|
||||
pages = Array.from({ length: this.count }, (_, i) => i + 1);
|
||||
}
|
||||
|
||||
return pages;
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
switchPage(newPage) {
|
||||
this.$emit("switch-page", newPage);
|
||||
if (newPage !== null && newPage !== "" && !isNaN(newPage)) {
|
||||
this.$emit("switch-page", Math.min(Math.max(newPage, 1), this.count));
|
||||
}
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
a {
|
||||
position: relative;
|
||||
color: var(--color-button-text);
|
||||
box-shadow: var(--shadow-raised), var(--shadow-inset);
|
||||
|
||||
padding: 0.5rem 1rem;
|
||||
margin: 0;
|
||||
border-radius: 2rem;
|
||||
background: var(--color-raised-bg);
|
||||
|
||||
transition:
|
||||
opacity 0.5s ease-in-out,
|
||||
filter 0.2s ease-in-out,
|
||||
transform 0.05s ease-in-out,
|
||||
outline 0.2s ease-in-out;
|
||||
|
||||
&.page-number.current {
|
||||
background: var(--color-brand);
|
||||
color: var(--color-brand-inverted);
|
||||
cursor: default;
|
||||
outline: 2px solid transparent;
|
||||
}
|
||||
|
||||
&.paginate.disabled {
|
||||
background-color: transparent;
|
||||
cursor: not-allowed;
|
||||
filter: grayscale(50%);
|
||||
opacity: 0.5;
|
||||
}
|
||||
}
|
||||
|
||||
.has-icon {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
svg {
|
||||
width: 1em;
|
||||
}
|
||||
}
|
||||
|
||||
.page-number-container,
|
||||
a,
|
||||
.has-icon {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.paginates {
|
||||
height: 2em;
|
||||
margin: 0.5rem 0;
|
||||
|
||||
> div,
|
||||
.has-icon {
|
||||
margin: 0 0.3em;
|
||||
}
|
||||
}
|
||||
|
||||
.left-arrow {
|
||||
margin-left: auto !important;
|
||||
}
|
||||
|
||||
.right-arrow {
|
||||
margin-right: auto !important;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 400px) {
|
||||
.paginates {
|
||||
font-size: 80%;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 530px) {
|
||||
a {
|
||||
width: 2.5rem;
|
||||
padding: 0.5rem 0;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -29,7 +29,7 @@
|
||||
{{ author }}
|
||||
</nuxt-link>
|
||||
</p>
|
||||
<Badge v-if="status && status !== 'approved'" :type="status" class="status" />
|
||||
<ProjectStatusBadge v-if="status && status !== 'approved'" :status="status" class="status" />
|
||||
</div>
|
||||
<p class="description">
|
||||
{{ description }}
|
||||
@@ -91,18 +91,16 @@
|
||||
|
||||
<script>
|
||||
import { CalendarIcon, UpdatedIcon, DownloadIcon, HeartIcon } from "@modrinth/assets";
|
||||
import { Avatar, ProjectStatusBadge, useRelativeTime } from "@modrinth/ui";
|
||||
import Categories from "~/components/ui/search/Categories.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import EnvironmentIndicator from "~/components/ui/EnvironmentIndicator.vue";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import { useRelativeTime } from "@modrinth/ui";
|
||||
|
||||
export default {
|
||||
components: {
|
||||
ProjectStatusBadge,
|
||||
EnvironmentIndicator,
|
||||
Avatar,
|
||||
Categories,
|
||||
Badge,
|
||||
CalendarIcon,
|
||||
UpdatedIcon,
|
||||
DownloadIcon,
|
||||
|
||||
@@ -118,7 +118,7 @@ import {
|
||||
ScaleIcon,
|
||||
DropdownIcon,
|
||||
} from "@modrinth/assets";
|
||||
import { formatProjectType } from "~/plugins/shorthands.js";
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
import { acceptTeamInvite, removeTeamMember } from "~/helpers/teams.js";
|
||||
|
||||
const props = defineProps({
|
||||
|
||||
@@ -11,8 +11,8 @@
|
||||
<div class="stacked">
|
||||
<span class="title">{{ report.project.title }}</span>
|
||||
<span>{{
|
||||
$formatProjectType(
|
||||
$getProjectTypeForUrl(report.project.project_type, report.project.loaders),
|
||||
formatProjectType(
|
||||
getProjectTypeForUrl(report.project.project_type, report.project.loaders),
|
||||
)
|
||||
}}</span>
|
||||
</div>
|
||||
@@ -53,8 +53,8 @@
|
||||
<div class="stacked">
|
||||
<span class="title">{{ report.project.title }}</span>
|
||||
<span>{{
|
||||
$formatProjectType(
|
||||
$getProjectTypeForUrl(report.project.project_type, report.project.loaders),
|
||||
formatProjectType(
|
||||
getProjectTypeForUrl(report.project.project_type, report.project.loaders),
|
||||
)
|
||||
}}</span>
|
||||
</div>
|
||||
@@ -104,12 +104,11 @@
|
||||
|
||||
<script setup>
|
||||
import { ReportIcon, UnknownIcon, VersionIcon } from "@modrinth/assets";
|
||||
import { Avatar, Badge, CopyCode, useRelativeTime } from "@modrinth/ui";
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
import { renderHighlightedString } from "~/helpers/highlight.js";
|
||||
import { useRelativeTime } from "@modrinth/ui";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import ThreadSummary from "~/components/ui/thread/ThreadSummary.vue";
|
||||
import CopyCode from "~/components/ui/CopyCode.vue";
|
||||
import { getProjectTypeForUrl } from "~/helpers/projects.js";
|
||||
|
||||
const formatRelativeTime = useRelativeTime();
|
||||
|
||||
|
||||
@@ -4,12 +4,14 @@
|
||||
<span
|
||||
v-for="category in categoriesFiltered"
|
||||
:key="category.name"
|
||||
v-html="category.icon + $formatCategory(category.name)"
|
||||
v-html="category.icon + formatCategory(category.name)"
|
||||
/>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { formatCategory } from "@modrinth/utils";
|
||||
|
||||
export default {
|
||||
props: {
|
||||
categories: {
|
||||
@@ -38,6 +40,7 @@ export default {
|
||||
);
|
||||
},
|
||||
},
|
||||
methods: { formatCategory },
|
||||
};
|
||||
</script>
|
||||
|
||||
|
||||
@@ -16,7 +16,7 @@ import {
|
||||
} from "@modrinth/assets";
|
||||
import { ButtonStyled, commonMessages, OverflowMenu, ProgressBar } from "@modrinth/ui";
|
||||
import { defineMessages, useVIntl } from "@vintl/vintl";
|
||||
import { ref } from "vue";
|
||||
import { ref, computed } from "vue";
|
||||
import type { Backup } from "@modrinth/utils";
|
||||
|
||||
const flags = useFeatureFlags();
|
||||
@@ -52,9 +52,10 @@ const failedToCreate = computed(() => props.backup.interrupted);
|
||||
const preparedDownloadStates = ["ready", "done"];
|
||||
const inactiveStates = ["failed", "cancelled"];
|
||||
|
||||
const hasPreparedDownload = computed(() =>
|
||||
preparedDownloadStates.includes(props.backup.task?.file?.state ?? ""),
|
||||
);
|
||||
const hasPreparedDownload = computed(() => {
|
||||
const fileState = props.backup.task?.file?.state ?? "";
|
||||
return preparedDownloadStates.includes(fileState);
|
||||
});
|
||||
|
||||
const creating = computed(() => {
|
||||
const task = props.backup.task?.create;
|
||||
@@ -81,6 +82,10 @@ const restoring = computed(() => {
|
||||
const initiatedPrepare = ref(false);
|
||||
|
||||
const preparingFile = computed(() => {
|
||||
if (hasPreparedDownload.value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const task = props.backup.task?.file;
|
||||
return (
|
||||
(!task && initiatedPrepare.value) ||
|
||||
|
||||
@@ -39,7 +39,7 @@
|
||||
/>
|
||||
<XCircleIcon
|
||||
v-show="
|
||||
item.status === 'error' ||
|
||||
item.status.includes('error') ||
|
||||
item.status === 'cancelled' ||
|
||||
item.status === 'incorrect-type'
|
||||
"
|
||||
@@ -54,9 +54,14 @@
|
||||
<template v-if="item.status === 'completed'">
|
||||
<span>Done</span>
|
||||
</template>
|
||||
<template v-else-if="item.status === 'error'">
|
||||
<template v-else-if="item.status === 'error-file-exists'">
|
||||
<span class="text-red">Failed - File already exists</span>
|
||||
</template>
|
||||
<template v-else-if="item.status === 'error-generic'">
|
||||
<span class="text-red"
|
||||
>Failed - {{ item.error?.message || "An unexpected error occured." }}</span
|
||||
>
|
||||
</template>
|
||||
<template v-else-if="item.status === 'incorrect-type'">
|
||||
<span class="text-red">Failed - Incorrect file type</span>
|
||||
</template>
|
||||
@@ -104,9 +109,17 @@ import { FSModule } from "~/composables/servers/modules/fs.ts";
|
||||
interface UploadItem {
|
||||
file: File;
|
||||
progress: number;
|
||||
status: "pending" | "uploading" | "completed" | "error" | "cancelled" | "incorrect-type";
|
||||
status:
|
||||
| "pending"
|
||||
| "uploading"
|
||||
| "completed"
|
||||
| "error-file-exists"
|
||||
| "error-generic"
|
||||
| "cancelled"
|
||||
| "incorrect-type";
|
||||
size: string;
|
||||
uploader?: any;
|
||||
error?: Error;
|
||||
}
|
||||
|
||||
interface Props {
|
||||
@@ -245,8 +258,18 @@ const uploadFile = async (file: File) => {
|
||||
console.error("Error uploading file:", error);
|
||||
const index = uploadQueue.value.findIndex((item) => item.file.name === file.name);
|
||||
if (index !== -1 && uploadQueue.value[index].status !== "cancelled") {
|
||||
uploadQueue.value[index].status =
|
||||
error instanceof Error && error.message === badFileTypeMsg ? "incorrect-type" : "error";
|
||||
const target = uploadQueue.value[index];
|
||||
|
||||
if (error instanceof Error) {
|
||||
if (error.message === badFileTypeMsg) {
|
||||
target.status = "incorrect-type";
|
||||
} else if (target.progress === 100 && error.message.includes("401")) {
|
||||
target.status = "error-file-exists";
|
||||
} else {
|
||||
target.status = "error-generic";
|
||||
target.error = error;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
setTimeout(async () => {
|
||||
|
||||
@@ -214,7 +214,7 @@
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { OverflowMenu, MarkdownEditor } from "@modrinth/ui";
|
||||
import { CopyCode, OverflowMenu, MarkdownEditor } from "@modrinth/ui";
|
||||
import {
|
||||
DropdownIcon,
|
||||
ReplyIcon,
|
||||
@@ -226,7 +226,6 @@ import {
|
||||
ScaleIcon,
|
||||
} from "@modrinth/assets";
|
||||
import { useImageUpload } from "~/composables/image-upload.ts";
|
||||
import CopyCode from "~/components/ui/CopyCode.vue";
|
||||
import ThreadMessage from "~/components/ui/thread/ThreadMessage.vue";
|
||||
import { isStaff } from "~/helpers/users.js";
|
||||
import { isApproved, isRejected } from "~/helpers/projects.js";
|
||||
|
||||
@@ -103,10 +103,8 @@ import {
|
||||
ModrinthIcon,
|
||||
ScaleIcon,
|
||||
} from "@modrinth/assets";
|
||||
import { AutoLink, OverflowMenu, useRelativeTime } from "@modrinth/ui";
|
||||
import { AutoLink, Avatar, Badge, OverflowMenu, useRelativeTime } from "@modrinth/ui";
|
||||
import { renderString } from "@modrinth/utils";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import { isStaff } from "~/helpers/users.js";
|
||||
|
||||
const props = defineProps({
|
||||
|
||||
@@ -124,58 +124,63 @@ export class ModrinthServer {
|
||||
return dataURL;
|
||||
}
|
||||
} catch (error) {
|
||||
if (error instanceof ModrinthServerError && error.statusCode === 404 && iconUrl) {
|
||||
// Handle external icon processing
|
||||
try {
|
||||
const response = await fetch(iconUrl);
|
||||
if (!response.ok) throw new Error("Failed to fetch icon");
|
||||
const file = await response.blob();
|
||||
const originalFile = new File([file], "server-icon-original.png", {
|
||||
type: "image/png",
|
||||
});
|
||||
|
||||
if (import.meta.client) {
|
||||
const dataURL = await new Promise<string>((resolve) => {
|
||||
const canvas = document.createElement("canvas");
|
||||
const ctx = canvas.getContext("2d");
|
||||
const img = new Image();
|
||||
img.onload = () => {
|
||||
canvas.width = 64;
|
||||
canvas.height = 64;
|
||||
ctx?.drawImage(img, 0, 0, 64, 64);
|
||||
canvas.toBlob(async (blob) => {
|
||||
if (blob) {
|
||||
const scaledFile = new File([blob], "server-icon.png", { type: "image/png" });
|
||||
await useServersFetch(`/create?path=/server-icon.png&type=file`, {
|
||||
method: "POST",
|
||||
contentType: "application/octet-stream",
|
||||
body: scaledFile,
|
||||
override: auth,
|
||||
});
|
||||
await useServersFetch(`/create?path=/server-icon-original.png&type=file`, {
|
||||
method: "POST",
|
||||
contentType: "application/octet-stream",
|
||||
body: originalFile,
|
||||
override: auth,
|
||||
});
|
||||
}
|
||||
}, "image/png");
|
||||
const dataURL = canvas.toDataURL("image/png");
|
||||
sharedImage.value = dataURL;
|
||||
resolve(dataURL);
|
||||
URL.revokeObjectURL(img.src);
|
||||
};
|
||||
img.src = URL.createObjectURL(file);
|
||||
if (error instanceof ModrinthServerError && error.statusCode === 404) {
|
||||
if (iconUrl) {
|
||||
try {
|
||||
const response = await fetch(iconUrl);
|
||||
if (!response.ok) throw new Error("Failed to fetch icon");
|
||||
const file = await response.blob();
|
||||
const originalFile = new File([file], "server-icon-original.png", {
|
||||
type: "image/png",
|
||||
});
|
||||
return dataURL;
|
||||
|
||||
if (import.meta.client) {
|
||||
const dataURL = await new Promise<string>((resolve) => {
|
||||
const canvas = document.createElement("canvas");
|
||||
const ctx = canvas.getContext("2d");
|
||||
const img = new Image();
|
||||
img.onload = () => {
|
||||
canvas.width = 64;
|
||||
canvas.height = 64;
|
||||
ctx?.drawImage(img, 0, 0, 64, 64);
|
||||
canvas.toBlob(async (blob) => {
|
||||
if (blob) {
|
||||
const scaledFile = new File([blob], "server-icon.png", {
|
||||
type: "image/png",
|
||||
});
|
||||
await useServersFetch(`/create?path=/server-icon.png&type=file`, {
|
||||
method: "POST",
|
||||
contentType: "application/octet-stream",
|
||||
body: scaledFile,
|
||||
override: auth,
|
||||
});
|
||||
await useServersFetch(`/create?path=/server-icon-original.png&type=file`, {
|
||||
method: "POST",
|
||||
contentType: "application/octet-stream",
|
||||
body: originalFile,
|
||||
override: auth,
|
||||
});
|
||||
}
|
||||
}, "image/png");
|
||||
const dataURL = canvas.toDataURL("image/png");
|
||||
sharedImage.value = dataURL;
|
||||
resolve(dataURL);
|
||||
URL.revokeObjectURL(img.src);
|
||||
};
|
||||
img.src = URL.createObjectURL(file);
|
||||
});
|
||||
return dataURL;
|
||||
}
|
||||
} catch (externalError: any) {
|
||||
console.debug("Could not process external icon:", externalError.message);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("Failed to process external icon:", error);
|
||||
}
|
||||
} else {
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("Failed to process server icon:", error);
|
||||
} catch (error: any) {
|
||||
console.debug("Icon processing failed:", error.message);
|
||||
}
|
||||
|
||||
sharedImage.value = undefined;
|
||||
@@ -239,6 +244,18 @@ export class ModrinthServer {
|
||||
break;
|
||||
}
|
||||
} catch (error) {
|
||||
if (error instanceof ModrinthServerError) {
|
||||
if (error.statusCode === 404 && ["fs", "content"].includes(module)) {
|
||||
console.debug(`Optional ${module} resource not found:`, error.message);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (error.statusCode === 503) {
|
||||
console.debug(`Temporary ${module} unavailable:`, error.message);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
this.errors[module] = {
|
||||
error:
|
||||
error instanceof ModrinthServerError
|
||||
|
||||
@@ -155,19 +155,25 @@ export class GeneralModule extends ServerModule implements ServerGeneral {
|
||||
}
|
||||
|
||||
async setMotd(motd: string): Promise<void> {
|
||||
const props = (await this.server.fetchConfigFile("ServerProperties")) as any;
|
||||
if (props) {
|
||||
props.motd = motd;
|
||||
const newProps = this.server.constructServerProperties(props);
|
||||
const octetStream = new Blob([newProps], { type: "application/octet-stream" });
|
||||
const auth = await useServersFetch<JWTAuth>(`servers/${this.serverId}/fs`);
|
||||
try {
|
||||
const props = (await this.server.fetchConfigFile("ServerProperties")) as any;
|
||||
if (props) {
|
||||
props.motd = motd;
|
||||
const newProps = this.server.constructServerProperties(props);
|
||||
const octetStream = new Blob([newProps], { type: "application/octet-stream" });
|
||||
const auth = await useServersFetch<JWTAuth>(`servers/${this.serverId}/fs`);
|
||||
|
||||
await useServersFetch(`/update?path=/server.properties`, {
|
||||
method: "PUT",
|
||||
contentType: "application/octet-stream",
|
||||
body: octetStream,
|
||||
override: auth,
|
||||
});
|
||||
await useServersFetch(`/update?path=/server.properties`, {
|
||||
method: "PUT",
|
||||
contentType: "application/octet-stream",
|
||||
body: octetStream,
|
||||
override: auth,
|
||||
});
|
||||
}
|
||||
} catch {
|
||||
console.error(
|
||||
"[Modrinth Servers] [General] Failed to set MOTD due to lack of server properties file.",
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { formatBytes } from "~/plugins/shorthands.js";
|
||||
import { formatBytes } from "@modrinth/utils";
|
||||
|
||||
export const fileIsValid = (file, validationOptions) => {
|
||||
const { maxSize, alertOnInvalid } = validationOptions;
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
<h1 class="wrap-as-needed">
|
||||
{{ project.title }}
|
||||
</h1>
|
||||
<Badge :type="project.status" />
|
||||
<ProjectStatusBadge :status="project.status" />
|
||||
</div>
|
||||
</div>
|
||||
<h2>Project settings</h2>
|
||||
@@ -870,17 +870,24 @@ import {
|
||||
ProjectSidebarCreators,
|
||||
ProjectSidebarDetails,
|
||||
ProjectSidebarLinks,
|
||||
ProjectStatusBadge,
|
||||
ScrollablePanel,
|
||||
useRelativeTime,
|
||||
} from "@modrinth/ui";
|
||||
import VersionSummary from "@modrinth/ui/src/components/version/VersionSummary.vue";
|
||||
import { formatCategory, isRejected, isStaff, isUnderReview, renderString } from "@modrinth/utils";
|
||||
import {
|
||||
formatCategory,
|
||||
formatProjectType,
|
||||
isRejected,
|
||||
isStaff,
|
||||
isUnderReview,
|
||||
renderString,
|
||||
} from "@modrinth/utils";
|
||||
import { navigateTo } from "#app";
|
||||
import dayjs from "dayjs";
|
||||
import Accordion from "~/components/ui/Accordion.vue";
|
||||
import AdPlaceholder from "~/components/ui/AdPlaceholder.vue";
|
||||
import AutomaticAccordion from "~/components/ui/AutomaticAccordion.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import Breadcrumbs from "~/components/ui/Breadcrumbs.vue";
|
||||
import CollectionCreateModal from "~/components/ui/CollectionCreateModal.vue";
|
||||
import MessageBanner from "~/components/ui/MessageBanner.vue";
|
||||
@@ -1286,7 +1293,7 @@ featuredVersions.value.sort((a, b) => {
|
||||
});
|
||||
|
||||
const projectTypeDisplay = computed(() =>
|
||||
data.$formatProjectType(
|
||||
formatProjectType(
|
||||
data.$getProjectTypeForDisplay(project.value.project_type, project.value.loaders),
|
||||
),
|
||||
);
|
||||
|
||||
@@ -104,7 +104,7 @@
|
||||
<span class="label__title">Client-side</span>
|
||||
<span class="label__description">
|
||||
Select based on if the
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }} has functionality on the
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }} has functionality on the
|
||||
client side. Just because a mod works in Singleplayer doesn't mean it has actual
|
||||
client-side functionality.
|
||||
</span>
|
||||
@@ -128,7 +128,7 @@
|
||||
<span class="label__title">Server-side</span>
|
||||
<span class="label__description">
|
||||
Select based on if the
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }} has functionality on the
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }} has functionality on the
|
||||
<strong>logical</strong> server. Remember that Singleplayer contains an integrated
|
||||
server.
|
||||
</span>
|
||||
@@ -239,11 +239,10 @@
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { formatProjectStatus } from "@modrinth/utils";
|
||||
import { formatProjectStatus, formatProjectType } from "@modrinth/utils";
|
||||
import { UploadIcon, SaveIcon, TrashIcon, XIcon, IssuesIcon, CheckIcon } from "@modrinth/assets";
|
||||
import { Multiselect } from "vue-multiselect";
|
||||
import { ConfirmModal } from "@modrinth/ui";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import { ConfirmModal, Avatar } from "@modrinth/ui";
|
||||
import FileInput from "~/components/ui/FileInput.vue";
|
||||
|
||||
const props = defineProps({
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
</div>
|
||||
<p>
|
||||
Accurate tagging is important to help people find your
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }}. Make sure to select all tags
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }}. Make sure to select all tags
|
||||
that apply.
|
||||
</p>
|
||||
<p v-if="project.versions.length === 0" class="known-errors">
|
||||
@@ -18,25 +18,25 @@
|
||||
<template v-for="header in Object.keys(categoryLists)" :key="`categories-${header}`">
|
||||
<div class="label">
|
||||
<h4>
|
||||
<span class="label__title">{{ $formatCategoryHeader(header) }}</span>
|
||||
<span class="label__title">{{ formatCategoryHeader(header) }}</span>
|
||||
</h4>
|
||||
<span class="label__description">
|
||||
<template v-if="header === 'categories'">
|
||||
Select all categories that reflect the themes or function of your
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }}.
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }}.
|
||||
</template>
|
||||
<template v-else-if="header === 'features'">
|
||||
Select all of the features that your
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }} makes use of.
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }} makes use of.
|
||||
</template>
|
||||
<template v-else-if="header === 'resolutions'">
|
||||
Select the resolution(s) of textures in your
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }}.
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }}.
|
||||
</template>
|
||||
<template v-else-if="header === 'performance impact'">
|
||||
Select the realistic performance impact of your
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }}. Select multiple if the
|
||||
{{ $formatProjectType(project.project_type).toLowerCase() }} is configurable to
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }}. Select multiple if the
|
||||
{{ formatProjectType(project.project_type).toLowerCase() }} is configurable to
|
||||
different levels of performance impact.
|
||||
</template>
|
||||
</span>
|
||||
@@ -46,7 +46,7 @@
|
||||
v-for="category in categoryLists[header]"
|
||||
:key="`category-${header}-${category.name}`"
|
||||
:model-value="selectedTags.includes(category)"
|
||||
:description="$formatCategory(category.name)"
|
||||
:description="formatCategory(category.name)"
|
||||
class="category-selector"
|
||||
@update:model-value="toggleCategory(category)"
|
||||
>
|
||||
@@ -57,7 +57,7 @@
|
||||
class="icon"
|
||||
v-html="category.icon"
|
||||
/>
|
||||
<span aria-hidden="true"> {{ $formatCategory(category.name) }}</span>
|
||||
<span aria-hidden="true"> {{ formatCategory(category.name) }}</span>
|
||||
</div>
|
||||
</Checkbox>
|
||||
</div>
|
||||
@@ -80,7 +80,7 @@
|
||||
:key="`featured-category-${category.name}`"
|
||||
class="category-selector"
|
||||
:model-value="featuredTags.includes(category)"
|
||||
:description="$formatCategory(category.name)"
|
||||
:description="formatCategory(category.name)"
|
||||
:disabled="featuredTags.length >= 3 && !featuredTags.includes(category)"
|
||||
@update:model-value="toggleFeaturedCategory(category)"
|
||||
>
|
||||
@@ -91,7 +91,7 @@
|
||||
class="icon"
|
||||
v-html="category.icon"
|
||||
/>
|
||||
<span aria-hidden="true"> {{ $formatCategory(category.name) }}</span>
|
||||
<span aria-hidden="true"> {{ formatCategory(category.name) }}</span>
|
||||
</div>
|
||||
</Checkbox>
|
||||
</div>
|
||||
@@ -114,6 +114,7 @@
|
||||
|
||||
<script>
|
||||
import { StarIcon, SaveIcon } from "@modrinth/assets";
|
||||
import { formatCategory, formatCategoryHeader, formatProjectType } from "@modrinth/utils";
|
||||
import Checkbox from "~/components/ui/Checkbox.vue";
|
||||
|
||||
export default defineNuxtComponent({
|
||||
@@ -222,6 +223,9 @@ export default defineNuxtComponent({
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
formatProjectType,
|
||||
formatCategoryHeader,
|
||||
formatCategory,
|
||||
toggleCategory(category) {
|
||||
if (this.selectedTags.includes(category)) {
|
||||
this.selectedTags = this.selectedTags.filter((x) => x !== category);
|
||||
|
||||
@@ -144,7 +144,7 @@
|
||||
<div v-else class="input-group">
|
||||
<ButtonStyled v-if="primaryFile" color="brand">
|
||||
<a
|
||||
v-tooltip="primaryFile.filename + ' (' + $formatBytes(primaryFile.size) + ')'"
|
||||
v-tooltip="primaryFile.filename + ' (' + formatBytes(primaryFile.size) + ')'"
|
||||
:href="primaryFile.url"
|
||||
@click="emit('onDownload')"
|
||||
>
|
||||
@@ -320,7 +320,7 @@
|
||||
<FileIcon aria-hidden="true" />
|
||||
<span class="filename">
|
||||
<strong>{{ replaceFile.name }}</strong>
|
||||
<span class="file-size">({{ $formatBytes(replaceFile.size) }})</span>
|
||||
<span class="file-size">({{ formatBytes(replaceFile.size) }})</span>
|
||||
</span>
|
||||
<FileInput
|
||||
class="iconified-button raised-button"
|
||||
@@ -345,7 +345,7 @@
|
||||
<FileIcon aria-hidden="true" />
|
||||
<span class="filename">
|
||||
<strong>{{ file.filename }}</strong>
|
||||
<span class="file-size">({{ $formatBytes(file.size) }})</span>
|
||||
<span class="file-size">({{ formatBytes(file.size) }})</span>
|
||||
<span v-if="primaryFile.hashes.sha1 === file.hashes.sha1" class="file-type">
|
||||
Primary
|
||||
</span>
|
||||
@@ -412,7 +412,7 @@
|
||||
<FileIcon aria-hidden="true" />
|
||||
<span class="filename">
|
||||
<strong>{{ file.name }}</strong>
|
||||
<span class="file-size">({{ $formatBytes(file.size) }})</span>
|
||||
<span class="file-size">({{ formatBytes(file.size) }})</span>
|
||||
</span>
|
||||
<multiselect
|
||||
v-if="version.loaders.some((x) => tags.loaderData.dataPackLoaders.includes(x))"
|
||||
@@ -533,7 +533,7 @@
|
||||
)
|
||||
.map((it) => it.name)
|
||||
"
|
||||
:custom-label="(value) => $formatCategory(value)"
|
||||
:custom-label="formatCategory"
|
||||
:loading="tags.loaders.length === 0"
|
||||
:multiple="true"
|
||||
:searchable="true"
|
||||
@@ -630,7 +630,15 @@
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
import { ButtonStyled, ConfirmModal, MarkdownEditor } from "@modrinth/ui";
|
||||
import {
|
||||
Avatar,
|
||||
Badge,
|
||||
CopyCode,
|
||||
Checkbox,
|
||||
ButtonStyled,
|
||||
ConfirmModal,
|
||||
MarkdownEditor,
|
||||
} from "@modrinth/ui";
|
||||
import {
|
||||
FileIcon,
|
||||
TrashIcon,
|
||||
@@ -649,6 +657,7 @@ import {
|
||||
ChevronRightIcon,
|
||||
} from "@modrinth/assets";
|
||||
import { Multiselect } from "vue-multiselect";
|
||||
import { formatBytes, formatCategory } from "@modrinth/utils";
|
||||
import { acceptFileFromProjectType } from "~/helpers/fileUtils.js";
|
||||
import { inferVersionInfo } from "~/helpers/infer.js";
|
||||
import { createDataPackVersion } from "~/helpers/package.js";
|
||||
@@ -656,13 +665,9 @@ import { renderHighlightedString } from "~/helpers/highlight.js";
|
||||
import { reportVersion } from "~/utils/report-helpers.ts";
|
||||
import { useImageUpload } from "~/composables/image-upload.ts";
|
||||
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import AdPlaceholder from "~/components/ui/AdPlaceholder.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import Breadcrumbs from "~/components/ui/Breadcrumbs.vue";
|
||||
import CopyCode from "~/components/ui/CopyCode.vue";
|
||||
import Categories from "~/components/ui/search/Categories.vue";
|
||||
import Checkbox from "~/components/ui/Checkbox.vue";
|
||||
import FileInput from "~/components/ui/FileInput.vue";
|
||||
import Modal from "~/components/ui/Modal.vue";
|
||||
|
||||
@@ -958,6 +963,8 @@ export default defineNuxtComponent({
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
formatBytes,
|
||||
formatCategory,
|
||||
async onImageUpload(file) {
|
||||
const response = await useImageUpload(file, { context: "version" });
|
||||
|
||||
|
||||
@@ -8,13 +8,11 @@ import {
|
||||
DownloadIcon,
|
||||
LinkIcon,
|
||||
} from "@modrinth/assets";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import { Avatar, Checkbox, Badge } from "@modrinth/ui";
|
||||
import LogoAnimated from "~/components/brand/LogoAnimated.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import PrismIcon from "~/assets/images/external/prism.svg?component";
|
||||
import ATLauncher from "~/assets/images/external/atlauncher.svg?component";
|
||||
import CurseForge from "~/assets/images/external/curseforge.svg?component";
|
||||
import Checkbox from "~/components/ui/Checkbox.vue";
|
||||
|
||||
import { homePageProjects } from "~/generated/state.json";
|
||||
|
||||
|
||||
@@ -97,7 +97,7 @@
|
||||
</template>
|
||||
<script setup>
|
||||
import { ChevronRightIcon, HistoryIcon } from "@modrinth/assets";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import { Avatar } from "@modrinth/ui";
|
||||
import NotificationItem from "~/components/ui/NotificationItem.vue";
|
||||
import { fetchExtraNotificationData, groupNotifications } from "~/helpers/notifications.ts";
|
||||
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
v-if="notifTypes.length > 1"
|
||||
v-model="selectedType"
|
||||
:items="notifTypes"
|
||||
:format-label="(x) => (x === 'all' ? 'All' : $formatProjectType(x).replace('_', ' ') + 's')"
|
||||
:format-label="(x) => (x === 'all' ? 'All' : formatProjectType(x).replace('_', ' ') + 's')"
|
||||
:capitalize="false"
|
||||
/>
|
||||
<p v-if="pending">Loading notifications...</p>
|
||||
@@ -49,13 +49,16 @@
|
||||
/>
|
||||
</template>
|
||||
<p v-else>You don't have any unread notifications.</p>
|
||||
<Pagination :page="page" :count="pages" @switch-page="changePage" />
|
||||
<div class="flex justify-end">
|
||||
<Pagination :page="page" :count="pages" @switch-page="changePage" />
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</template>
|
||||
<script setup>
|
||||
import { Button, Chips } from "@modrinth/ui";
|
||||
import { Button, Pagination, Chips } from "@modrinth/ui";
|
||||
import { HistoryIcon, CheckCheckIcon } from "@modrinth/assets";
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
import {
|
||||
fetchExtraNotificationData,
|
||||
groupNotifications,
|
||||
@@ -63,7 +66,6 @@ import {
|
||||
} from "~/helpers/notifications.ts";
|
||||
import NotificationItem from "~/components/ui/NotificationItem.vue";
|
||||
import Breadcrumbs from "~/components/ui/Breadcrumbs.vue";
|
||||
import Pagination from "~/components/ui/Pagination.vue";
|
||||
|
||||
useHead({
|
||||
title: "Notifications - Modrinth",
|
||||
|
||||
@@ -239,7 +239,7 @@
|
||||
<div>
|
||||
<nuxt-link
|
||||
tabindex="-1"
|
||||
:to="`/${$getProjectTypeForUrl(project.project_type, project.loaders)}/${
|
||||
:to="`/${getProjectTypeForUrl(project.project_type, project.loaders)}/${
|
||||
project.slug ? project.slug : project.id
|
||||
}`"
|
||||
>
|
||||
@@ -261,7 +261,7 @@
|
||||
|
||||
<nuxt-link
|
||||
class="hover-link wrap-as-needed"
|
||||
:to="`/${$getProjectTypeForUrl(project.project_type, project.loaders)}/${
|
||||
:to="`/${getProjectTypeForUrl(project.project_type, project.loaders)}/${
|
||||
project.slug ? project.slug : project.id
|
||||
}`"
|
||||
>
|
||||
@@ -275,22 +275,23 @@
|
||||
</div>
|
||||
|
||||
<div>
|
||||
{{ $formatProjectType($getProjectTypeForUrl(project.project_type, project.loaders)) }}
|
||||
{{ formatProjectType(getProjectTypeForUrl(project.project_type, project.loaders)) }}
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<Badge v-if="project.status" :type="project.status" class="status" />
|
||||
<ProjectStatusBadge v-if="project.status" :status="project.status" />
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<nuxt-link
|
||||
class="square-button"
|
||||
:to="`/${$getProjectTypeForUrl(project.project_type, project.loaders)}/${
|
||||
project.slug ? project.slug : project.id
|
||||
}/settings`"
|
||||
>
|
||||
<SettingsIcon />
|
||||
</nuxt-link>
|
||||
<ButtonStyled circular>
|
||||
<nuxt-link
|
||||
:to="`/${getProjectTypeForUrl(project.project_type, project.loaders)}/${
|
||||
project.slug ? project.slug : project.id
|
||||
}/settings`"
|
||||
>
|
||||
<SettingsIcon />
|
||||
</nuxt-link>
|
||||
</ButtonStyled>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -312,19 +313,25 @@ import {
|
||||
SortAscendingIcon as AscendingIcon,
|
||||
SortDescendingIcon as DescendingIcon,
|
||||
} from "@modrinth/assets";
|
||||
import { commonMessages } from "@modrinth/ui";
|
||||
import {
|
||||
Avatar,
|
||||
ButtonStyled,
|
||||
Checkbox,
|
||||
CopyCode,
|
||||
ProjectStatusBadge,
|
||||
commonMessages,
|
||||
} from "@modrinth/ui";
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import Checkbox from "~/components/ui/Checkbox.vue";
|
||||
import Modal from "~/components/ui/Modal.vue";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import ModalCreation from "~/components/ui/ModalCreation.vue";
|
||||
import CopyCode from "~/components/ui/CopyCode.vue";
|
||||
import { getProjectTypeForUrl } from "~/helpers/projects.js";
|
||||
|
||||
export default defineNuxtComponent({
|
||||
components: {
|
||||
Avatar,
|
||||
Badge,
|
||||
ButtonStyled,
|
||||
ProjectStatusBadge,
|
||||
SettingsIcon,
|
||||
TrashIcon,
|
||||
Checkbox,
|
||||
@@ -390,6 +397,8 @@ export default defineNuxtComponent({
|
||||
this.DELETE_PROJECT = 1 << 7;
|
||||
},
|
||||
methods: {
|
||||
getProjectTypeForUrl,
|
||||
formatProjectType,
|
||||
updateDescending() {
|
||||
this.descending = !this.descending;
|
||||
this.projects = this.updateSort(this.projects, this.sortBy, this.descending);
|
||||
|
||||
@@ -76,7 +76,7 @@
|
||||
</span>
|
||||
<template v-if="payout.method">
|
||||
<span>⋅</span>
|
||||
<span>{{ $formatWallet(payout.method) }} ({{ payout.method_address }})</span>
|
||||
<span>{{ formatWallet(payout.method) }} ({{ payout.method_address }})</span>
|
||||
</template>
|
||||
</div>
|
||||
</div>
|
||||
@@ -95,7 +95,7 @@
|
||||
</template>
|
||||
<script setup>
|
||||
import { XIcon, PayPalIcon, UnknownIcon } from "@modrinth/assets";
|
||||
import { capitalizeString } from "@modrinth/utils";
|
||||
import { capitalizeString, formatWallet } from "@modrinth/utils";
|
||||
import { Badge, Breadcrumbs, DropdownSelect } from "@modrinth/ui";
|
||||
import dayjs from "dayjs";
|
||||
import TremendousIcon from "~/assets/images/external/tremendous.svg?component";
|
||||
|
||||
@@ -139,8 +139,8 @@
|
||||
<template v-if="knownErrors.length === 0 && amount">
|
||||
<Checkbox v-if="fees > 0" v-model="agreedFees" description="Consent to fee">
|
||||
I acknowledge that an estimated
|
||||
{{ $formatMoney(fees) }} will be deducted from the amount I receive to cover
|
||||
{{ $formatWallet(selectedMethod.type) }} processing fees.
|
||||
{{ formatMoney(fees) }} will be deducted from the amount I receive to cover
|
||||
{{ formatWallet(selectedMethod.type) }} processing fees.
|
||||
</Checkbox>
|
||||
<Checkbox v-model="agreedTransfer" description="Confirm transfer">
|
||||
<template v-if="selectedMethod.type === 'tremendous'">
|
||||
@@ -149,7 +149,7 @@
|
||||
</template>
|
||||
<template v-else>
|
||||
I confirm that I am initiating a transfer to the following
|
||||
{{ $formatWallet(selectedMethod.type) }} account: {{ withdrawAccount }}
|
||||
{{ formatWallet(selectedMethod.type) }} account: {{ withdrawAccount }}
|
||||
</template>
|
||||
</Checkbox>
|
||||
<Checkbox v-model="agreedTerms" class="rewards-checkbox">
|
||||
@@ -198,6 +198,7 @@ import {
|
||||
} from "@modrinth/assets";
|
||||
import { Chips, Checkbox, Breadcrumbs } from "@modrinth/ui";
|
||||
import { all } from "iso-3166-1";
|
||||
import { formatMoney, formatWallet } from "@modrinth/utils";
|
||||
import VenmoIcon from "~/assets/images/external/venmo.svg?component";
|
||||
|
||||
const auth = await useAuth();
|
||||
@@ -360,9 +361,7 @@ async function withdraw() {
|
||||
text:
|
||||
selectedMethod.value.type === "tremendous"
|
||||
? "An email has been sent to your account with further instructions on how to redeem your payout!"
|
||||
: `Payment has been sent to your ${data.$formatWallet(
|
||||
selectedMethod.value.type,
|
||||
)} account!`,
|
||||
: `Payment has been sent to your ${formatWallet(selectedMethod.value.type)} account!`,
|
||||
type: "success",
|
||||
});
|
||||
} catch (err) {
|
||||
|
||||
@@ -527,7 +527,7 @@
|
||||
</template>
|
||||
<script setup>
|
||||
import { Multiselect } from "vue-multiselect";
|
||||
import { ButtonStyled, useRelativeTime } from "@modrinth/ui";
|
||||
import { Avatar, ButtonStyled, useRelativeTime } from "@modrinth/ui";
|
||||
import {
|
||||
CompassIcon,
|
||||
LogInIcon,
|
||||
@@ -539,7 +539,6 @@ import {
|
||||
} from "@modrinth/assets";
|
||||
import PrismLauncherLogo from "~/assets/images/external/prism.svg?component";
|
||||
import ATLauncherLogo from "~/assets/images/external/atlauncher.svg?component";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import ProjectCard from "~/components/ui/ProjectCard.vue";
|
||||
|
||||
import { homePageProjects, homePageSearch, homePageNotifs } from "~/generated/state.json";
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
</div>
|
||||
</template>
|
||||
<script setup>
|
||||
import { formatNumber } from "~/plugins/shorthands.js";
|
||||
import { formatNumber } from "@modrinth/utils";
|
||||
|
||||
useHead({
|
||||
title: "Staff overview - Modrinth",
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
<Chips
|
||||
v-model="projectType"
|
||||
:items="projectTypes"
|
||||
:format-label="(x) => (x === 'all' ? 'All' : $formatProjectType(x) + 's')"
|
||||
:format-label="(x) => (x === 'all' ? 'All' : formatProjectType(x) + 's')"
|
||||
/>
|
||||
<button v-if="oldestFirst" class="iconified-button push-right" @click="oldestFirst = false">
|
||||
<SortDescendingIcon />
|
||||
@@ -56,7 +56,7 @@
|
||||
<Avatar :src="project.icon_url" size="xs" no-shadow raised />
|
||||
<span class="stacked">
|
||||
<span class="title">{{ project.name }}</span>
|
||||
<span>{{ $formatProjectType(project.inferred_project_type) }}</span>
|
||||
<span>{{ formatProjectType(project.inferred_project_type) }}</span>
|
||||
</span>
|
||||
</nuxt-link>
|
||||
</div>
|
||||
@@ -81,7 +81,9 @@
|
||||
</div>
|
||||
<div class="mobile-row">
|
||||
is requesting to be
|
||||
<Badge :type="project.requested_status ? project.requested_status : 'approved'" />
|
||||
<ProjectStatusBadge
|
||||
:status="project.requested_status ? project.requested_status : 'approved'"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div class="input-group">
|
||||
@@ -103,7 +105,7 @@
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { Chips, useRelativeTime } from "@modrinth/ui";
|
||||
import { Avatar, ProjectStatusBadge, Chips, useRelativeTime } from "@modrinth/ui";
|
||||
import {
|
||||
UnknownIcon,
|
||||
EyeIcon,
|
||||
@@ -112,9 +114,7 @@ import {
|
||||
IssuesIcon,
|
||||
ScaleIcon,
|
||||
} from "@modrinth/assets";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import Badge from "~/components/ui/Badge.vue";
|
||||
import { formatProjectType } from "~/plugins/shorthands.js";
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
import { asEncodedJsonArray, fetchSegmented } from "~/utils/fetch-helpers.ts";
|
||||
|
||||
useHead({
|
||||
|
||||
@@ -272,7 +272,7 @@
|
||||
<div class="table-cell">
|
||||
<BoxIcon />
|
||||
<span>{{
|
||||
$formatProjectType(
|
||||
formatProjectType(
|
||||
$getProjectTypeForDisplay(project.project_types[0] ?? "project", project.loaders),
|
||||
)
|
||||
}}</span>
|
||||
@@ -313,6 +313,7 @@ import {
|
||||
} from "@modrinth/assets";
|
||||
import { Button, Modal, Avatar, CopyCode, Badge, Checkbox, commonMessages } from "@modrinth/ui";
|
||||
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
import ModalCreation from "~/components/ui/ModalCreation.vue";
|
||||
import OrganizationProjectTransferModal from "~/components/ui/OrganizationProjectTransferModal.vue";
|
||||
|
||||
|
||||
@@ -520,7 +520,6 @@ async function serverInstall(project) {
|
||||
|
||||
if (projectType.value.id === "modpack") {
|
||||
await server.value.general.reinstall(
|
||||
server.value.serverId,
|
||||
false,
|
||||
project.project_id,
|
||||
version.id,
|
||||
|
||||
@@ -18,48 +18,25 @@
|
||||
v-if="serverData?.status === 'suspended' && serverData.suspension_reason === 'upgrading'"
|
||||
class="flex min-h-[calc(100vh-4rem)] items-center justify-center text-contrast"
|
||||
>
|
||||
<div class="flex max-w-lg flex-col items-center rounded-3xl bg-bg-raised p-6 shadow-xl">
|
||||
<div class="flex flex-col items-center text-center">
|
||||
<div class="flex flex-col items-center gap-4">
|
||||
<div class="grid place-content-center rounded-full bg-bg-blue p-4">
|
||||
<TransferIcon class="size-12 text-blue" />
|
||||
</div>
|
||||
<h1 class="m-0 mb-2 w-fit text-4xl font-bold">Server upgrading</h1>
|
||||
</div>
|
||||
<p class="text-lg text-secondary">
|
||||
Your server's hardware is currently being upgraded and will be back online shortly!
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<ErrorInformationCard
|
||||
title="Server upgrading"
|
||||
description="Your server's hardware is currently being upgraded and will be back online shortly!"
|
||||
:icon="TransferIcon"
|
||||
icon-color="blue"
|
||||
:action="generalErrorAction"
|
||||
/>
|
||||
</div>
|
||||
<div
|
||||
v-else-if="serverData?.status === 'suspended'"
|
||||
class="flex min-h-[calc(100vh-4rem)] items-center justify-center text-contrast"
|
||||
>
|
||||
<div class="flex max-w-lg flex-col items-center rounded-3xl bg-bg-raised p-6 shadow-xl">
|
||||
<div class="flex flex-col items-center text-center">
|
||||
<div class="flex flex-col items-center gap-4">
|
||||
<div class="grid place-content-center rounded-full bg-bg-orange p-4">
|
||||
<LockIcon class="size-12 text-orange" />
|
||||
</div>
|
||||
<h1 class="m-0 mb-2 w-fit text-4xl font-bold">Server suspended</h1>
|
||||
</div>
|
||||
<p class="text-lg text-secondary">
|
||||
{{
|
||||
serverData.suspension_reason === "cancelled"
|
||||
? "Your subscription has been cancelled."
|
||||
: serverData.suspension_reason
|
||||
? `Your server has been suspended: ${serverData.suspension_reason}`
|
||||
: "Your server has been suspended."
|
||||
}}
|
||||
<br />
|
||||
Contact Modrinth Support if you believe this is an error.
|
||||
</p>
|
||||
</div>
|
||||
<ButtonStyled size="large" color="brand" @click="() => router.push('/settings/billing')">
|
||||
<button class="mt-6 !w-full">Go to billing settings</button>
|
||||
</ButtonStyled>
|
||||
</div>
|
||||
<ErrorInformationCard
|
||||
title="Server suspended"
|
||||
:description="suspendedDescription"
|
||||
:icon="LockIcon"
|
||||
icon-color="orange"
|
||||
:action="suspendedAction"
|
||||
/>
|
||||
</div>
|
||||
<div
|
||||
v-else-if="
|
||||
@@ -68,110 +45,69 @@
|
||||
"
|
||||
class="flex min-h-[calc(100vh-4rem)] items-center justify-center text-contrast"
|
||||
>
|
||||
<div class="flex max-w-lg flex-col items-center rounded-3xl bg-bg-raised p-6 shadow-xl">
|
||||
<div class="flex flex-col items-center text-center">
|
||||
<div class="flex flex-col items-center gap-4">
|
||||
<div class="grid place-content-center rounded-full bg-bg-orange p-4">
|
||||
<TransferIcon class="size-12 text-orange" />
|
||||
</div>
|
||||
<h1 class="m-0 mb-2 w-fit text-4xl font-bold">Server not found</h1>
|
||||
</div>
|
||||
<p class="text-lg text-secondary">
|
||||
You don't have permission to view this server or it no longer exists. If you believe this
|
||||
is an error, please contact Modrinth Support.
|
||||
</p>
|
||||
</div>
|
||||
<UiCopyCode :text="JSON.stringify(server.moduleErrors?.general?.error)" />
|
||||
|
||||
<ButtonStyled size="large" color="brand" @click="() => router.push('/servers/manage')">
|
||||
<button class="mt-6 !w-full">Go back to all servers</button>
|
||||
</ButtonStyled>
|
||||
</div>
|
||||
<ErrorInformationCard
|
||||
title="An error occured."
|
||||
description="Please contact Modrinth Support."
|
||||
:icon="TransferIcon"
|
||||
icon-color="orange"
|
||||
:error-details="generalErrorDetails"
|
||||
:action="generalErrorAction"
|
||||
/>
|
||||
</div>
|
||||
<div
|
||||
v-else-if="server.moduleErrors?.general?.error.statusCode === 503"
|
||||
class="flex min-h-[calc(100vh-4rem)] items-center justify-center text-contrast"
|
||||
>
|
||||
<div class="flex max-w-lg flex-col items-center rounded-3xl bg-bg-raised p-6 shadow-xl">
|
||||
<div class="flex flex-col items-center text-center">
|
||||
<div class="flex flex-col items-center gap-4">
|
||||
<div class="grid place-content-center rounded-full bg-bg-red p-4">
|
||||
<UiServersIconsPanelErrorIcon class="size-12 text-red" />
|
||||
</div>
|
||||
<h1 class="m-0 mb-4 w-fit text-4xl font-bold">Server Node Unavailable</h1>
|
||||
<ErrorInformationCard
|
||||
title="Server Node Unavailable"
|
||||
:icon="PanelErrorIcon"
|
||||
icon-color="red"
|
||||
:action="nodeUnavailableAction"
|
||||
:error-details="nodeUnavailableDetails"
|
||||
>
|
||||
<template #description>
|
||||
<div class="text-md space-y-4">
|
||||
<p class="leading-[170%] text-secondary">
|
||||
Your server's node, where your Modrinth Server is physically hosted, is experiencing
|
||||
issues. We are working with our datacenter to resolve the issue as quickly as possible.
|
||||
</p>
|
||||
<p class="leading-[170%] text-secondary">
|
||||
Your data is safe and will not be lost, and your server will be back online as soon as
|
||||
the issue is resolved.
|
||||
</p>
|
||||
<p class="leading-[170%] text-secondary">
|
||||
For updates, please join the Modrinth Discord or contact Modrinth Support via the chat
|
||||
bubble in the bottom right corner and we'll be happy to help.
|
||||
</p>
|
||||
</div>
|
||||
<p class="m-0 mb-4 leading-[170%] text-secondary">
|
||||
Your server's node, where your Modrinth Server is physically hosted, is experiencing
|
||||
issues. We are working with our datacenter to resolve the issue as quickly as possible.
|
||||
</p>
|
||||
<p class="m-0 mb-4 leading-[170%] text-secondary">
|
||||
Your data is safe and will not be lost, and your server will be back online as soon as the
|
||||
issue is resolved.
|
||||
</p>
|
||||
<p class="m-0 mb-4 leading-[170%] text-secondary">
|
||||
For updates, please join the Modrinth Discord or contact Modrinth Support via the chat
|
||||
bubble in the bottom right corner and we'll be happy to help.
|
||||
</p>
|
||||
|
||||
<div class="flex flex-col gap-2">
|
||||
<UiCopyCode :text="'Server ID: ' + server.serverId" />
|
||||
<UiCopyCode :text="'Node: ' + server.general?.datacenter" />
|
||||
</div>
|
||||
</div>
|
||||
<ButtonStyled
|
||||
size="large"
|
||||
color="standard"
|
||||
@click="
|
||||
() =>
|
||||
navigateTo('https://discord.modrinth.com', {
|
||||
external: true,
|
||||
})
|
||||
"
|
||||
>
|
||||
<button class="mt-6 !w-full">Join Modrinth Discord</button>
|
||||
</ButtonStyled>
|
||||
<ButtonStyled
|
||||
:disabled="formattedTime !== '00'"
|
||||
size="large"
|
||||
color="standard"
|
||||
@click="() => reloadNuxtApp()"
|
||||
>
|
||||
<button class="mt-3 !w-full">Reload</button>
|
||||
</ButtonStyled>
|
||||
</div>
|
||||
</template>
|
||||
</ErrorInformationCard>
|
||||
</div>
|
||||
<div
|
||||
v-else-if="server.moduleErrors?.general?.error"
|
||||
class="flex min-h-[calc(100vh-4rem)] items-center justify-center text-contrast"
|
||||
>
|
||||
<div class="flex max-w-lg flex-col items-center rounded-3xl bg-bg-raised p-6 shadow-xl">
|
||||
<div class="flex flex-col items-center text-center">
|
||||
<div class="flex flex-col items-center gap-4">
|
||||
<div class="grid place-content-center rounded-full bg-bg-orange p-4">
|
||||
<TransferIcon class="size-12 text-orange" />
|
||||
</div>
|
||||
<h1 class="m-0 mb-2 w-fit text-4xl font-bold">Connection lost</h1>
|
||||
<ErrorInformationCard
|
||||
title="Connection lost"
|
||||
description=""
|
||||
:icon="TransferIcon"
|
||||
icon-color="orange"
|
||||
:action="connectionLostAction"
|
||||
>
|
||||
<template #description>
|
||||
<div class="space-y-4">
|
||||
<div class="text-center text-secondary">
|
||||
{{
|
||||
formattedTime == "00" ? "Reconnecting..." : `Retrying in ${formattedTime} seconds...`
|
||||
}}
|
||||
</div>
|
||||
<p class="text-lg text-secondary">
|
||||
Something went wrong, and we couldn't connect to your server. This is likely due to a
|
||||
temporary network issue. You'll be reconnected automatically.
|
||||
</p>
|
||||
</div>
|
||||
<p class="text-lg text-secondary">
|
||||
Something went wrong, and we couldn't connect to your server. This is likely due to a
|
||||
temporary network issue. You'll be reconnected automatically.
|
||||
</p>
|
||||
</div>
|
||||
<UiCopyCode :text="JSON.stringify(server.moduleErrors?.general?.error)" />
|
||||
<ButtonStyled
|
||||
:disabled="formattedTime !== '00'"
|
||||
size="large"
|
||||
color="brand"
|
||||
@click="() => reloadNuxtApp()"
|
||||
>
|
||||
<button class="mt-6 !w-full">Reload</button>
|
||||
</ButtonStyled>
|
||||
</div>
|
||||
</template>
|
||||
</ErrorInformationCard>
|
||||
</div>
|
||||
<!-- SERVER START -->
|
||||
<div
|
||||
@@ -432,7 +368,7 @@ import {
|
||||
LockIcon,
|
||||
} from "@modrinth/assets";
|
||||
import DOMPurify from "dompurify";
|
||||
import { ButtonStyled, ServerNotice } from "@modrinth/ui";
|
||||
import { ButtonStyled, ErrorInformationCard, ServerNotice } from "@modrinth/ui";
|
||||
import { Intercom, shutdown } from "@intercom/messenger-js-sdk";
|
||||
import type { MessageDescriptor } from "@vintl/vintl";
|
||||
import type {
|
||||
@@ -448,6 +384,7 @@ import { useModrinthServersConsole } from "~/store/console.ts";
|
||||
import { useServersFetch } from "~/composables/servers/servers-fetch.ts";
|
||||
import { ModrinthServer, useModrinthServers } from "~/composables/servers/modrinth-servers.ts";
|
||||
import ServerInstallation from "~/components/ui/servers/ServerInstallation.vue";
|
||||
import PanelErrorIcon from "~/components/ui/servers/icons/PanelErrorIcon.vue";
|
||||
|
||||
const app = useNuxtApp() as unknown as { $notify: any };
|
||||
|
||||
@@ -760,7 +697,7 @@ const startUptimeUpdates = () => {
|
||||
const stopUptimeUpdates = () => {
|
||||
if (uptimeIntervalId) {
|
||||
clearInterval(uptimeIntervalId);
|
||||
intervalId = null;
|
||||
pollingIntervalId = null;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -1055,7 +992,7 @@ const notifyError = (title: string, text: string) => {
|
||||
});
|
||||
};
|
||||
|
||||
let intervalId: ReturnType<typeof setInterval> | null = null;
|
||||
let pollingIntervalId: ReturnType<typeof setInterval> | null = null;
|
||||
const countdown = ref(15);
|
||||
|
||||
const formattedTime = computed(() => {
|
||||
@@ -1099,23 +1036,142 @@ const backupInProgress = computed(() => {
|
||||
});
|
||||
|
||||
const stopPolling = () => {
|
||||
if (intervalId) {
|
||||
clearInterval(intervalId);
|
||||
intervalId = null;
|
||||
if (pollingIntervalId) {
|
||||
clearTimeout(pollingIntervalId);
|
||||
pollingIntervalId = null;
|
||||
}
|
||||
};
|
||||
|
||||
const startPolling = () => {
|
||||
countdown.value = 15;
|
||||
intervalId = setInterval(() => {
|
||||
if (countdown.value <= 0) {
|
||||
reloadNuxtApp();
|
||||
} else {
|
||||
countdown.value--;
|
||||
stopPolling();
|
||||
|
||||
let retryCount = 0;
|
||||
const maxRetries = 10;
|
||||
|
||||
const poll = async () => {
|
||||
try {
|
||||
await server.refresh(["general", "ws"]);
|
||||
|
||||
if (!server.moduleErrors?.general?.error) {
|
||||
stopPolling();
|
||||
connectWebSocket();
|
||||
return;
|
||||
}
|
||||
|
||||
retryCount++;
|
||||
if (retryCount >= maxRetries) {
|
||||
console.error("Max retries reached, stopping polling");
|
||||
stopPolling();
|
||||
return;
|
||||
}
|
||||
|
||||
// Exponential backoff: 3s, 6s, 12s, 24s, etc.
|
||||
const delay = Math.min(3000 * Math.pow(2, retryCount - 1), 60000);
|
||||
|
||||
pollingIntervalId = setTimeout(poll, delay);
|
||||
} catch (error) {
|
||||
console.error("Polling failed:", error);
|
||||
retryCount++;
|
||||
|
||||
if (retryCount < maxRetries) {
|
||||
const delay = Math.min(3000 * Math.pow(2, retryCount - 1), 60000);
|
||||
pollingIntervalId = setTimeout(poll, delay);
|
||||
}
|
||||
}
|
||||
}, 1000);
|
||||
};
|
||||
|
||||
poll();
|
||||
};
|
||||
|
||||
const nodeUnavailableDetails = computed(() => [
|
||||
{
|
||||
label: "Server ID",
|
||||
value: server.serverId,
|
||||
type: "inline" as const,
|
||||
},
|
||||
{
|
||||
label: "Node",
|
||||
value: server.general?.datacenter ?? "Unknown! Please contact support!",
|
||||
type: "inline" as const,
|
||||
},
|
||||
]);
|
||||
|
||||
const suspendedDescription = computed(() => {
|
||||
if (serverData.value?.suspension_reason === "cancelled") {
|
||||
return "Your subscription has been cancelled.\nContact Modrinth Support if you believe this is an error.";
|
||||
}
|
||||
if (serverData.value?.suspension_reason) {
|
||||
return `Your server has been suspended: ${serverData.value.suspension_reason}\nContact Modrinth Support if you believe this is an error.`;
|
||||
}
|
||||
return "Your server has been suspended.\nContact Modrinth Support if you believe this is an error.";
|
||||
});
|
||||
|
||||
const generalErrorDetails = computed(() => [
|
||||
{
|
||||
label: "Server ID",
|
||||
value: server.serverId,
|
||||
type: "inline" as const,
|
||||
},
|
||||
{
|
||||
label: "Timestamp",
|
||||
value: String(server.moduleErrors?.general?.timestamp),
|
||||
type: "inline" as const,
|
||||
},
|
||||
{
|
||||
label: "Error Name",
|
||||
value: server.moduleErrors?.general?.error.name,
|
||||
type: "inline" as const,
|
||||
},
|
||||
{
|
||||
label: "Error Message",
|
||||
value: server.moduleErrors?.general?.error.message,
|
||||
type: "block" as const,
|
||||
},
|
||||
...(server.moduleErrors?.general?.error.originalError
|
||||
? [
|
||||
{
|
||||
label: "Original Error",
|
||||
value: String(server.moduleErrors.general.error.originalError),
|
||||
type: "hidden" as const,
|
||||
},
|
||||
]
|
||||
: []),
|
||||
...(server.moduleErrors?.general?.error.stack
|
||||
? [
|
||||
{
|
||||
label: "Stack Trace",
|
||||
value: server.moduleErrors.general.error.stack,
|
||||
type: "hidden" as const,
|
||||
},
|
||||
]
|
||||
: []),
|
||||
]);
|
||||
|
||||
const suspendedAction = computed(() => ({
|
||||
label: "Go to billing settings",
|
||||
onClick: () => router.push("/settings/billing"),
|
||||
color: "brand" as const,
|
||||
}));
|
||||
|
||||
const generalErrorAction = computed(() => ({
|
||||
label: "Go back to all servers",
|
||||
onClick: () => router.push("/servers/manage"),
|
||||
color: "brand" as const,
|
||||
}));
|
||||
|
||||
const nodeUnavailableAction = computed(() => ({
|
||||
label: "Join Modrinth Discord",
|
||||
onClick: () => navigateTo("https://discord.modrinth.com", { external: true }),
|
||||
color: "standard" as const,
|
||||
}));
|
||||
|
||||
const connectionLostAction = computed(() => ({
|
||||
label: "Reload",
|
||||
onClick: () => reloadNuxtApp(),
|
||||
color: "brand" as const,
|
||||
disabled: formattedTime.value !== "00",
|
||||
}));
|
||||
|
||||
const copyServerDebugInfo = () => {
|
||||
const debugInfo = `Server ID: ${serverData.value?.server_id}\nError: ${errorMessage.value}\nKind: ${serverData.value?.upstream?.kind}\nProject ID: ${serverData.value?.upstream?.project_id}\nVersion ID: ${serverData.value?.upstream?.version_id}\nLog: ${errorLog.value}`;
|
||||
navigator.clipboard.writeText(debugInfo);
|
||||
|
||||
@@ -155,26 +155,18 @@ const saveGeneral = async () => {
|
||||
if (serverSubdomain.value !== data.value?.net?.domain) {
|
||||
try {
|
||||
// type shit backend makes me do
|
||||
const response = await props.server.network?.checkSubdomainAvailability(
|
||||
const available = await props.server.network?.checkSubdomainAvailability(
|
||||
serverSubdomain.value,
|
||||
);
|
||||
if (response === undefined) {
|
||||
throw new Error("Failed to check subdomain availability");
|
||||
}
|
||||
|
||||
if (typeof response === "object" && response !== null && "available" in response) {
|
||||
const typedResponse = response as { available: boolean };
|
||||
if (!typedResponse.available) {
|
||||
addNotification({
|
||||
group: "serverOptions",
|
||||
type: "error",
|
||||
title: "Subdomain not available",
|
||||
text: "The subdomain you entered is already in use.",
|
||||
});
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
throw new Error("Invalid response format from availability check");
|
||||
if (!available) {
|
||||
addNotification({
|
||||
group: "serverOptions",
|
||||
type: "error",
|
||||
title: "Subdomain not available",
|
||||
text: "The subdomain you entered is already in use.",
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
await props.server.network?.changeSubdomain(serverSubdomain.value);
|
||||
|
||||
@@ -330,8 +330,7 @@
|
||||
<ButtonStyled
|
||||
v-if="
|
||||
getPyroCharge(subscription) &&
|
||||
getPyroCharge(subscription).status !== 'cancelled' &&
|
||||
getPyroCharge(subscription).status !== 'failed'
|
||||
getPyroCharge(subscription).status !== 'cancelled'
|
||||
"
|
||||
>
|
||||
<button @click="showCancellationSurvey(subscription)">
|
||||
|
||||
@@ -200,9 +200,9 @@
|
||||
<script setup lang="ts">
|
||||
import { CodeIcon, RadioButtonCheckedIcon, RadioButtonIcon } from "@modrinth/assets";
|
||||
import { Button, ThemeSelector } from "@modrinth/ui";
|
||||
import { formatProjectType } from "@modrinth/utils";
|
||||
import MessageBanner from "~/components/ui/MessageBanner.vue";
|
||||
import type { DisplayLocation } from "~/plugins/cosmetics";
|
||||
import { formatProjectType } from "~/plugins/shorthands.js";
|
||||
import { isDarkTheme, type Theme } from "~/plugins/theme/index.ts";
|
||||
|
||||
useHead({
|
||||
|
||||
@@ -205,6 +205,7 @@
|
||||
import { PlusIcon, XIcon, TrashIcon, EditIcon, SaveIcon } from "@modrinth/assets";
|
||||
import {
|
||||
Checkbox,
|
||||
CopyCode,
|
||||
ConfirmModal,
|
||||
commonSettingsMessages,
|
||||
commonMessages,
|
||||
@@ -219,7 +220,6 @@ import {
|
||||
getScopeValue,
|
||||
} from "~/composables/auth/scopes.ts";
|
||||
|
||||
import CopyCode from "~/components/ui/CopyCode.vue";
|
||||
import Modal from "~/components/ui/Modal.vue";
|
||||
|
||||
const { formatMessage } = useVIntl();
|
||||
|
||||
@@ -355,6 +355,7 @@ import {
|
||||
GlobeIcon,
|
||||
} from "@modrinth/assets";
|
||||
import {
|
||||
Avatar,
|
||||
OverflowMenu,
|
||||
ButtonStyled,
|
||||
ContentPageHeader,
|
||||
@@ -377,7 +378,6 @@ import BetaTesterBadge from "~/assets/images/badges/beta-tester.svg?component";
|
||||
|
||||
import UpToDate from "~/assets/images/illustrations/up_to_date.svg?component";
|
||||
import ModalCreation from "~/components/ui/ModalCreation.vue";
|
||||
import Avatar from "~/components/ui/Avatar.vue";
|
||||
import CollectionCreateModal from "~/components/ui/CollectionCreateModal.vue";
|
||||
import AdPlaceholder from "~/components/ui/AdPlaceholder.vue";
|
||||
|
||||
|
||||
@@ -13,11 +13,6 @@ export default defineNuxtPlugin((nuxtApp) => {
|
||||
|
||||
return cosmeticsStore.externalLinksNewTab ? "_blank" : "";
|
||||
});
|
||||
nuxtApp.provide("formatBytes", formatBytes);
|
||||
nuxtApp.provide("formatWallet", formatWallet);
|
||||
nuxtApp.provide("formatProjectType", formatProjectType);
|
||||
nuxtApp.provide("formatCategory", formatCategory);
|
||||
nuxtApp.provide("formatCategoryHeader", formatCategoryHeader);
|
||||
|
||||
/*
|
||||
Only use on the complete list of versions for a project, partial lists will generate
|
||||
@@ -156,89 +151,10 @@ export const formatMoney = (number, abbreviate = false) => {
|
||||
}
|
||||
};
|
||||
|
||||
export const formatBytes = (bytes, decimals = 2) => {
|
||||
if (bytes === 0) {
|
||||
return "0 Bytes";
|
||||
}
|
||||
|
||||
const k = 1024;
|
||||
const dm = decimals < 0 ? 0 : decimals;
|
||||
const sizes = ["Bytes", "KiB", "MiB", "GiB"];
|
||||
|
||||
const i = Math.floor(Math.log(bytes) / Math.log(k));
|
||||
|
||||
return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + " " + sizes[i];
|
||||
};
|
||||
|
||||
export const capitalizeString = (name) => {
|
||||
return name ? name.charAt(0).toUpperCase() + name.slice(1) : name;
|
||||
};
|
||||
|
||||
export const formatWallet = (name) => {
|
||||
if (name === "paypal") {
|
||||
return "PayPal";
|
||||
}
|
||||
return capitalizeString(name);
|
||||
};
|
||||
|
||||
export const formatProjectType = (name) => {
|
||||
if (name === "resourcepack") {
|
||||
return "Resource Pack";
|
||||
} else if (name === "datapack") {
|
||||
return "Data Pack";
|
||||
}
|
||||
|
||||
return capitalizeString(name);
|
||||
};
|
||||
|
||||
export const formatCategory = (name) => {
|
||||
if (name === "modloader") {
|
||||
return "Risugami's ModLoader";
|
||||
} else if (name === "bungeecord") {
|
||||
return "BungeeCord";
|
||||
} else if (name === "liteloader") {
|
||||
return "LiteLoader";
|
||||
} else if (name === "neoforge") {
|
||||
return "NeoForge";
|
||||
} else if (name === "game-mechanics") {
|
||||
return "Game Mechanics";
|
||||
} else if (name === "worldgen") {
|
||||
return "World Generation";
|
||||
} else if (name === "core-shaders") {
|
||||
return "Core Shaders";
|
||||
} else if (name === "gui") {
|
||||
return "GUI";
|
||||
} else if (name === "8x-") {
|
||||
return "8x or lower";
|
||||
} else if (name === "512x+") {
|
||||
return "512x or higher";
|
||||
} else if (name === "kitchen-sink") {
|
||||
return "Kitchen Sink";
|
||||
} else if (name === "path-tracing") {
|
||||
return "Path Tracing";
|
||||
} else if (name === "pbr") {
|
||||
return "PBR";
|
||||
} else if (name === "datapack") {
|
||||
return "Data Pack";
|
||||
} else if (name === "colored-lighting") {
|
||||
return "Colored Lighting";
|
||||
} else if (name === "optifine") {
|
||||
return "OptiFine";
|
||||
} else if (name === "mrpack") {
|
||||
return "Modpack";
|
||||
} else if (name === "minecraft") {
|
||||
return "Resource Pack";
|
||||
} else if (name === "vanilla") {
|
||||
return "Vanilla Shader";
|
||||
}
|
||||
|
||||
return capitalizeString(name);
|
||||
};
|
||||
|
||||
export const formatCategoryHeader = (name) => {
|
||||
return capitalizeString(name);
|
||||
};
|
||||
|
||||
export const formatVersions = (tag, versionArray) => {
|
||||
const allVersions = tag.value.gameVersions.slice().reverse();
|
||||
const allReleases = allVersions.filter((x) => x.version_type === "release");
|
||||
|
||||
@@ -3,7 +3,8 @@ RUST_LOG=info,sqlx::query=warn
|
||||
SENTRY_DSN=none
|
||||
|
||||
SITE_URL=http://localhost:3000
|
||||
CDN_URL=https://staging-cdn.modrinth.com
|
||||
# This CDN URL matches the local storage backend set below, which uses MOCK_FILE_PATH
|
||||
CDN_URL=file:///tmp/modrinth
|
||||
LABRINTH_ADMIN_KEY=feedbeef
|
||||
RATE_LIMIT_IGNORE_KEY=feedbeef
|
||||
|
||||
@@ -25,18 +26,21 @@ PUBLIC_DISCORD_WEBHOOK=
|
||||
CLOUDFLARE_INTEGRATION=false
|
||||
|
||||
STORAGE_BACKEND=local
|
||||
|
||||
MOCK_FILE_PATH=/tmp/modrinth
|
||||
|
||||
BACKBLAZE_KEY_ID=none
|
||||
BACKBLAZE_KEY=none
|
||||
BACKBLAZE_BUCKET_ID=none
|
||||
S3_PUBLIC_BUCKET_NAME=none
|
||||
S3_PUBLIC_USES_PATH_STYLE_BUCKET=false
|
||||
S3_PUBLIC_REGION=none
|
||||
S3_PUBLIC_URL=none
|
||||
S3_PUBLIC_ACCESS_TOKEN=none
|
||||
S3_PUBLIC_SECRET=none
|
||||
|
||||
S3_ACCESS_TOKEN=none
|
||||
S3_SECRET=none
|
||||
S3_URL=none
|
||||
S3_REGION=none
|
||||
S3_BUCKET_NAME=none
|
||||
S3_PRIVATE_BUCKET_NAME=none
|
||||
S3_PRIVATE_USES_PATH_STYLE_BUCKET=false
|
||||
S3_PRIVATE_REGION=none
|
||||
S3_PRIVATE_URL=none
|
||||
S3_PRIVATE_ACCESS_TOKEN=none
|
||||
S3_PRIVATE_SECRET=none
|
||||
|
||||
# 1 hour
|
||||
LOCAL_INDEX_INTERVAL=3600
|
||||
|
||||
@@ -1,14 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET moderation_message = NULL, moderation_message_body = NULL, queued = NOW()\n WHERE (id = $1)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "010cafcafb6adc25b00e3c81d844736b0245e752a90334c58209d8a02536c800"
|
||||
}
|
||||
16
apps/labrinth/.sqlx/query-09ebec1a568edf1959f20b33d8ba2b8edb55d93ada8f2243448865163f555d8d.json
generated
Normal file
16
apps/labrinth/.sqlx/query-09ebec1a568edf1959f20b33d8ba2b8edb55d93ada8f2243448865163f555d8d.json
generated
Normal file
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n INSERT INTO shared_instance_users (user_id, shared_instance_id, permissions)\n VALUES ($1, $2, $3)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"Int8",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "09ebec1a568edf1959f20b33d8ba2b8edb55d93ada8f2243448865163f555d8d"
|
||||
}
|
||||
@@ -1,14 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET webhook_sent = TRUE\n WHERE id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "124fbf0544ea6989d6dc5e840405dbc76d7385276a38ad79d9093c53c73bbde2"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n DELETE FROM mods_links\n WHERE joining_mod_id = $1 AND joining_platform_id IN (\n SELECT id FROM link_platforms WHERE name = ANY($2)\n )\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"TextArray"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "186d0e933ece20163915926293a01754ff571de4f06e521bb4f7c0207268e03b"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET license = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "19dc22c4d6d14222f8e8bace74c2961761c53b7375460ade15af921754d5d7da"
|
||||
}
|
||||
46
apps/labrinth/.sqlx/query-1ebe19b7b4f10039065967a0b1ca4bb38acc54e4ea5de020fffef7457000fa6e.json
generated
Normal file
46
apps/labrinth/.sqlx/query-1ebe19b7b4f10039065967a0b1ca4bb38acc54e4ea5de020fffef7457000fa6e.json
generated
Normal file
@@ -0,0 +1,46 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT id, title, owner_id, public, current_version_id\n FROM shared_instances\n WHERE id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 1,
|
||||
"name": "title",
|
||||
"type_info": "Varchar"
|
||||
},
|
||||
{
|
||||
"ordinal": 2,
|
||||
"name": "owner_id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 3,
|
||||
"name": "public",
|
||||
"type_info": "Bool"
|
||||
},
|
||||
{
|
||||
"ordinal": 4,
|
||||
"name": "current_version_id",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
true
|
||||
]
|
||||
},
|
||||
"hash": "1ebe19b7b4f10039065967a0b1ca4bb38acc54e4ea5de020fffef7457000fa6e"
|
||||
}
|
||||
46
apps/labrinth/.sqlx/query-265c4d6f33714c8a5cf3137c429e2b57e917e9507942d65f40c1b733209cabf0.json
generated
Normal file
46
apps/labrinth/.sqlx/query-265c4d6f33714c8a5cf3137c429e2b57e917e9507942d65f40c1b733209cabf0.json
generated
Normal file
@@ -0,0 +1,46 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT id, shared_instance_id, size, sha512, created\n FROM shared_instance_versions\n WHERE shared_instance_id = $1\n ORDER BY created DESC\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 1,
|
||||
"name": "shared_instance_id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 2,
|
||||
"name": "size",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 3,
|
||||
"name": "sha512",
|
||||
"type_info": "Bytea"
|
||||
},
|
||||
{
|
||||
"ordinal": 4,
|
||||
"name": "created",
|
||||
"type_info": "Timestamptz"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
false
|
||||
]
|
||||
},
|
||||
"hash": "265c4d6f33714c8a5cf3137c429e2b57e917e9507942d65f40c1b733209cabf0"
|
||||
}
|
||||
14
apps/labrinth/.sqlx/query-299b8ea6e7a0048fa389cc4432715dc2a09e227d2f08e91167a43372a7ac6e35.json
generated
Normal file
14
apps/labrinth/.sqlx/query-299b8ea6e7a0048fa389cc4432715dc2a09e227d2f08e91167a43372a7ac6e35.json
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n DELETE FROM mods_categories\n WHERE joining_mod_id = $1 AND is_additional = FALSE\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "299b8ea6e7a0048fa389cc4432715dc2a09e227d2f08e91167a43372a7ac6e35"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-374c234b92b838b0bd65de100a9008b0fb78c79976fd858e0599e1ccb7f08b82.json
generated
Normal file
15
apps/labrinth/.sqlx/query-374c234b92b838b0bd65de100a9008b0fb78c79976fd858e0599e1ccb7f08b82.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET side_types_migration_review_status = $1\n WHERE id = $2\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "374c234b92b838b0bd65de100a9008b0fb78c79976fd858e0599e1ccb7f08b82"
|
||||
}
|
||||
14
apps/labrinth/.sqlx/query-3fcfed18cbfb37866e0fa57a4e95efb326864f8219941d1b696add39ed333ad1.json
generated
Normal file
14
apps/labrinth/.sqlx/query-3fcfed18cbfb37866e0fa57a4e95efb326864f8219941d1b696add39ed333ad1.json
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n DELETE FROM mods_categories\n WHERE joining_mod_id = $1 AND is_additional = TRUE\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "3fcfed18cbfb37866e0fa57a4e95efb326864f8219941d1b696add39ed333ad1"
|
||||
}
|
||||
@@ -1,14 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n DELETE FROM mods_categories\n WHERE joining_mod_id = $1 AND is_additional = TRUE\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "40f7c5bec98fe3503d6bd6db2eae5a4edb8d5d6efda9b9dc124f344ae5c60e08"
|
||||
}
|
||||
14
apps/labrinth/.sqlx/query-47130ef29ce5914528e5424fe516a9158a3ea08f8720f6df5b4902cd8094d3bb.json
generated
Normal file
14
apps/labrinth/.sqlx/query-47130ef29ce5914528e5424fe516a9158a3ea08f8720f6df5b4902cd8094d3bb.json
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n DELETE FROM shared_instance_versions\n WHERE id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "47130ef29ce5914528e5424fe516a9158a3ea08f8720f6df5b4902cd8094d3bb"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-47ec9f179f1c52213bd32b37621ab13ae43d180b8c86cb2a6fab0253dd4eba55.json
generated
Normal file
15
apps/labrinth/.sqlx/query-47ec9f179f1c52213bd32b37621ab13ae43d180b8c86cb2a6fab0253dd4eba55.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE shared_instances SET current_version_id = $1 WHERE id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "47ec9f179f1c52213bd32b37621ab13ae43d180b8c86cb2a6fab0253dd4eba55"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET description = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "4e9f9eafbfd705dfc94571018cb747245a98ea61bad3fae4b3ce284229d99955"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET slug = LOWER($1)\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "4fb5bd341369b4beb6b4a88de296b608ea5441a96db9f7360fbdccceb4628202"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-595f4e7432d5b41002988c6cc6b0b1f09273ad02c319e6631c74d80a9b278328.json
generated
Normal file
15
apps/labrinth/.sqlx/query-595f4e7432d5b41002988c6cc6b0b1f09273ad02c319e6631c74d80a9b278328.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET summary = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "595f4e7432d5b41002988c6cc6b0b1f09273ad02c319e6631c74d80a9b278328"
|
||||
}
|
||||
@@ -1,16 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n INSERT INTO mods_links (joining_mod_id, joining_platform_id, url)\n VALUES ($1, $2, $3)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"Int4",
|
||||
"Varchar"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "6366891bb34a14278f1ae857b8d6f68dff44badae9ae5c5aceba3c32e8d00356"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET requested_status = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "66b06ddcd0a4cf01e716331befa393a12631fe6752a7d078bda06b24d50daae2"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-6b166d129b0ee028898620054a58fa4c3641eb2221e522bf50abad4f5e977599.json
generated
Normal file
15
apps/labrinth/.sqlx/query-6b166d129b0ee028898620054a58fa4c3641eb2221e522bf50abad4f5e977599.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE shared_instances\n SET public = $1\n WHERE id = $2\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Bool",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "6b166d129b0ee028898620054a58fa4c3641eb2221e522bf50abad4f5e977599"
|
||||
}
|
||||
17
apps/labrinth/.sqlx/query-6f72c853e139f23322fe6f1f02e4e07e5ae80b5dfca6dc041a03c0c7a30a5cf1.json
generated
Normal file
17
apps/labrinth/.sqlx/query-6f72c853e139f23322fe6f1f02e4e07e5ae80b5dfca6dc041a03c0c7a30a5cf1.json
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n INSERT INTO shared_instances (id, title, owner_id, current_version_id)\n VALUES ($1, $2, $3, $4)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"Varchar",
|
||||
"Int8",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "6f72c853e139f23322fe6f1f02e4e07e5ae80b5dfca6dc041a03c0c7a30a5cf1"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-70be97b02e402de0490ade5866c47232f9c341add2f3838cc3ae1a07a310d561.json
generated
Normal file
15
apps/labrinth/.sqlx/query-70be97b02e402de0490ade5866c47232f9c341add2f3838cc3ae1a07a310d561.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET name = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "70be97b02e402de0490ade5866c47232f9c341add2f3838cc3ae1a07a310d561"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-72ae0e8debd06067894a2f7bea279446dd964da4efa49c5464cebde57860f741.json
generated
Normal file
15
apps/labrinth/.sqlx/query-72ae0e8debd06067894a2f7bea279446dd964da4efa49c5464cebde57860f741.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE shared_instances\n SET owner_id = $1\n WHERE owner_id = $2\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "72ae0e8debd06067894a2f7bea279446dd964da4efa49c5464cebde57860f741"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-79040825457845cc078be7b3293804d6fb2e05ffce07e7b4248d8705d6fc6e61.json
generated
Normal file
15
apps/labrinth/.sqlx/query-79040825457845cc078be7b3293804d6fb2e05ffce07e7b4248d8705d6fc6e61.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET moderation_message_body = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "79040825457845cc078be7b3293804d6fb2e05ffce07e7b4248d8705d6fc6e61"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET monetization_status = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "7916fe4f04067324ae05598ec9dc6f97f18baf9eda30c64f32677158ada87478"
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT m.id id, m.name name, m.summary summary, m.downloads downloads, m.follows follows,\n m.icon_url icon_url, m.raw_icon_url raw_icon_url, m.description description, m.published published,\n m.approved approved, m.queued, m.status status, m.requested_status requested_status,\n m.license_url license_url,\n m.team_id team_id, m.organization_id organization_id, m.license license, m.slug slug, m.moderation_message moderation_message, m.moderation_message_body moderation_message_body,\n m.webhook_sent, m.color,\n t.id thread_id, m.monetization_status monetization_status,\n ARRAY_AGG(DISTINCT c.category) filter (where c.category is not null and mc.is_additional is false) categories,\n ARRAY_AGG(DISTINCT c.category) filter (where c.category is not null and mc.is_additional is true) additional_categories\n FROM mods m\n INNER JOIN threads t ON t.mod_id = m.id\n LEFT JOIN mods_categories mc ON mc.joining_mod_id = m.id\n LEFT JOIN categories c ON mc.joining_category_id = c.id\n WHERE m.id = ANY($1) OR m.slug = ANY($2)\n GROUP BY t.id, m.id;\n ",
|
||||
"query": "\n SELECT m.id id, m.name name, m.summary summary, m.downloads downloads, m.follows follows,\n m.icon_url icon_url, m.raw_icon_url raw_icon_url, m.description description, m.published published,\n m.approved approved, m.queued, m.status status, m.requested_status requested_status,\n m.license_url license_url,\n m.team_id team_id, m.organization_id organization_id, m.license license, m.slug slug, m.moderation_message moderation_message, m.moderation_message_body moderation_message_body,\n m.webhook_sent, m.color,\n t.id thread_id, m.monetization_status monetization_status,\n m.side_types_migration_review_status side_types_migration_review_status,\n ARRAY_AGG(DISTINCT c.category) filter (where c.category is not null and mc.is_additional is false) categories,\n ARRAY_AGG(DISTINCT c.category) filter (where c.category is not null and mc.is_additional is true) additional_categories\n FROM mods m\n INNER JOIN threads t ON t.mod_id = m.id\n LEFT JOIN mods_categories mc ON mc.joining_mod_id = m.id\n LEFT JOIN categories c ON mc.joining_category_id = c.id\n WHERE m.id = ANY($1) OR m.slug = ANY($2)\n GROUP BY t.id, m.id;\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
@@ -125,11 +125,16 @@
|
||||
},
|
||||
{
|
||||
"ordinal": 24,
|
||||
"name": "side_types_migration_review_status",
|
||||
"type_info": "Varchar"
|
||||
},
|
||||
{
|
||||
"ordinal": 25,
|
||||
"name": "categories",
|
||||
"type_info": "VarcharArray"
|
||||
},
|
||||
{
|
||||
"ordinal": 25,
|
||||
"ordinal": 26,
|
||||
"name": "additional_categories",
|
||||
"type_info": "VarcharArray"
|
||||
}
|
||||
@@ -165,9 +170,10 @@
|
||||
true,
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
null,
|
||||
null
|
||||
]
|
||||
},
|
||||
"hash": "5f75c0c48083de27f853ee877aac070567fd2ed2be4a9a038821b790dd7cb763"
|
||||
"hash": "7a6d6a91e6bd27f7be34b8cc7955a66c4175ebd1c55e437f187f61efca681c62"
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT EXISTS(SELECT 1 FROM mods WHERE id=$1)\n ",
|
||||
"query": "SELECT EXISTS(SELECT 1 FROM shared_instance_versions WHERE id=$1)",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
@@ -18,5 +18,5 @@
|
||||
null
|
||||
]
|
||||
},
|
||||
"hash": "f34bbe639ad21801258dc8beaab9877229a451761be07f85a1dd04d027832329"
|
||||
"hash": "7c445073f61e30723416a9690aa9d227d95f2a8f2eb9852833e14c723903988b"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-7e403d399ddd3279c4c65db7b9ea850cdd9fef3df1b3f7d5f62e079b4522f2ca.json
generated
Normal file
15
apps/labrinth/.sqlx/query-7e403d399ddd3279c4c65db7b9ea850cdd9fef3df1b3f7d5f62e079b4522f2ca.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET slug = LOWER($1)\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "7e403d399ddd3279c4c65db7b9ea850cdd9fef3df1b3f7d5f62e079b4522f2ca"
|
||||
}
|
||||
14
apps/labrinth/.sqlx/query-92d805d2e13cfc0f2220f15b0a35ff71e654e5e6b386766e6c6047cf3861b26e.json
generated
Normal file
14
apps/labrinth/.sqlx/query-92d805d2e13cfc0f2220f15b0a35ff71e654e5e6b386766e6c6047cf3861b26e.json
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET approved = NOW()\n WHERE id = $1 AND approved IS NULL\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "92d805d2e13cfc0f2220f15b0a35ff71e654e5e6b386766e6c6047cf3861b26e"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-9482a3419337911ac6a10eeaf065e29589ee1b707729344e81d183c713aa0d28.json
generated
Normal file
15
apps/labrinth/.sqlx/query-9482a3419337911ac6a10eeaf065e29589ee1b707729344e81d183c713aa0d28.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET license_url = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "9482a3419337911ac6a10eeaf065e29589ee1b707729344e81d183c713aa0d28"
|
||||
}
|
||||
46
apps/labrinth/.sqlx/query-9c6e18cb19251e54b3b96446ab88d84842152b82c9a0032d1db587d7099b8550.json
generated
Normal file
46
apps/labrinth/.sqlx/query-9c6e18cb19251e54b3b96446ab88d84842152b82c9a0032d1db587d7099b8550.json
generated
Normal file
@@ -0,0 +1,46 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n -- See https://github.com/launchbadge/sqlx/issues/1266 for why we need all the \"as\"\n SELECT\n id as \"id!\",\n title as \"title!\",\n public as \"public!\",\n owner_id as \"owner_id!\",\n current_version_id\n FROM shared_instances\n WHERE owner_id = $1\n UNION\n SELECT\n id as \"id!\",\n title as \"title!\",\n public as \"public!\",\n owner_id as \"owner_id!\",\n current_version_id\n FROM shared_instances\n JOIN shared_instance_users ON id = shared_instance_id\n WHERE user_id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "id!",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 1,
|
||||
"name": "title!",
|
||||
"type_info": "Varchar"
|
||||
},
|
||||
{
|
||||
"ordinal": 2,
|
||||
"name": "public!",
|
||||
"type_info": "Bool"
|
||||
},
|
||||
{
|
||||
"ordinal": 3,
|
||||
"name": "owner_id!",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 4,
|
||||
"name": "current_version_id",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
null,
|
||||
null,
|
||||
null,
|
||||
null,
|
||||
null
|
||||
]
|
||||
},
|
||||
"hash": "9c6e18cb19251e54b3b96446ab88d84842152b82c9a0032d1db587d7099b8550"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-9ccaf8ea52b1b6f0880d34cdb4a9405e28c265bef6121b457c4f39cacf00683f.json
generated
Normal file
15
apps/labrinth/.sqlx/query-9ccaf8ea52b1b6f0880d34cdb4a9405e28c265bef6121b457c4f39cacf00683f.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE shared_instances\n SET title = $1\n WHERE id = $2\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "9ccaf8ea52b1b6f0880d34cdb4a9405e28c265bef6121b457c4f39cacf00683f"
|
||||
}
|
||||
@@ -1,14 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n DELETE FROM mods_categories\n WHERE joining_mod_id = $1 AND is_additional = FALSE\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "a0148ff25855202e7bb220b6a2bc9220a95e309fb0dae41d9a05afa86e6b33af"
|
||||
}
|
||||
@@ -1,14 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET approved = NOW()\n WHERE id = $1 AND approved IS NULL\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "a11d613479d09dff5fcdc45ab7a0341fb1b4738f0ede71572d939ef0984bd65f"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-a5ae1fe0ca4ca8432736398fed25687173b2fbde3405340a5579c5ef68cb5218.json
generated
Normal file
15
apps/labrinth/.sqlx/query-a5ae1fe0ca4ca8432736398fed25687173b2fbde3405340a5579c5ef68cb5218.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET license = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "a5ae1fe0ca4ca8432736398fed25687173b2fbde3405340a5579c5ef68cb5218"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-a74230ad1bb1b13bab850e204436e7746a96f9605afe2ca62d6d8337530cb5ad.json
generated
Normal file
15
apps/labrinth/.sqlx/query-a74230ad1bb1b13bab850e204436e7746a96f9605afe2ca62d6d8337530cb5ad.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET status = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "a74230ad1bb1b13bab850e204436e7746a96f9605afe2ca62d6d8337530cb5ad"
|
||||
}
|
||||
34
apps/labrinth/.sqlx/query-aec58041cf5e5e68501652336581b8c709645ef29f3b5fb6e8e07fc212b36798.json
generated
Normal file
34
apps/labrinth/.sqlx/query-aec58041cf5e5e68501652336581b8c709645ef29f3b5fb6e8e07fc212b36798.json
generated
Normal file
@@ -0,0 +1,34 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT shared_instance_id, user_id, permissions\n FROM shared_instance_users\n WHERE shared_instance_id = ANY($1)\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "shared_instance_id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 1,
|
||||
"name": "user_id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 2,
|
||||
"name": "permissions",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8Array"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false,
|
||||
false,
|
||||
false
|
||||
]
|
||||
},
|
||||
"hash": "aec58041cf5e5e68501652336581b8c709645ef29f3b5fb6e8e07fc212b36798"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET summary = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "b677e66031752e66d2219079a559e368c6cea1800da8a5f9d50ba5b1ac3a15fc"
|
||||
}
|
||||
46
apps/labrinth/.sqlx/query-b93253bbc35b24974d13bc8ee0447be2a18275f33f8991d910f693fbcc1ff731.json
generated
Normal file
46
apps/labrinth/.sqlx/query-b93253bbc35b24974d13bc8ee0447be2a18275f33f8991d910f693fbcc1ff731.json
generated
Normal file
@@ -0,0 +1,46 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT id, shared_instance_id, size, sha512, created\n FROM shared_instance_versions\n WHERE id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 1,
|
||||
"name": "shared_instance_id",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 2,
|
||||
"name": "size",
|
||||
"type_info": "Int8"
|
||||
},
|
||||
{
|
||||
"ordinal": 3,
|
||||
"name": "sha512",
|
||||
"type_info": "Bytea"
|
||||
},
|
||||
{
|
||||
"ordinal": 4,
|
||||
"name": "created",
|
||||
"type_info": "Timestamptz"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
false
|
||||
]
|
||||
},
|
||||
"hash": "b93253bbc35b24974d13bc8ee0447be2a18275f33f8991d910f693fbcc1ff731"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET license_url = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "c100a3be0e1b7bf449576c4052d87494979cb89d194805a5ce9e928eef796ae9"
|
||||
}
|
||||
23
apps/labrinth/.sqlx/query-c3869a595693757ccf81085d0c8eb2231578aff18c93d02ead97c3c07f0b27ea.json
generated
Normal file
23
apps/labrinth/.sqlx/query-c3869a595693757ccf81085d0c8eb2231578aff18c93d02ead97c3c07f0b27ea.json
generated
Normal file
@@ -0,0 +1,23 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT permissions\n FROM shared_instance_users\n WHERE shared_instance_id = $1 AND user_id = $2\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "permissions",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false
|
||||
]
|
||||
},
|
||||
"hash": "c3869a595693757ccf81085d0c8eb2231578aff18c93d02ead97c3c07f0b27ea"
|
||||
}
|
||||
14
apps/labrinth/.sqlx/query-c6693ea80ab1675dd2da72d70add734a92bb25f17a0536968e4b9a4dbe05cf5b.json
generated
Normal file
14
apps/labrinth/.sqlx/query-c6693ea80ab1675dd2da72d70add734a92bb25f17a0536968e4b9a4dbe05cf5b.json
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET moderation_message = NULL, moderation_message_body = NULL, queued = NOW()\n WHERE (id = $1)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "c6693ea80ab1675dd2da72d70add734a92bb25f17a0536968e4b9a4dbe05cf5b"
|
||||
}
|
||||
@@ -1,15 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET name = $1\n WHERE (id = $2)\n ",
|
||||
"query": "\n UPDATE mods\n SET webhook_sent = TRUE\n WHERE id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "9c1b6ba7cbe2619ff767ee7bbfb01725dc3324d284b2f20cf393574ab3bc655f"
|
||||
"hash": "cec98010827455127da68a2bc5cd3c1ee3bfd357a6a8604febad3ed214a9b77b"
|
||||
}
|
||||
14
apps/labrinth/.sqlx/query-cef730c02bb67b0536d35e5aaca0bd34c3893e8b55bbd126a988137ec7bf1ff9.json
generated
Normal file
14
apps/labrinth/.sqlx/query-cef730c02bb67b0536d35e5aaca0bd34c3893e8b55bbd126a988137ec7bf1ff9.json
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n DELETE FROM shared_instances\n WHERE id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "cef730c02bb67b0536d35e5aaca0bd34c3893e8b55bbd126a988137ec7bf1ff9"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-d010207297e1c4f2ebfb0a81caf45481c94edb1e8d8ac47db13ec0ff9b2f5328.json
generated
Normal file
15
apps/labrinth/.sqlx/query-d010207297e1c4f2ebfb0a81caf45481c94edb1e8d8ac47db13ec0ff9b2f5328.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET moderation_message = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "d010207297e1c4f2ebfb0a81caf45481c94edb1e8d8ac47db13ec0ff9b2f5328"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET moderation_message = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "d331ca8f22da418cf654985c822ce4466824beaa00dea64cde90dc651a03024b"
|
||||
}
|
||||
22
apps/labrinth/.sqlx/query-d5ad5a67fe53351b760335b80501f09a2799bf575af90beeac94193fe8c4388b.json
generated
Normal file
22
apps/labrinth/.sqlx/query-d5ad5a67fe53351b760335b80501f09a2799bf575af90beeac94193fe8c4388b.json
generated
Normal file
@@ -0,0 +1,22 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT tm.user_id id\n FROM team_members tm\n WHERE tm.team_id = $1 AND tm.accepted\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "id",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false
|
||||
]
|
||||
},
|
||||
"hash": "d5ad5a67fe53351b760335b80501f09a2799bf575af90beeac94193fe8c4388b"
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT EXISTS(SELECT 1 FROM mods WHERE slug = LOWER($1))\n ",
|
||||
"query": "SELECT EXISTS(SELECT 1 FROM shared_instances WHERE id=$1)",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
@@ -11,12 +11,12 @@
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text"
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
null
|
||||
]
|
||||
},
|
||||
"hash": "abf790170e3a807ffe8b3a188da620c89e6398f38ff066220fdadffe8e7481c1"
|
||||
"hash": "d8558a8039ade3b383db4f0e095e6826f46c27ab3a21520e9e169fd1491521c4"
|
||||
}
|
||||
18
apps/labrinth/.sqlx/query-d8a1d710f86b3df4d99c2d2ec26ec405531e4270be85087122245991ec88473e.json
generated
Normal file
18
apps/labrinth/.sqlx/query-d8a1d710f86b3df4d99c2d2ec26ec405531e4270be85087122245991ec88473e.json
generated
Normal file
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n INSERT INTO shared_instance_versions (id, shared_instance_id, size, sha512, created)\n VALUES ($1, $2, $3, $4, $5)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8",
|
||||
"Int8",
|
||||
"Int8",
|
||||
"Bytea",
|
||||
"Timestamptz"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "d8a1d710f86b3df4d99c2d2ec26ec405531e4270be85087122245991ec88473e"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-e42e63db3ae4d1d745508b80651494da8738873b98aa608792af19e60b9fb998.json
generated
Normal file
15
apps/labrinth/.sqlx/query-e42e63db3ae4d1d745508b80651494da8738873b98aa608792af19e60b9fb998.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET requested_status = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "e42e63db3ae4d1d745508b80651494da8738873b98aa608792af19e60b9fb998"
|
||||
}
|
||||
15
apps/labrinth/.sqlx/query-e7654740161726b2aef4f7c9a26eb00efcac9f6285a39d8df06d606613684ba3.json
generated
Normal file
15
apps/labrinth/.sqlx/query-e7654740161726b2aef4f7c9a26eb00efcac9f6285a39d8df06d606613684ba3.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET description = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "e7654740161726b2aef4f7c9a26eb00efcac9f6285a39d8df06d606613684ba3"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET status = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "e925b15ec46f0263c7775ba1ba00ed11cfd6749fa792d4eabed73b619f230585"
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT tm.user_id id\n FROM team_members tm\n WHERE tm.team_id = $1 AND tm.accepted\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "id",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false
|
||||
]
|
||||
},
|
||||
"hash": "ea1525cbe7460d0d9e9da8f448c661f7209bc1a7a04e2ea0026fa69c3f550a14"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n UPDATE mods\n SET moderation_message_body = $1\n WHERE (id = $2)\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Int8"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "ed1d5d9433bc7f4a360431ecfdd9430c5e58cd6d1c623c187d8661200400b1a4"
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n INSERT INTO mods (\n id, team_id, name, summary, description,\n published, downloads, icon_url, raw_icon_url, status, requested_status,\n license_url, license,\n slug, color, monetization_status, organization_id\n )\n VALUES (\n $1, $2, $3, $4, $5, $6,\n $7, $8, $9, $10, $11,\n $12, $13,\n LOWER($14), $15, $16, $17\n )\n ",
|
||||
"query": "\n INSERT INTO mods (\n id, team_id, name, summary, description,\n published, downloads, icon_url, raw_icon_url, status, requested_status,\n license_url, license,\n slug, color, monetization_status, organization_id,\n side_types_migration_review_status\n )\n VALUES (\n $1, $2, $3, $4, $5, $6,\n $7, $8, $9, $10, $11,\n $12, $13,\n LOWER($14), $15, $16, $17,\n $18\n )\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
@@ -21,10 +21,11 @@
|
||||
"Text",
|
||||
"Int4",
|
||||
"Varchar",
|
||||
"Int8"
|
||||
"Int8",
|
||||
"Varchar"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "bcbcac3c0b2b2b0327577d3095fa744ab42f7f1dcd2b7f3c3dace12b899b3f38"
|
||||
"hash": "ee74bbff42dd29ab5a23d5811ea18e62ac199fe5e68275bf1bc7c71ace630702"
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user