1diff --git a/src/deploy/search/index.ts b/src/deploy/search/index.ts
2index 6d292d5e..7483dc9a 100644
3--- a/src/deploy/search/index.ts
4+++ b/src/deploy/search/index.ts
5@@ -1,4 +1,4 @@
6-import { selectDeploymentsAsList } from "@app/deployment";
7+import { selectDeployments } from "@app/deployment";
8 import { WebState, schema } from "@app/schema";
9 import { selectSourcesAsList } from "@app/source";
10 import { DeployServiceRow, DeploySource, Deployment } from "@app/types";
11@@ -150,17 +150,16 @@ export const selectAppsForTable = createSelector(
12 selectEnvironments,
13 selectOperationsAsList,
14 selectServicesAsList,
15- selectDeploymentsAsList,
16+ selectDeployments,
17 (apps, envs, ops, services, deployments) =>
18 apps
19 .map((app): DeployAppRow => {
20 const env = findEnvById(envs, { id: app.environmentId });
21 const appOps = findOperationsByAppId(ops, app.id);
22 const lastOperation = appOps?.[0] || schema.operations.empty;
23- const currentDeployment =
24- deployments.find(
25- (d) => d.id.toString() === app.currentDeploymentId.toString(),
26- ) || schema.deployments.empty;
27+ const currentDeployment = schema.deployments.findById(deployments, {
28+ id: app.currentDeploymentId,
29+ });
30 const appServices = services.filter((s) => s.appId === app.id);
31 const cost = appServices.reduce((acc, service) => {
32 const mm = calcServiceMetrics(service);
33@@ -375,19 +374,19 @@ export const selectAppsForTableSearchBySourceId = createSelector(
34 },
35 );
36
37-export type GitCommit = {
38+export interface GitCommit {
39 sha: string;
40 ref: string;
41 message: string;
42 date: string | null;
43 url: string;
44-};
45+}
46
47-export type DeploySourceRow = DeploySource & {
48+export interface DeploySourceRow extends DeploySource {
49 apps: DeployAppRow[];
50 deployments: Deployment[];
51 liveCommits: GitCommit[];
52-};
53+}
54
55 export const selectSourcesForTable = createSelector(
56 selectSourcesAsList,
57@@ -395,7 +394,7 @@ export const selectSourcesForTable = createSelector(
58 (sources, apps) =>
59 sources.map<DeploySourceRow>((source) => {
60 const sourceApps = apps.filter(
61- (app) => app.currentSourceId.toString() === source.id.toString(),
62+ (app) => app.currentSourceId === source.id,
63 );
64 const sourceDeployments = sourceApps.map((app) => app.currentDeployment);
65 const distinctCommits = sourceDeployments.reduce<
66@@ -403,7 +402,7 @@ export const selectSourcesForTable = createSelector(
67 >((commits, deployment) => {
68 const sha = deployment.gitCommitSha;
69
70- if (!sha || !!commits[sha]) {
71+ if (!sha || Object.hasOwn(commits, sha)) {
72 return commits;
73 }
74
75diff --git a/src/deployment/index.ts b/src/deployment/index.ts
76index 1c864d2d..ca430447 100644
77--- a/src/deployment/index.ts
78+++ b/src/deployment/index.ts
79@@ -5,7 +5,7 @@ import { WebState, schema } from "@app/schema";
80 import { Deployment, LinkResponse, OperationStatus } from "@app/types";
81
82 export interface DeploymentResponse {
83- id: string;
84+ id: number;
85 status: string;
86 docker_image: string | null;
87 docker_repository_url: string | null;
88@@ -32,7 +32,7 @@ export const defaultDeploymentResponse = (
89 ): DeploymentResponse => {
90 const now = new Date().toISOString();
91 return {
92- id: "",
93+ id: -1,
94 status: "",
95 docker_image: "",
96 docker_repository_url: "",
97@@ -84,6 +84,7 @@ export const deserializeDeployment = (
98 };
99
100 export const selectDeploymentById = schema.deployments.selectById;
101+export const selectDeployments = schema.deployments.selectTable;
102 export const selectDeploymentsAsList = createSelector(
103 schema.deployments.selectTableAsList,
104 (deployments) =>
105diff --git a/src/mocks/data.ts b/src/mocks/data.ts
106index 3018db9a..8b12f53d 100644
107--- a/src/mocks/data.ts
108+++ b/src/mocks/data.ts
109@@ -672,7 +672,7 @@ export const testSaml = defaultSamlConfigurationResponse({
110 const deployDate = new Date("2023-12-17T00:00:00Z").toISOString();
111
112 export const testDeploymentGit = defaultDeploymentResponse({
113- id: "3",
114+ id: 3,
115 docker_image: "",
116 git_repository_url: "https://github.com/aptible/app-ui",
117 git_ref: "v3",
118@@ -694,7 +694,7 @@ export const testDeploymentGit = defaultDeploymentResponse({
119 });
120
121 export const testDeploymentDocker = defaultDeploymentResponse({
122- id: "2",
123+ id: 2,
124 docker_image: "quay.io/aptible/cloud-ui:v200",
125 docker_repository_url: "https://quay.io/repositories/aptible/cloud-ui",
126 git_repository_url: "https://github.com/aptible/app-ui",
127@@ -717,7 +717,7 @@ export const testDeploymentDocker = defaultDeploymentResponse({
128 });
129
130 export const testDeploymentEmpty = defaultDeploymentResponse({
131- id: "1",
132+ id: 1,
133 docker_image: "",
134 git_repository_url: "",
135 git_ref: "",
136diff --git a/src/source/index.ts b/src/source/index.ts
137index 71f9cf75..1173f6ca 100644
138--- a/src/source/index.ts
139+++ b/src/source/index.ts
140@@ -4,7 +4,7 @@ import { schema } from "@app/schema";
141 import { DeploySource } from "@app/types";
142
143 interface DeploySourceResponse {
144- id: string;
145+ id: number;
146 display_name: string;
147 url: string;
148 created_at: string;
149@@ -17,7 +17,7 @@ export const defaultDeploySourceResponse = (
150 ): DeploySourceResponse => {
151 const now = new Date().toISOString();
152 return {
153- id: "",
154+ id: -1,
155 display_name: "",
156 url: "",
157 created_at: now,
158@@ -29,7 +29,7 @@ export const defaultDeploySourceResponse = (
159
160 const deserializeDeploySource = (r: DeploySourceResponse): DeploySource => {
161 return {
162- id: r.id,
163+ id: `${r.id}`,
164 displayName: r.display_name || "Unknown",
165 url: r.url,
166 createdAt: r.created_at,
167diff --git a/src/ui/pages/sources.tsx b/src/ui/pages/sources.tsx
168index 7f01d23d..6bf91ca1 100644
169--- a/src/ui/pages/sources.tsx
170+++ b/src/ui/pages/sources.tsx
171@@ -52,31 +52,31 @@ function SourceListRow({ source }: { source: DeploySourceRow }) {
172 </Link>
173 </Td>
174 <Td>
175- {(liveCommits.length && (
176- <div className="flex flex-row gap-1 items-center">
177- {liveCommits.map((liveCommit) => (
178- <Tooltip
179- key={liveCommit.sha}
180- fluid
181- theme="light"
182- className="py-1"
183- text={
184- <GitRef
185- gitRef={liveCommit.ref}
186- commitSha={liveCommit.sha}
187- commitUrl={liveCommit.url}
188- />
189- }
190- >
191- <Link
192- to="#"
193- className="block bg-gray-300 h-[16px] w-[6px] hover:bg-indigo rounded-md"
194+ {liveCommits.length === 0 ? <em>No commit information</em> : null}
195+
196+ <Group variant="horizontal" size="xs" className="items-center">
197+ {liveCommits.map((liveCommit) => (
198+ <Tooltip
199+ key={liveCommit.sha}
200+ fluid
201+ theme="light"
202+ className="py-1"
203+ text={
204+ <GitRef
205+ gitRef={liveCommit.ref}
206+ commitSha={liveCommit.sha}
207+ commitUrl={liveCommit.url}
208 />
209- </Tooltip>
210- ))}
211- {extraLiveCommits ? <p>+{extraLiveCommits}</p> : null}
212- </div>
213- )) || <em>No commit information</em>}
214+ }
215+ >
216+ <Link
217+ to="#"
218+ className="block bg-gray-300 h-[16px] w-[6px] hover:bg-indigo rounded-md"
219+ />
220+ </Tooltip>
221+ ))}
222+ {extraLiveCommits ? <p>+{extraLiveCommits}</p> : null}
223+ </Group>
224 </Td>
225 <Td variant="center" className="center items-center justify-center">
226 <div className="text-center">{source.apps.length}</div>