Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New GPU stats api #478

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open
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
4 changes: 2 additions & 2 deletions src/controller/abstractServiceController.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import type { Service } from "../modules/service/types";
import type { GPUStats, Service } from "../modules/service/types";
import type { Registry } from "../modules/settings/types";
import type { Interface } from "../shared/helpers/interfaces";

Expand All @@ -21,7 +21,7 @@ abstract class AbstractServiceController {
abstract getLogs(serviceId: string): Promise<string>;
abstract getServiceStats(serviceId: string): Promise<Record<string, string>>;
abstract getSystemStats(): Promise<Record<string, string>>;
abstract getGPUStats(): Promise<Record<string, string>>;
abstract getGPUStats(): Promise<GPUStats>;
abstract getInterfaces(): Promise<Interface[]>;
abstract addService(service: Service): Promise<void>;
abstract addRegistry(registry: Registry): Promise<void>;
Expand Down
6 changes: 3 additions & 3 deletions src/controller/binariesController.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { invoke } from "@tauri-apps/api/tauri";
import type { Registry } from "modules/settings/types";

import type { Service, ServiceBinary } from "../modules/service/types";
import type { GPUStats, Service, ServiceBinary } from "../modules/service/types";
import type { Interface } from "../shared/helpers/interfaces";
import interfaces from "../shared/helpers/interfaces";

Expand Down Expand Up @@ -59,8 +59,8 @@ class BinariesController extends AbstractServiceController {
return await invoke<string>("get_logs_for_service", { serviceId });
}

async getGPUStats(): Promise<Record<string, string>> {
return await invoke<Record<string, string>>("get_gpu_stats");
async getGPUStats(): Promise<GPUStats> {
return await invoke<GPUStats>("get_gpu_stats");
}

async getServiceStats(serviceId: string): Promise<Record<string, string>> {
Expand Down
4 changes: 2 additions & 2 deletions src/controller/dockerController.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import type { Registry } from "modules/settings/types";

import downloadServiceStream from "../modules/service/api/downloadServiceStream";
import type { Service, ServiceDocker } from "../modules/service/types";
import type { GPUStats, Service, ServiceDocker } from "../modules/service/types";
import api from "../shared/api/v1";
import type { Interface } from "../shared/helpers/interfaces";
import useSettingStore from "../shared/store/setting";
Expand Down Expand Up @@ -83,7 +83,7 @@ class DockerController extends AbstractServiceController {
return response.data;
}

async getGPUStats(): Promise<Record<string, string>> {
async getGPUStats(): Promise<GPUStats> {
const response = await api().get("v1/gpu-stats-all/");
return response.data;
}
Expand Down
9 changes: 4 additions & 5 deletions src/controller/serviceController.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import type { Service } from "../modules/service/types";
import type { GPUStats, Service } from "../modules/service/types";
import type { Registry } from "../modules/settings/types";
import type { Interface } from "../shared/helpers/interfaces";
import useSettingStore from "../shared/store/setting";
Expand Down Expand Up @@ -31,7 +31,7 @@ interface IServiceController {
getLogs(serviceId: string, serviceType: Service["serviceType"]): Promise<string>;
getServiceStats(serviceId: string, serviceType: Service["serviceType"]): Promise<any>;
getSystemStats(serviceType: Service["serviceType"]): Promise<any>;
getGPUStats(serviceType: Service["serviceType"]): Promise<any>;
getGPUStats(serviceType: Service["serviceType"]): Promise<GPUStats>;
getInterfaces(serviceType: Service["serviceType"]): Promise<Interface[]>;
addService(service: Service, serviceType: Service["serviceType"]): Promise<void>;
addRegistry(registry: Registry, serviceType: Service["serviceType"]): Promise<void>;
Expand Down Expand Up @@ -182,15 +182,14 @@ class ServiceController implements IServiceController {
return {};
}
}

async getGPUStats(serviceType: Service["serviceType"]): Promise<Record<string, string>> {
async getGPUStats(serviceType: Service["serviceType"]): Promise<GPUStats> {
// We check the env (browser or desktop) to determine serviceType
if (serviceType === "docker") {
return await this.dockerController.getGPUStats();
} else if (serviceType === "binary") {
return await this.binariesController.getGPUStats();
} else {
return {};
return {} as GPUStats;
}
}

Expand Down
16 changes: 14 additions & 2 deletions src/modules/service/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -81,12 +81,24 @@ export type Stats = {
storage_percentage: number;
};

type GPUInfos = {
gpu_name: string;
total_memory: number;
used_memory: number;
free_memory: number;
utilised_memory: number;
load: number;
};

export type GPUStats = {
gpu_name: string | null;
total_memory: number | null;
used_memory: number | null;
memory_percentage: number | null;
free_memory: number | null;
average_utilised_memory: number | null;
average_load: number | null;
gpus: GPUInfos[];
};

export type Message = {
message: string;
};
Expand Down
59 changes: 30 additions & 29 deletions src/modules/settings/components/GPUResources.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,40 +3,41 @@ import useGPUStats from "shared/hooks/useGPUStats";

const GPUResources = () => {
const { data } = useGPUStats();

return (
<>
<h2 className="text-grey-300 text-lg mt-10 mb-4">GPUs</h2>
<div className="grid lg:grid-cols-3 sm:grid-cols-2 gap-4">
{data?.gpu_name ? (
<div>
<div className="gpu-resources__header">
<img src={nvidia_logo} alt="nvidia-logo" />
</div>
<div className="gpu-resources__body">
<h3 className="text-grey-300 text-lg">{data.gpu_name}</h3>
<ul className="!p-0">
<li className="mt-4">
<div className="flex flex-wrap justify-between">
<span className="flex items-center">Memory&nbsp;</span>
<span>
{data.used_memory} / {data.total_memory} GiB
</span>
</div>
<div className="progress">
<div
className="progress-container"
style={{
width: `${data.memory_percentage}%`,
}}
></div>
</div>
</li>
</ul>
{data?.gpus?.map((gpu) => {
return (
<div key={gpu.gpu_name}>
<div className="gpu-resources__header">
<img src={nvidia_logo} alt="nvidia-logo" />
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

May not be nvidia, on say mac or other platforms.

From docker we can assume for now that it's always Nvidia perhaps, but for mac and other platforms I am not quite sure having nvidia logo is correct.

</div>
<div className="gpu-resources__body">
<h3 className="text-grey-300 text-lg">{gpu.gpu_name}</h3>
<ul className="!p-0">
<li className="mt-4">
<div className="flex flex-wrap justify-between">
<span className="flex items-center">Memory&nbsp;</span>
<span>
{gpu.used_memory} / {gpu.total_memory} GiB
</span>
</div>
<div className="progress">
<div
className="progress-container"
style={{
width: `${gpu.utilised_memory * 100}%`,
}}
></div>
</div>
</li>
</ul>
</div>
</div>
</div>
) : (
<p className="text-white opacity-70">No GPUs available</p>
)}
);
}) ?? <p className="text-white opacity-70">No GPUs available</p>}
</div>
</>
);
Expand Down