fetch latest version tag from docker hub (#11362)

closes #11352

---------

Co-authored-by: Félix Malfait <felix@twenty.com>
This commit is contained in:
nitin
2025-04-08 14:25:03 +05:30
committed by GitHub
parent 95eba07f6e
commit ea93ac6348
11 changed files with 273 additions and 77 deletions

View File

@ -1,72 +1,34 @@
import { SettingsAdminTableCard } from '@/settings/admin-panel/components/SettingsAdminTableCard';
import { checkTwentyVersionExists } from '@/settings/admin-panel/utils/checkTwentyVersionExists';
import { fetchLatestTwentyRelease } from '@/settings/admin-panel/utils/fetchLatestTwentyRelease';
import styled from '@emotion/styled';
import { SettingsAdminVersionDisplay } from '@/settings/admin-panel/components/SettingsAdminVersionDisplay';
import { t } from '@lingui/core/macro';
import { useEffect, useState } from 'react';
import packageJson from '../../../../../package.json';
import { GITHUB_LINK } from 'twenty-ui/navigation';
import { IconCircleDot, IconStatusChange } from 'twenty-ui/display';
const StyledActionLink = styled.a`
align-items: center;
color: ${({ theme }) => theme.font.color.primary};
display: flex;
font-size: ${({ theme }) => theme.font.size.sm};
font-weight: ${({ theme }) => theme.font.weight.regular};
gap: ${({ theme }) => theme.spacing(1)};
text-decoration: none;
:hover {
color: ${({ theme }) => theme.font.color.primary};
cursor: pointer;
}
`;
const StyledSpan = styled.span`
color: ${({ theme }) => theme.font.color.primary};
font-size: ${({ theme }) => theme.font.size.sm};
font-weight: ${({ theme }) => theme.font.weight.regular};
`;
import { useGetVersionInfoQuery } from '~/generated/graphql';
export const SettingsAdminVersionContainer = () => {
const [latestVersion, setLatestVersion] = useState<string | null>(null);
const [currentVersionExists, setCurrentVersionExists] = useState(false);
useEffect(() => {
fetchLatestTwentyRelease().then(setLatestVersion);
checkTwentyVersionExists(packageJson.version).then(setCurrentVersionExists);
}, []);
const { data, loading } = useGetVersionInfoQuery();
const { currentVersion, latestVersion } = data?.versionInfo ?? {};
const versionItems = [
{
Icon: IconCircleDot,
label: t`Current version`,
value: currentVersionExists ? (
<StyledActionLink
href={`${GITHUB_LINK}/releases/tag/v${packageJson.version}`}
target="_blank"
rel="noreferrer"
>
{packageJson.version}
</StyledActionLink>
) : (
<StyledSpan>{packageJson.version}</StyledSpan>
value: (
<SettingsAdminVersionDisplay
version={currentVersion}
loading={loading}
noVersionMessage={t`Unknown`}
/>
),
},
{
Icon: IconStatusChange,
label: t`Latest version`,
value: latestVersion ? (
<StyledActionLink
href={`${GITHUB_LINK}/releases/tag/v${latestVersion}`}
target="_blank"
rel="noreferrer"
>
{latestVersion}
</StyledActionLink>
) : (
<StyledSpan>{latestVersion ?? 'Loading...'}</StyledSpan>
value: (
<SettingsAdminVersionDisplay
version={latestVersion}
loading={loading}
noVersionMessage={t`No latest version found`}
/>
),
},
];

View File

@ -0,0 +1,53 @@
import styled from '@emotion/styled';
import { t } from '@lingui/core/macro';
type SettingsAdminVersionDisplayProps = {
version: string | undefined | null;
loading: boolean;
noVersionMessage: string;
};
const StyledActionLink = styled.a`
align-items: center;
color: ${({ theme }) => theme.font.color.primary};
display: flex;
font-size: ${({ theme }) => theme.font.size.sm};
font-weight: ${({ theme }) => theme.font.weight.regular};
gap: ${({ theme }) => theme.spacing(1)};
text-decoration: none;
:hover {
color: ${({ theme }) => theme.font.color.primary};
cursor: pointer;
}
`;
const StyledSpan = styled.span`
color: ${({ theme }) => theme.font.color.primary};
font-size: ${({ theme }) => theme.font.size.sm};
font-weight: ${({ theme }) => theme.font.weight.regular};
`;
export const SettingsAdminVersionDisplay = ({
version,
loading,
noVersionMessage,
}: SettingsAdminVersionDisplayProps) => {
if (loading) {
return <StyledSpan>{t`Loading...`}</StyledSpan>;
}
if (!version) {
return <StyledSpan>{noVersionMessage}</StyledSpan>;
}
return (
<StyledActionLink
href={`https://hub.docker.com/r/twentycrm/twenty/tags?name=${version}`}
target="_blank"
rel="noreferrer"
>
{version}
</StyledActionLink>
);
};

View File

@ -0,0 +1,10 @@
import { gql } from '@apollo/client';
export const GET_VERSION_INFO = gql`
query GetVersionInfo {
versionInfo {
currentVersion
latestVersion
}
}
`;

View File

@ -1,12 +0,0 @@
export const checkTwentyVersionExists = async (
version: string,
): Promise<boolean> => {
try {
const response = await fetch(
`https://api.github.com/repos/twentyhq/twenty/releases/tags/v${version}`,
);
return response.status === 200;
} catch (error) {
return false;
}
};

View File

@ -1,11 +0,0 @@
export const fetchLatestTwentyRelease = async (): Promise<string> => {
try {
const response = await fetch(
'https://api.github.com/repos/twentyhq/twenty/releases/latest',
);
const data = await response.json();
return data.tag_name.replace('v', '');
} catch (error) {
return 'Could not fetch latest release';
}
};