[FEATURE] Backup Database sync
This commit is contained in:
parent
b538ab5089
commit
7d34fcfce8
7 changed files with 79 additions and 15 deletions
|
@ -16,16 +16,31 @@ function payloadFilter(req, res) {
|
|||
const serverSpec = req.body;
|
||||
if (!serverSpec) return res.sendStatus(400);
|
||||
const { name, host, version, serverType, memory } = serverSpec;
|
||||
const { backupHost, backupBucket, backupId, backupKey } = serverSpec;
|
||||
const { backupHost, backupBucket, backupId, backupKey, backupInterval } =
|
||||
serverSpec;
|
||||
if (!name) return res.status(400).send("Server name is required!");
|
||||
if (!host) return res.status(400).send("Server host is required!");
|
||||
if (!dnsRegex.test(host)) return res.status(400).send("Hostname invalid!");
|
||||
if (!version) return res.status(400).send("Server version is required!");
|
||||
if (!serverType) return res.status(400).send("Server type is required!");
|
||||
if (!memory) return res.status(400).send("Memory is required!");
|
||||
if (!!backupHost || !!backupBucket || !!backupId || !!backupKey) {
|
||||
if (
|
||||
!!backupHost ||
|
||||
!!backupBucket ||
|
||||
!!backupId ||
|
||||
!!backupKey ||
|
||||
!backupInterval
|
||||
) {
|
||||
// If any keys are required, all are required
|
||||
if (!(!!backupHost && !!backupBucket && !!backupId && !!backupKey))
|
||||
if (
|
||||
!(
|
||||
!!backupHost &&
|
||||
!!backupBucket &&
|
||||
!!backupId &&
|
||||
!!backupKey &&
|
||||
!!backupInterval
|
||||
)
|
||||
)
|
||||
return res.status(400).send("All backup keys are required!");
|
||||
if (!dnsRegex.test(backupHost))
|
||||
return res.status(400).send("Backup Host invalid!");
|
||||
|
|
|
@ -20,6 +20,7 @@ export async function createServerEntry(serverSpec) {
|
|||
backupBucket: backup_bucket_path,
|
||||
backupId: backup_id,
|
||||
backupKey: backup_key,
|
||||
backupInterval: backup_interval,
|
||||
} = serverSpec;
|
||||
var q = insertQuery(table, {
|
||||
name,
|
||||
|
@ -31,6 +32,7 @@ export async function createServerEntry(serverSpec) {
|
|||
backup_bucket_path,
|
||||
backup_id,
|
||||
backup_key,
|
||||
backup_interval,
|
||||
});
|
||||
q += "\n RETURNING *";
|
||||
try {
|
||||
|
@ -71,9 +73,28 @@ export async function getServerEntry(serverId) {
|
|||
version,
|
||||
server_type: serverType,
|
||||
memory,
|
||||
backup_host: backupHost,
|
||||
backup_bucket_path: backupPath,
|
||||
backup_id: backupId,
|
||||
backup_key: backupKey,
|
||||
backup_interval: backupInterval,
|
||||
} = serverSpecs[0];
|
||||
const mclName = getMclName(host, id);
|
||||
return { name, mclName, id, host, version, serverType, memory };
|
||||
return {
|
||||
name,
|
||||
mclName,
|
||||
id,
|
||||
host,
|
||||
version,
|
||||
serverType,
|
||||
memory,
|
||||
backupHost,
|
||||
backupPath,
|
||||
backupId,
|
||||
backupKey,
|
||||
backupInterval
|
||||
|
||||
};
|
||||
} catch (e) {
|
||||
asExpressClientError(e);
|
||||
}
|
||||
|
|
|
@ -33,20 +33,20 @@ env:
|
|||
- name: DEST_DIR
|
||||
value: /backups
|
||||
- name: LINK_LATEST
|
||||
value: "false"
|
||||
value: "true"
|
||||
- name: TAR_COMPRESS_METHOD
|
||||
value: gzip
|
||||
- name: ZSTD_PARAMETERS
|
||||
value: -3 --long=25 --single-thread
|
||||
- name: RCLONE_REMOTE
|
||||
value: mc-dunemask-net
|
||||
value: mcl-backup-changeme
|
||||
- name: RCLONE_DEST_DIR
|
||||
value: /minecraft-backups/deltasmp-backups
|
||||
value: /mcl/backups/changeme
|
||||
- name: RCLONE_COMPRESS_METHOD
|
||||
value: gzip
|
||||
image: itzg/mc-backup:latest
|
||||
imagePullPolicy: IfNotPresent
|
||||
name: mcs-deltasmp-minecraft-mc-backup
|
||||
name: mcl-backup-changeme
|
||||
resources:
|
||||
requests:
|
||||
cpu: 500m
|
||||
|
|
|
@ -63,5 +63,6 @@ export function getServerContainer(serverSpec) {
|
|||
|
||||
export function getBackupContainer(serverSpec) {
|
||||
const container = loadYaml("lib/k8s/configs/containers/minecraft-backup.yml");
|
||||
console.log(serverSpec);
|
||||
return container;
|
||||
}
|
||||
|
|
|
@ -1,11 +1,12 @@
|
|||
import TextField from "@mui/material/TextField";
|
||||
export default function BackupBucketOption(props) {
|
||||
const { onChange } = props;
|
||||
const { value, onChange } = props;
|
||||
|
||||
return (
|
||||
<TextField
|
||||
label="Bucket Path"
|
||||
onChange={onChange}
|
||||
defaultValue={value}
|
||||
helperText="Example: /minecraft-backups/example-backups"
|
||||
FormHelperTextProps={{ sx: { ml: 0 } }}
|
||||
required
|
||||
|
|
|
@ -3,6 +3,8 @@ import Box from "@mui/material/Box";
|
|||
import MenuItem from "@mui/material/MenuItem";
|
||||
import TextField from "@mui/material/TextField";
|
||||
|
||||
const backupIntervalStepDisplay = ["Minutes", "Hours", "Days"];
|
||||
export const backupIntervalDefault = "1d";
|
||||
export const backupIntervalStepOptions = ["m", "h", "d"];
|
||||
export default function BackupIntervalOption(props) {
|
||||
const { onChange } = props;
|
||||
|
@ -11,20 +13,31 @@ export default function BackupIntervalOption(props) {
|
|||
backupIntervalStepOptions[2],
|
||||
);
|
||||
|
||||
const changeInterval = (e) => console.log(e.target.value);
|
||||
const changeStep = (e) => {
|
||||
setIntervalStep(e.target.value);
|
||||
onChange({ target: { value: `${interval}${e.target.value}` } });
|
||||
};
|
||||
|
||||
const changeInterval = (e) => {
|
||||
setInterval(e.target.value);
|
||||
onChange({ target: { value: `${e.target.value}${intervalStep}` } });
|
||||
};
|
||||
|
||||
return (
|
||||
<Box>
|
||||
<TextField
|
||||
label="Backup Interval"
|
||||
sx={{ width: "100%" }}
|
||||
sx={{ width: "70%" }}
|
||||
value={interval}
|
||||
onChange={changeInterval}
|
||||
helperText="Examples: 1m, 3h, 3.5d"
|
||||
FormHelperTextProps={{ sx: { ml: 0 } }}
|
||||
type="number"
|
||||
required
|
||||
/>
|
||||
<TextField
|
||||
label="Backup Step"
|
||||
label="Step"
|
||||
sx={{ width: "30%", minWidth: "4rem" }}
|
||||
onChange={onChange}
|
||||
value={intervalStep}
|
||||
select
|
||||
|
@ -33,7 +46,7 @@ export default function BackupIntervalOption(props) {
|
|||
>
|
||||
{backupIntervalStepOptions.map((o, i) => (
|
||||
<MenuItem value={o} key={i}>
|
||||
{o}
|
||||
{backupIntervalStepDisplay[i]}
|
||||
</MenuItem>
|
||||
))}
|
||||
</TextField>
|
||||
|
|
|
@ -26,7 +26,9 @@ import BackupHostOption from "@mcl/components/server-options/BackupHostOption.js
|
|||
import BackupBucketOption from "@mcl/components/server-options/BackupBucketOption.jsx";
|
||||
import BackupIdOption from "@mcl/components/server-options/BackupIdOption.jsx";
|
||||
import BackupKeyOption from "@mcl/components/server-options/BackupKeyOption.jsx";
|
||||
import BackupIntervalOption from "@mcl/components/server-options/BackupIntervalOption.jsx";
|
||||
import BackupIntervalOption, {
|
||||
backupIntervalDefault,
|
||||
} from "@mcl/components/server-options/BackupIntervalOption.jsx";
|
||||
|
||||
const defaultServer = {
|
||||
version: "latest",
|
||||
|
@ -68,7 +70,18 @@ export default function CreateCoreOptions() {
|
|||
alert(`Could not validate spec because: ${reason}`);
|
||||
}
|
||||
|
||||
const toggleBackupEnabled = () => setBackupEnabled(!backupEnabled);
|
||||
const toggleBackupEnabled = () => {
|
||||
const s = { ...spec };
|
||||
if (!backupEnabled) {
|
||||
(s.backupInterval = backupIntervalDefault),
|
||||
(s.backupBucket = `/mcl/server-backups/${(
|
||||
s.name ?? "my-server"
|
||||
).toLowerCase()}`);
|
||||
} else for (var k in s) if (k.startsWith("backup")) delete s[k];
|
||||
setSpec(s);
|
||||
console.log(s);
|
||||
setBackupEnabled(!backupEnabled);
|
||||
};
|
||||
|
||||
return (
|
||||
<Box
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue