mirror of
https://github.com/lensapp/lens.git
synced 2025-05-20 05:10:56 +00:00
Merge branch 'master' into fix-edit-resource-not-close-tab-on-error
This commit is contained in:
commit
ff6bc562c3
103
.github/workflows/daily-alpha.yml
vendored
Normal file
103
.github/workflows/daily-alpha.yml
vendored
Normal file
@ -0,0 +1,103 @@
|
|||||||
|
name: Release daily alpha
|
||||||
|
on:
|
||||||
|
schedule:
|
||||||
|
- cron: 0 0 30 * 1-5 # At 12:30am UTC work day
|
||||||
|
workflow_dispatch: # for testing
|
||||||
|
jobs:
|
||||||
|
tag:
|
||||||
|
outputs:
|
||||||
|
tagname: v${{ steps.version.outputs.VERSION }}
|
||||||
|
version: ${{ steps.version.outputs.VERSION }}
|
||||||
|
continue: ${{ steps.create-branch.outputs.CONTINUE }}
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v3
|
||||||
|
|
||||||
|
- name: Setup Node.js
|
||||||
|
uses: actions/setup-node@v3
|
||||||
|
with:
|
||||||
|
node-version: "16.x"
|
||||||
|
registry-url: "https://npm.pkg.github.com"
|
||||||
|
|
||||||
|
- name: Install deps
|
||||||
|
run: |
|
||||||
|
npm i --location=global semver
|
||||||
|
npm install
|
||||||
|
|
||||||
|
sudo apt-get install -y ripgrep
|
||||||
|
env:
|
||||||
|
NODE_AUTH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
- name: Bump version
|
||||||
|
id: version
|
||||||
|
run: npm run bump-version-for-cron
|
||||||
|
- name: Check if branch already exists
|
||||||
|
id: check-branch
|
||||||
|
run: git ls-remote --exit-code --tags origin v${{ steps.version.outputs.VERSION }}
|
||||||
|
continue-on-error: true
|
||||||
|
- name: Create branch and tag and push
|
||||||
|
id: create-branch
|
||||||
|
run: |
|
||||||
|
# failure means that the tag doesn't exist so we should create it
|
||||||
|
if [ ${{ steps.check-branch.outcome }} != 'failure' ]; then
|
||||||
|
echo "CONTINUE=false" >> "$GITHUB_OUTPUT"
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
git config --global user.email "bot@k8slens.dev"
|
||||||
|
git config --global user.name "k8slens bot"
|
||||||
|
|
||||||
|
git checkout -b release/v${{ steps.version.outputs.VERSION }}
|
||||||
|
git add .
|
||||||
|
git commit -sm "Release ${{ steps.version.outputs.VERSION }}"
|
||||||
|
git tag v${{ steps.version.outputs.VERSION }}
|
||||||
|
git push origin v${{ steps.version.outputs.VERSION }}
|
||||||
|
echo "CONTINUE=true" >> "$GITHUB_OUTPUT"
|
||||||
|
create_release:
|
||||||
|
outputs:
|
||||||
|
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
||||||
|
version: ${{ needs.tag.outputs.version }}
|
||||||
|
needs: [tag]
|
||||||
|
if: ${{ needs.tag.outputs.continue == 'true' }}
|
||||||
|
runs-on: ubuntu-20.04
|
||||||
|
steps:
|
||||||
|
- name: Create GitHub release
|
||||||
|
uses: softprops/action-gh-release@v1
|
||||||
|
id: create_release
|
||||||
|
env:
|
||||||
|
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
with:
|
||||||
|
tag_name: ${{ needs.tag.outputs.tagname }}
|
||||||
|
name: ${{ needs.tag.outputs.tagname }}
|
||||||
|
generate_release_notes: true
|
||||||
|
prerelease: true
|
||||||
|
release_packages:
|
||||||
|
needs: [create_release]
|
||||||
|
runs-on: ubuntu-20.04
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v3
|
||||||
|
with:
|
||||||
|
ref: v${{ needs.create_release.outputs.version }}
|
||||||
|
- name: Use Node.js ${{ env.NODE_VERSION }}
|
||||||
|
uses: actions/setup-node@v3
|
||||||
|
with:
|
||||||
|
node-version: "16.x"
|
||||||
|
cache: "npm"
|
||||||
|
registry-url: "https://npm.pkg.github.com"
|
||||||
|
- name: Build package
|
||||||
|
shell: bash
|
||||||
|
run: |
|
||||||
|
yarn install --frozen-lockfile
|
||||||
|
yarn run build
|
||||||
|
env:
|
||||||
|
NODE_AUTH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
- name: Release to GitHub NPM registry
|
||||||
|
run: |
|
||||||
|
npm config set '//registry.npmjs.org/:_authToken' "${NPM_TOKEN}"
|
||||||
|
yarn lerna \
|
||||||
|
publish from-package \
|
||||||
|
--no-push \
|
||||||
|
--no-git-tag-version \
|
||||||
|
--yes \
|
||||||
|
--dist-tag cron
|
||||||
|
env:
|
||||||
|
NPM_TOKEN: ${{ secrets.NPM_TOKEN }}
|
||||||
38
.github/workflows/publish-master-npm.yml
vendored
38
.github/workflows/publish-master-npm.yml
vendored
@ -1,38 +0,0 @@
|
|||||||
name: Publish NPM Package `master`
|
|
||||||
on:
|
|
||||||
pull_request:
|
|
||||||
types:
|
|
||||||
- closed
|
|
||||||
concurrency:
|
|
||||||
group: publish-master-npm
|
|
||||||
cancel-in-progress: true
|
|
||||||
jobs:
|
|
||||||
publish:
|
|
||||||
name: Publish Extensions NPM Package `master`
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
if: ${{ github.event.pull_request.merged == true && contains(github.event.pull_request.labels.*.name, 'area/extension') }}
|
|
||||||
strategy:
|
|
||||||
matrix:
|
|
||||||
node-version: [16.x]
|
|
||||||
steps:
|
|
||||||
- name: Checkout Release
|
|
||||||
uses: actions/checkout@v3
|
|
||||||
with:
|
|
||||||
fetch-depth: 0
|
|
||||||
|
|
||||||
- name: Using Node.js ${{ matrix.node-version }}
|
|
||||||
uses: actions/setup-node@v3
|
|
||||||
with:
|
|
||||||
node-version: ${{ matrix.node-version }}
|
|
||||||
|
|
||||||
- name: Generate NPM packages
|
|
||||||
run: |
|
|
||||||
yarn install --frozen-lockfile
|
|
||||||
yarn run build
|
|
||||||
|
|
||||||
- name: Publish NPM package
|
|
||||||
run: |
|
|
||||||
npm config set '//registry.npmjs.org/:_authToken' "${NPM_TOKEN}"
|
|
||||||
yarn lerna publish from-package --dist-tag master --no-push --no-git-tag-version --yes
|
|
||||||
env:
|
|
||||||
NPM_TOKEN: ${{ secrets.NPM_TOKEN }}
|
|
||||||
@ -3,20 +3,13 @@
|
|||||||
* Licensed under MIT License. See LICENSE in root directory for more information.
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
*/
|
*/
|
||||||
import { getInjectable } from "@ogre-tools/injectable";
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
import { createLogger, format } from "winston";
|
|
||||||
import type { Logger } from "./logger";
|
import type { Logger } from "./logger";
|
||||||
import { loggerTransportInjectionToken } from "./logger/transports";
|
import winstonLoggerInjectable from "./winston-logger.injectable";
|
||||||
|
|
||||||
const loggerInjectable = getInjectable({
|
const loggerInjectable = getInjectable({
|
||||||
id: "logger",
|
id: "logger",
|
||||||
instantiate: (di): Logger => {
|
instantiate: (di): Logger => {
|
||||||
const baseLogger = createLogger({
|
const baseLogger = di.inject(winstonLoggerInjectable);
|
||||||
format: format.combine(
|
|
||||||
format.splat(),
|
|
||||||
format.simple(),
|
|
||||||
),
|
|
||||||
transports: di.injectMany(loggerTransportInjectionToken),
|
|
||||||
});
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
debug: (message, ...data) => baseLogger.debug(message, ...data),
|
debug: (message, ...data) => baseLogger.debug(message, ...data),
|
||||||
|
|||||||
20
packages/core/src/common/winston-logger.injectable.ts
Normal file
20
packages/core/src/common/winston-logger.injectable.ts
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { createLogger, format } from "winston";
|
||||||
|
import { loggerTransportInjectionToken } from "./logger/transports";
|
||||||
|
|
||||||
|
const winstonLoggerInjectable = getInjectable({
|
||||||
|
id: "winston-logger",
|
||||||
|
instantiate: (di) => createLogger({
|
||||||
|
format: format.combine(
|
||||||
|
format.splat(),
|
||||||
|
format.simple(),
|
||||||
|
),
|
||||||
|
transports: di.injectMany(loggerTransportInjectionToken),
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
|
||||||
|
export default winstonLoggerInjectable;
|
||||||
@ -27,6 +27,12 @@ export interface UrlSource {
|
|||||||
}
|
}
|
||||||
export type ContentSource = RequireExactlyOne<FileSource & UrlSource>;
|
export type ContentSource = RequireExactlyOne<FileSource & UrlSource>;
|
||||||
|
|
||||||
|
enum ChromiumNetError {
|
||||||
|
SUCCESS = 0,
|
||||||
|
FAILURE = 1,
|
||||||
|
RESULT_FROM_CHROMIUM,
|
||||||
|
}
|
||||||
|
|
||||||
export interface ElectronWindowConfiguration {
|
export interface ElectronWindowConfiguration {
|
||||||
id: string;
|
id: string;
|
||||||
title: string;
|
title: string;
|
||||||
@ -112,6 +118,15 @@ const createElectronWindowInjectable = getInjectable({
|
|||||||
|
|
||||||
applicationWindowState.manage(browserWindow);
|
applicationWindowState.manage(browserWindow);
|
||||||
|
|
||||||
|
browserWindow.webContents.session.setCertificateVerifyProc((request, shouldBeTrusted) => {
|
||||||
|
const { certificate } = request;
|
||||||
|
const cert = new X509Certificate(certificate.data);
|
||||||
|
const shouldTrustCert = cert.raw.length === lensProxyX509Cert.raw.length
|
||||||
|
&& timingSafeEqual(cert.raw, lensProxyX509Cert.raw);
|
||||||
|
|
||||||
|
shouldBeTrusted(shouldTrustCert ? ChromiumNetError.SUCCESS : ChromiumNetError.RESULT_FROM_CHROMIUM);
|
||||||
|
});
|
||||||
|
|
||||||
browserWindow
|
browserWindow
|
||||||
.on("focus", () => {
|
.on("focus", () => {
|
||||||
configuration.onFocus?.();
|
configuration.onFocus?.();
|
||||||
@ -126,13 +141,6 @@ const createElectronWindowInjectable = getInjectable({
|
|||||||
.webContents.on("dom-ready", () => {
|
.webContents.on("dom-ready", () => {
|
||||||
configuration.onDomReady?.();
|
configuration.onDomReady?.();
|
||||||
})
|
})
|
||||||
.on("certificate-error", (event, url, error, certificate, shouldBeTrusted) => {
|
|
||||||
const cert = new X509Certificate(certificate.data);
|
|
||||||
const shouldTrustCert = cert.raw.length === lensProxyX509Cert.raw.length
|
|
||||||
&& timingSafeEqual(cert.raw, lensProxyX509Cert.raw);
|
|
||||||
|
|
||||||
shouldBeTrusted(shouldTrustCert);
|
|
||||||
})
|
|
||||||
.on("did-fail-load", (_event, code, desc) => {
|
.on("did-fail-load", (_event, code, desc) => {
|
||||||
logger.error(
|
logger.error(
|
||||||
`[CREATE-ELECTRON-WINDOW]: Failed to load window "${configuration.id}"`,
|
`[CREATE-ELECTRON-WINDOW]: Failed to load window "${configuration.id}"`,
|
||||||
|
|||||||
@ -54,7 +54,9 @@ export async function bootstrap(di: DiContainer) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await initializeApp(() => unmountComponentAtNode(rootElem));
|
await initializeApp(() => {
|
||||||
|
unmountComponentAtNode(rootElem);
|
||||||
|
});
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error(`[BOOTSTRAP]: view initialization error: ${error}`, {
|
console.error(`[BOOTSTRAP]: view initialization error: ${error}`, {
|
||||||
origin: location.href,
|
origin: location.href,
|
||||||
|
|||||||
@ -12,6 +12,7 @@ import emitAppEventInjectable from "../../../../common/app-event-bus/emit-event.
|
|||||||
import loadExtensionsInjectable from "../../load-extensions.injectable";
|
import loadExtensionsInjectable from "../../load-extensions.injectable";
|
||||||
import loggerInjectable from "../../../../common/logger.injectable";
|
import loggerInjectable from "../../../../common/logger.injectable";
|
||||||
import showErrorNotificationInjectable from "../../../components/notifications/show-error-notification.injectable";
|
import showErrorNotificationInjectable from "../../../components/notifications/show-error-notification.injectable";
|
||||||
|
import closeRendererLogFileInjectable from "../../../logger/close-renderer-log-file.injectable";
|
||||||
|
|
||||||
const initClusterFrameInjectable = getInjectable({
|
const initClusterFrameInjectable = getInjectable({
|
||||||
id: "init-cluster-frame",
|
id: "init-cluster-frame",
|
||||||
@ -29,6 +30,7 @@ const initClusterFrameInjectable = getInjectable({
|
|||||||
emitAppEvent: di.inject(emitAppEventInjectable),
|
emitAppEvent: di.inject(emitAppEventInjectable),
|
||||||
logger: di.inject(loggerInjectable),
|
logger: di.inject(loggerInjectable),
|
||||||
showErrorNotification: di.inject(showErrorNotificationInjectable),
|
showErrorNotification: di.inject(showErrorNotificationInjectable),
|
||||||
|
closeFileLogging: di.inject(closeRendererLogFileInjectable),
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@ -2,6 +2,7 @@
|
|||||||
* Copyright (c) OpenLens Authors. All rights reserved.
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
* Licensed under MIT License. See LICENSE in root directory for more information.
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
*/
|
*/
|
||||||
|
import { once } from "lodash";
|
||||||
import type { Cluster } from "../../../../common/cluster/cluster";
|
import type { Cluster } from "../../../../common/cluster/cluster";
|
||||||
import type { CatalogEntityRegistry } from "../../../api/catalog/entity/registry";
|
import type { CatalogEntityRegistry } from "../../../api/catalog/entity/registry";
|
||||||
import type { ShowNotification } from "../../../components/notifications";
|
import type { ShowNotification } from "../../../components/notifications";
|
||||||
@ -18,6 +19,7 @@ interface Dependencies {
|
|||||||
emitAppEvent: EmitAppEvent;
|
emitAppEvent: EmitAppEvent;
|
||||||
logger: Logger;
|
logger: Logger;
|
||||||
showErrorNotification: ShowNotification;
|
showErrorNotification: ShowNotification;
|
||||||
|
closeFileLogging: () => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
const logPrefix = "[CLUSTER-FRAME]:";
|
const logPrefix = "[CLUSTER-FRAME]:";
|
||||||
@ -30,6 +32,7 @@ export const initClusterFrame = ({
|
|||||||
emitAppEvent,
|
emitAppEvent,
|
||||||
logger,
|
logger,
|
||||||
showErrorNotification,
|
showErrorNotification,
|
||||||
|
closeFileLogging,
|
||||||
}: Dependencies) =>
|
}: Dependencies) =>
|
||||||
async (unmountRoot: () => void) => {
|
async (unmountRoot: () => void) => {
|
||||||
// TODO: Make catalogEntityRegistry already initialized when passed as dependency
|
// TODO: Make catalogEntityRegistry already initialized when passed as dependency
|
||||||
@ -73,11 +76,14 @@ export const initClusterFrame = ({
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
window.onbeforeunload = () => {
|
const onCloseFrame = once(() => {
|
||||||
logger.info(
|
logger.info(
|
||||||
`${logPrefix} Unload dashboard, clusterId=${(hostedCluster.id)}, frameId=${frameRoutingId}`,
|
`${logPrefix} Unload dashboard, clusterId=${(hostedCluster.id)}, frameId=${frameRoutingId}`,
|
||||||
);
|
);
|
||||||
|
closeFileLogging();
|
||||||
unmountRoot();
|
unmountRoot();
|
||||||
};
|
});
|
||||||
|
|
||||||
|
window.addEventListener("beforeunload", onCloseFrame);
|
||||||
|
window.addEventListener("pagehide", onCloseFrame);
|
||||||
};
|
};
|
||||||
|
|||||||
@ -13,6 +13,7 @@ import loggerInjectable from "../../../common/logger.injectable";
|
|||||||
import { delay } from "../../../common/utils";
|
import { delay } from "../../../common/utils";
|
||||||
import { broadcastMessage } from "../../../common/ipc";
|
import { broadcastMessage } from "../../../common/ipc";
|
||||||
import { bundledExtensionsLoaded } from "../../../common/ipc/extension-handling";
|
import { bundledExtensionsLoaded } from "../../../common/ipc/extension-handling";
|
||||||
|
import closeRendererLogFileInjectable from "../../logger/close-renderer-log-file.injectable";
|
||||||
|
|
||||||
const initRootFrameInjectable = getInjectable({
|
const initRootFrameInjectable = getInjectable({
|
||||||
id: "init-root-frame",
|
id: "init-root-frame",
|
||||||
@ -24,6 +25,7 @@ const initRootFrameInjectable = getInjectable({
|
|||||||
const lensProtocolRouterRenderer = di.inject(lensProtocolRouterRendererInjectable);
|
const lensProtocolRouterRenderer = di.inject(lensProtocolRouterRendererInjectable);
|
||||||
const catalogEntityRegistry = di.inject(catalogEntityRegistryInjectable);
|
const catalogEntityRegistry = di.inject(catalogEntityRegistryInjectable);
|
||||||
const logger = di.inject(loggerInjectable);
|
const logger = di.inject(loggerInjectable);
|
||||||
|
const closeRendererLogFile = di.inject(closeRendererLogFileInjectable);
|
||||||
|
|
||||||
return async (unmountRoot: () => void) => {
|
return async (unmountRoot: () => void) => {
|
||||||
catalogEntityRegistry.init();
|
catalogEntityRegistry.init();
|
||||||
@ -59,7 +61,7 @@ const initRootFrameInjectable = getInjectable({
|
|||||||
|
|
||||||
window.addEventListener("beforeunload", () => {
|
window.addEventListener("beforeunload", () => {
|
||||||
logger.info("[ROOT-FRAME]: Unload app");
|
logger.info("[ROOT-FRAME]: Unload app");
|
||||||
|
closeRendererLogFile();
|
||||||
unmountRoot();
|
unmountRoot();
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
@ -0,0 +1,22 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import winstonLoggerInjectable from "../../common/winston-logger.injectable";
|
||||||
|
import rendererFileLoggerTransportInjectable from "./file-transport.injectable";
|
||||||
|
|
||||||
|
const closeRendererLogFileInjectable = getInjectable({
|
||||||
|
id: "close-renderer-log-file",
|
||||||
|
instantiate: (di) => {
|
||||||
|
const winstonLogger = di.inject(winstonLoggerInjectable);
|
||||||
|
const fileLoggingTransport = di.inject(rendererFileLoggerTransportInjectable);
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
fileLoggingTransport.close?.();
|
||||||
|
winstonLogger.remove(fileLoggingTransport);
|
||||||
|
};
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
export default closeRendererLogFileInjectable;
|
||||||
@ -0,0 +1,44 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { transports } from "winston";
|
||||||
|
import directoryForLogsInjectable from "../../common/app-paths/directory-for-logs.injectable";
|
||||||
|
import { loggerTransportInjectionToken } from "../../common/logger/transports";
|
||||||
|
import windowLocationInjectable from "../../common/k8s-api/window-location.injectable";
|
||||||
|
import currentlyInClusterFrameInjectable from "../routes/currently-in-cluster-frame.injectable";
|
||||||
|
import { getClusterIdFromHost } from "../utils";
|
||||||
|
|
||||||
|
const rendererFileLoggerTransportInjectable = getInjectable({
|
||||||
|
id: "renderer-file-logger-transport",
|
||||||
|
instantiate: (di) => {
|
||||||
|
let frameId: string;
|
||||||
|
|
||||||
|
const currentlyInClusterFrame = di.inject(
|
||||||
|
currentlyInClusterFrameInjectable,
|
||||||
|
);
|
||||||
|
|
||||||
|
if (currentlyInClusterFrame) {
|
||||||
|
const { host } = di.inject(windowLocationInjectable);
|
||||||
|
const clusterId = getClusterIdFromHost(host);
|
||||||
|
|
||||||
|
frameId = clusterId ? `cluster-${clusterId}` : "cluster";
|
||||||
|
} else {
|
||||||
|
frameId = "main";
|
||||||
|
}
|
||||||
|
|
||||||
|
return new transports.File({
|
||||||
|
handleExceptions: false,
|
||||||
|
level: "info",
|
||||||
|
filename: `lens-renderer-${frameId}.log`,
|
||||||
|
dirname: di.inject(directoryForLogsInjectable),
|
||||||
|
maxsize: 1024 * 1024,
|
||||||
|
maxFiles: 2,
|
||||||
|
tailable: true,
|
||||||
|
});
|
||||||
|
},
|
||||||
|
injectionToken: loggerTransportInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default rendererFileLoggerTransportInjectable;
|
||||||
Loading…
Reference in New Issue
Block a user