refactor: add latestVersion information to update data

This commit is contained in:
UndefinedPony
2024-12-20 18:26:54 +01:00
parent c8514e3a1b
commit 4565b3d7a2
4 changed files with 39 additions and 18 deletions

View File

@@ -20,16 +20,16 @@ export const UpdateServer = () => {
const [isUpdateAvailable, setIsUpdateAvailable] = useState<null | boolean>(
null,
);
const { mutateAsync: checkForUpdate, isLoading } =
api.settings.checkForUpdate.useMutation();
const { mutateAsync: getUpdateData, isLoading } =
api.settings.getUpdateData.useMutation();
const [isOpen, setIsOpen] = useState(false);
const handleCheckUpdates = async () => {
try {
const updateAvailable = await checkForUpdate();
const { updateAvailable, latestVersion } = await getUpdateData();
setIsUpdateAvailable(updateAvailable);
if (updateAvailable) {
toast.success("Update is available!");
toast.success(`${latestVersion} update is available!`);
} else {
toast.info("No updates available");
}

View File

@@ -34,8 +34,8 @@ export const Navbar = () => {
},
);
const { mutateAsync } = api.auth.logout.useMutation();
const { mutateAsync: checkForUpdate } =
api.settings.checkForUpdate.useMutation();
const { mutateAsync: getUpdateData } =
api.settings.getUpdateData.useMutation();
const checkUpdatesIntervalRef = useRef<null | NodeJS.Timeout>(null);
@@ -58,7 +58,7 @@ export const Navbar = () => {
return;
}
const updateAvailable = await checkForUpdate();
const { updateAvailable } = await getUpdateData();
if (updateAvailable) {
// Stop interval when update is available

View File

@@ -45,7 +45,7 @@ import {
stopService,
stopServiceRemote,
updateAdmin,
checkIsUpdateAvailable,
getUpdateData,
updateLetsEncryptEmail,
updateServerById,
updateServerTraefik,
@@ -343,12 +343,12 @@ export const settingsRouter = createTRPCRouter({
writeConfig("middlewares", input.traefikConfig);
return true;
}),
checkForUpdate: adminProcedure.mutation(async () => {
getUpdateData: adminProcedure.mutation(async () => {
if (IS_CLOUD) {
return true;
return { latestVersion: null, updateAvailable: false };
}
return await checkIsUpdateAvailable();
return await getUpdateData();
}),
updateServer: adminProcedure.mutation(async () => {
if (IS_CLOUD) {

View File

@@ -1,7 +1,6 @@
import { readdirSync } from "node:fs";
import { join } from "node:path";
import { docker } from "@dokploy/server/constants";
import { getServiceContainer } from "@dokploy/server/utils/docker/utils";
import { execAsyncRemote } from "@dokploy/server/utils/process/execAsync";
import { spawnAsync } from "../utils/process/spawnAsync";
// import packageInfo from "../../../package.json";
@@ -11,8 +10,11 @@ export const getDokployImageTag = () => {
return process.env.RELEASE_TAG || "latest";
};
/** Checks if server update is available by comparing current image's digest against digest for provided image tag via Docker hub API */
export const checkIsUpdateAvailable = async () => {
/** Returns latest version number and information whether server update is available by comparing current image's digest against digest for provided image tag via Docker hub API. */
export const getUpdateData = async (): Promise<{
latestVersion: string | null;
updateAvailable: boolean;
}> => {
const commandResult = await spawnAsync("docker", [
"inspect",
"--format={{index .RepoDigests 0}}",
@@ -21,16 +23,35 @@ export const checkIsUpdateAvailable = async () => {
const currentDigest = commandResult.toString().trim().split("@")[1];
const url = `https://hub.docker.com/v2/repositories/dokploy/dokploy/tags/${getDokployImageTag()}`;
const url = "https://hub.docker.com/v2/repositories/dokploy/dokploy/tags";
const response = await fetch(url, {
method: "GET",
headers: { "Content-Type": "application/json" },
});
const data = (await response.json()) as { digest: string };
const { digest } = data;
const data = (await response.json()) as {
results: [{ digest: string; name: string }];
};
const { results } = data;
const latestTagDigest = results.find((t) => t.name === "latest")?.digest;
return digest !== currentDigest;
if (!latestTagDigest) {
return { latestVersion: null, updateAvailable: false };
}
const versionedTag = results.find(
(t) => t.digest === latestTagDigest && t.name.startsWith("v"),
);
if (!versionedTag) {
return { latestVersion: null, updateAvailable: false };
}
const { name: latestVersion, digest } = versionedTag;
const updateAvailable = digest !== currentDigest;
return { latestVersion, updateAvailable };
};
export const getDokployImage = () => {