Skip to content

Commit

Permalink
fix: display back the icons of registries (#5843)
Browse files Browse the repository at this point in the history
* fix: display back the icons of registries

instead of resolving images as files, embed them as
resources using vite

fixes #5742
Signed-off-by: Florent Benoit <fbenoit@redhat.com>
  • Loading branch information
benoitf committed Feb 6, 2024
1 parent 6588385 commit ea9670c
Show file tree
Hide file tree
Showing 5 changed files with 105 additions and 20 deletions.
4 changes: 2 additions & 2 deletions extensions/registries/package.json
Expand Up @@ -13,8 +13,8 @@
"source": "./src/extension.ts",
"scripts": {
"build": "vite build && node ./scripts/build.js",
"test": "vitest run --coverage --passWithNoTests",
"test:watch": "vitest watch --coverage --passWithNoTests",
"test": "vitest run --coverage",
"test:watch": "vitest watch --coverage",
"watch": "vite build --watch"
},
"dependencies": {
Expand Down
61 changes: 61 additions & 0 deletions extensions/registries/src/extension.spec.ts
@@ -0,0 +1,61 @@
/**********************************************************************
* Copyright (C) 2024 Red Hat, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* SPDX-License-Identifier: Apache-2.0
***********************************************************************/

/* eslint-disable @typescript-eslint/no-explicit-any */

import { beforeAll, beforeEach, expect, test, vi } from 'vitest';
import { activate, stripImagePrefix } from './extension';
import * as extensionApi from '@podman-desktop/api';

vi.mock('@podman-desktop/api', async () => {
return {
registry: {
suggestRegistry: vi.fn(),
},
};
});

beforeAll(() => {});

beforeEach(() => {
vi.clearAllMocks();
});

test('check remove prefix', async () => {
const base64Content = stripImagePrefix('data:image/png;base64,content');
expect(base64Content).toBe('content');
});

test('activate is registering 4 registries', async () => {
const extensionContext = { subscriptions: [] } as unknown as extensionApi.ExtensionContext;

await activate(extensionContext);

// should be called 4 times
expect(vi.mocked(extensionApi.registry.suggestRegistry)).toHaveBeenCalledTimes(4);

// should be called with the right parameters
expect(vi.mocked(extensionApi.registry.suggestRegistry)).toHaveBeenCalledWith({
name: 'Docker Hub',
url: 'docker.io',
icon: '/src/images/docker.io.png',
});

// 4 subscriptions/disposables should be added
expect(extensionContext.subscriptions.length).toBe(4);
});
35 changes: 18 additions & 17 deletions extensions/registries/src/extension.ts
@@ -1,5 +1,5 @@
/**********************************************************************
* Copyright (C) 2023 Red Hat, Inc.
* Copyright (C) 2023-2024 Red Hat, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
Expand All @@ -16,26 +16,23 @@
***********************************************************************/

import * as extensionApi from '@podman-desktop/api';
import * as fs from 'node:fs';

// The image path for the registry logos
const imagePath = __dirname + '/images/';
const imageExtension = '.png';
import dockerIoImage from './images/docker.io.png';
import ghcrIoImage from './images/ghcr.io.png';
import gcrIoImage from './images/gcr.io.png';
import quayIoImage from './images/quay.io.png';

// eslint-disable-next-line @typescript-eslint/no-unused-vars
export async function activate(extensionContext: extensionApi.ExtensionContext): Promise<void> {
// For each defaultRegistries, suggest the registry to Podman Desktop
for (const registry of defaultRegistries) {
// Let's check the folder for <registry.url>.png
const iconLocation = imagePath.concat(registry.url, imageExtension);

// If the icon exists, load the image, convert it to base64 and add it
if (fs.existsSync(iconLocation)) {
registry.icon = await base64EncodeFile(iconLocation);
}
// remove the image prefix from vite base64 object
const registryEntry = {
...registry,
icon: stripImagePrefix(registry.icon),
};

// Suggest it to the registry and add to subscriptions
const disposable = extensionApi.registry.suggestRegistry(registry);
const disposable = extensionApi.registry.suggestRegistry(registryEntry);
extensionContext.subscriptions.push(disposable);
}
}
Expand All @@ -50,22 +47,26 @@ const defaultRegistries: extensionApi.RegistrySuggestedProvider[] = [
{
name: 'Docker Hub',
url: 'docker.io',
icon: dockerIoImage,
},
{
name: 'Red Hat Quay',
url: 'quay.io',
icon: quayIoImage,
},
{
name: 'GitHub',
url: 'ghcr.io',
icon: ghcrIoImage,
},
{
name: 'Google Container Registry',
url: 'gcr.io',
icon: gcrIoImage,
},
];

// Return the base64 of the file
async function base64EncodeFile(file: string): Promise<string> {
return fs.promises.readFile(file).then(buffer => buffer.toString('base64'));
// Remove data:image/png;base64,
export function stripImagePrefix(imageContent: string): string {
return imageContent.replace(/^data:image\/\w+;base64,/, '');
}
3 changes: 2 additions & 1 deletion extensions/registries/tsconfig.json
Expand Up @@ -7,11 +7,12 @@
"outDir": "dist",
"target": "esnext",
"moduleResolution": "Node",
"allowSyntheticDefaultImports": true,
"resolveJsonModule": true,
"skipLibCheck": true,
"types": ["node"]
},
"include": ["src"],
"include": ["src", "types/*.d.ts"],
"ts-node": {
"compilerOptions": {
"module": "CommonJS",
Expand Down
22 changes: 22 additions & 0 deletions extensions/registries/types/template.d.ts
@@ -0,0 +1,22 @@
/**********************************************************************
* Copyright (C) 2024 Red Hat, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* SPDX-License-Identifier: Apache-2.0
***********************************************************************/

declare module '*.png' {
const contents: string;
export = contents;
}

0 comments on commit ea9670c

Please sign in to comment.