Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion client/scripts/update_api_spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import { parseDocument } from "yaml";

const GH_BASE_URL = "https://raw.githubusercontent.com";
const DATA_SERVICES_REPO = "SwissDataScienceCenter/renku-data-services";
const DATA_SERVICES_RELEASE = "main";
const DATA_SERVICES_RELEASE = "build/support-build-arm";

async function main() {
argv.forEach((arg) => {
Expand Down
2 changes: 1 addition & 1 deletion client/src/features/sessionsV2/SessionImageModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,7 @@ export default function SessionImageModal({
) : (
<>
<div className="mb-2">
<SessionImageBadge data={data} loading={isLoading} />
<SessionImageBadge data={data} isLoading={isLoading} />
</div>
{!data.connection && !data.provider ? (
<>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@

import { skipToken } from "@reduxjs/toolkit/query";
import cx from "classnames";
import { useContext } from "react";
import { useContext, useMemo } from "react";
import { CircleFill, Link45deg, Pencil, Trash } from "react-bootstrap-icons";
import { Card, CardBody, Col, DropdownItem, Row } from "reactstrap";

Expand All @@ -29,6 +29,7 @@ import { DEFAULT_APP_PARAMS } from "../../../utils/context/appParams.constants";
import PermissionsGuard from "../../permissionsV2/PermissionsGuard";
import useProjectPermissions from "../../ProjectPageV2/utils/useProjectPermissions.hook";
import { Project } from "../../projectsV2/api/projectV2.api";
import { computeResourcesApi } from "../api/computeResources.api";
import type { SessionLauncher } from "../api/sessionLaunchersV2.api";
import {
sessionLaunchersV2Api,
Expand Down Expand Up @@ -127,15 +128,24 @@ export default function SessionLauncherCard({
"text-muted",
];

const { data: containerImage, isLoading: loadingContainerImage } =
const { data: containerImage, isLoading: isLoadingContainerImage } =
useGetSessionsImagesQuery(
environment &&
environment.environment_kind === "CUSTOM" &&
environment.container_image
environment?.container_image != null
? { imageUrl: environment.container_image }
: skipToken
);

const { data: resourcePools, isLoading: isLoadingResourcePools } =
computeResourcesApi.endpoints.getResourcePools.useQueryState({});
const resourcePool = useMemo(() => {
if (launcher?.resource_class_id == null || resourcePools == null) {
return undefined;
}
return resourcePools.find(({ classes }) =>
classes.some(({ id }) => id === launcher.resource_class_id)
);
}, [launcher?.resource_class_id, resourcePools]);

return (
<Card
className={cx(
Expand Down Expand Up @@ -203,10 +213,13 @@ export default function SessionLauncherCard({
<SessionEnvironmentGitLabWarningBadge launcher={launcher} />
</Col>
</Row>
{isCodeEnvironment && (
{isCodeEnvironment ? (
<Row className="g-2">
<Col xs={12} xl={4}>
{isCodeEnvironment && isLoading ? (
{isCodeEnvironment &&
(isLoading ||
isLoadingContainerImage ||
isLoadingResourcePools) ? (
<SessionBadge
className={cx("border-warning", "bg-warning-subtle")}
>
Expand All @@ -220,7 +233,11 @@ export default function SessionLauncherCard({
</span>
</SessionBadge>
) : isCodeEnvironment && lastBuild ? (
<BuildStatusBadge status={lastBuild?.status} />
<BuildStatusBadge
buildStatus={lastBuild?.status}
imageCheck={containerImage}
resourcePool={resourcePool}
/>
) : !hasSession ? (
<SessionBadge
className={cx("border-dark-subtle", "bg-light")}
Expand Down Expand Up @@ -253,13 +270,14 @@ export default function SessionLauncherCard({
/>
</Col>
</Row>
)}
{isExternalImageEnvironment && (
) : (
<Row>
<Col>
<SessionImageBadge
data={containerImage}
loading={loadingContainerImage}
isLoading={isLoadingContainerImage}
resourcePool={resourcePool}
isLoadingResourcePools={isLoadingResourcePools}
/>
</Col>
</Row>
Expand Down
104 changes: 81 additions & 23 deletions client/src/features/sessionsV2/SessionView/EnvironmentCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ import AppContext from "../../../utils/context/appContext";
import { DEFAULT_APP_PARAMS } from "../../../utils/context/appParams.constants";
import useAppDispatch from "../../../utils/customHooks/useAppDispatch.hook";
import { toHumanDateTime } from "../../../utils/helpers/DateTimeUtils";
import { computeResourcesApi } from "../api/computeResources.api";
import type { SessionLauncher } from "../api/sessionLaunchersV2.api";
import {
sessionLaunchersV2Api,
Expand Down Expand Up @@ -115,6 +116,7 @@ export default function EnvironmentCard({
</EnvironmentRow>
{environment_kind === "GLOBAL" && (
<>
<GlobalEnvironmentSessionImageBadge launcher={launcher} />
<EnvironmentRow>
{environment?.description ? (
<p className={cx("text-truncate", "text-wrap")}>
Expand Down Expand Up @@ -150,20 +152,56 @@ export default function EnvironmentCard({
);
}

function GlobalEnvironmentSessionImageBadge({
launcher,
}: {
launcher: SessionLauncher;
}) {
const environment = launcher.environment;
const { data, isLoading } = useGetSessionsImagesQuery(
environment && environment.container_image
? { imageUrl: environment.container_image }
: skipToken
);
const { data: resourcePools, isLoading: isLoadingResourcePools } =
computeResourcesApi.endpoints.getResourcePools.useQueryState({});
const resourcePool = useMemo(() => {
if (launcher?.resource_class_id == null || resourcePools == null) {
return undefined;
}
return resourcePools.find(({ classes }) =>
classes.some(({ id }) => id === launcher.resource_class_id)
);
}, [launcher?.resource_class_id, resourcePools]);

return (
<div className="mb-2">
<SessionImageBadge
data={data}
isLoading={isLoading}
resourcePool={resourcePool}
isLoadingResourcePools={isLoadingResourcePools}
/>
</div>
);
}

function CustomEnvironmentValues({ launcher }: { launcher: SessionLauncher }) {
const { environment } = launcher;

if (environment.environment_image_source === "image") {
return <CustomImageEnvironmentValues launcher={launcher} />;
return <CustomImageEnvironmentValues launcher={launcher} showImageBadge />;
}

return <CustomBuildEnvironmentValues launcher={launcher} />;
}

function CustomImageEnvironmentValues({
launcher,
showImageBadge,
}: {
launcher: SessionLauncher;
showImageBadge?: boolean;
}) {
const { pathname, hash } = useLocation();
const environment = launcher.environment;
Expand All @@ -175,6 +213,16 @@ function CustomImageEnvironmentValues({
? { imageUrl: environment.container_image }
: skipToken
);
const { data: resourcePools, isLoading: isLoadingResourcePools } =
computeResourcesApi.endpoints.getResourcePools.useQueryState({});
const resourcePool = useMemo(() => {
if (launcher?.resource_class_id == null || resourcePools == null) {
return undefined;
}
return resourcePools.find(({ classes }) =>
classes.some(({ id }) => id === launcher.resource_class_id)
);
}, [launcher?.resource_class_id, resourcePools]);
const search = useMemo(() => {
return `?${new URLSearchParams({
targetProvider: data?.provider?.id ?? "",
Expand All @@ -188,7 +236,14 @@ function CustomImageEnvironmentValues({
return (
<>
<div className="mb-2">
<SessionImageBadge data={data} loading={isLoading} />
{showImageBadge && (
<SessionImageBadge
data={data}
isLoading={isLoading}
resourcePool={resourcePool}
isLoadingResourcePools={isLoadingResourcePools}
/>
)}
{!isLoading && data?.accessible === false && (
<div className="mt-2">
{!data.connection && !data.provider ? (
Expand Down Expand Up @@ -336,6 +391,23 @@ function CustomBuildEnvironmentValues({
}
);

const { data: imageCheck, isLoading: isLoadingContainerImage } =
useGetSessionsImagesQuery(
environment.container_image != null
? { imageUrl: environment.container_image }
: skipToken
);
const { data: resourcePools, isLoading: isLoadingResourcePools } =
computeResourcesApi.endpoints.getResourcePools.useQueryState({});
const resourcePool = useMemo(() => {
if (launcher?.resource_class_id == null || resourcePools == null) {
return undefined;
}
return resourcePools.find(({ classes }) =>
classes.some(({ id }) => id === launcher.resource_class_id)
);
}, [launcher?.resource_class_id, resourcePools]);

// Invalidate launchers if the container image is not the same as the
// image from the last successful build
const dispatch = useAppDispatch();
Expand Down Expand Up @@ -368,7 +440,12 @@ function CustomBuildEnvironmentValues({
<NotReadyStatusBadge />
) : (
<>
<ReadyStatusBadge />
<SessionImageBadge
data={imageCheck}
isLoading={isLoadingContainerImage}
resourcePool={resourcePool}
isLoadingResourcePools={isLoadingResourcePools}
/>
{lastSuccessfulBuild && (
<BuildStatusDescription
isOldImage={
Expand Down Expand Up @@ -415,7 +492,7 @@ function CustomBuildEnvironmentValues({
Last build status:
</label>
<span>
<BuildStatusBadge status={lastBuild.status} />
<BuildStatusBadge buildStatus={lastBuild.status} />
</span>
</div>
)}
Expand Down Expand Up @@ -505,25 +582,6 @@ function EnvironmentJSONArrayRowWithLabel({
);
}

function ReadyStatusBadge() {
return (
<Badge
className={cx(
"border",
"bg-success-subtle",
"border-success",
"text-success-emphasis",
"fs-small",
"fw-normal"
)}
pill
>
<CircleFill className={cx("bi", "me-1")} />
Ready
</Badge>
);
}

function NotReadyStatusBadge() {
return (
<Badge
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -653,6 +653,7 @@ export type RemoteConfigurationFirecrest = {
export type RemoteConfiguration = RemoteConfigurationFirecrest;
export type IdleThreshold = number;
export type HibernationThreshold = number;
export type RuntimePlatform = "linux/amd64" | "linux/arm64";
export type ResourcePoolWithIdFiltered = {
quota?: QuotaWithId;
classes: ResourceClassWithIdFiltered[];
Expand All @@ -664,6 +665,7 @@ export type ResourcePoolWithIdFiltered = {
idle_threshold?: IdleThreshold;
hibernation_threshold?: HibernationThreshold;
cluster_id?: Ulid;
platform: RuntimePlatform;
};
export type ResourcePoolsWithIdFiltered = ResourcePoolWithIdFiltered[];
export type CpuFilter = number;
Expand All @@ -682,6 +684,7 @@ export type ResourcePoolWithId = {
cluster?: {
id: Ulid;
};
platform: RuntimePlatform;
};
export type QuotaWithOptionalId = {
cpu: Cpu;
Expand Down Expand Up @@ -711,6 +714,7 @@ export type ResourcePool = {
idle_threshold?: IdleThreshold;
hibernation_threshold?: HibernationThreshold;
cluster_id?: Ulid;
platform?: RuntimePlatform;
};
export type ResourceClassesWithId = ResourceClassWithId[];
export type ResourcePoolPut = {
Expand All @@ -723,6 +727,7 @@ export type ResourcePoolPut = {
idle_threshold?: IdleThreshold;
hibernation_threshold?: HibernationThreshold;
cluster_id?: Ulid;
platform: RuntimePlatform;
};
export type QuotaPatch = {
cpu?: Cpu;
Expand Down Expand Up @@ -766,6 +771,7 @@ export type ResourcePoolPatch = {
idle_threshold?: IdleThreshold;
hibernation_threshold?: HibernationThreshold;
cluster_id?: Ulid;
platform?: RuntimePlatform;
};
export type ResourceClassesWithIdResponse = ResourceClassWithId[];
export type ResourceClassPatch = {
Expand Down
Loading
Loading