Restructure to monorepo (#6907)

* wip: restructure to monorepo

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* refactor create-release-pr to a package

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* build fixes

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* github workflow fixes

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* fix typo

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* add webpack-env types to core

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* fix github workflows

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* refactor/fix integration tests

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* lint fix

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* yarn run dev

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* eslint settings for vscode

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* move templates to right package

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* open-lens build fixes

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* integration test fix

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* fix nx task dependencies

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* use bash shell for unit tests in test workflow

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* fix test:unit for windows

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* fix win-ca webpack error in open-lens

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* fix win-ca webpack error in open-lens

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* fix build:app on windows

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* remove ELECTRON_BUILDER_EXTRA_ARGS

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* sync src/ from master

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

* remove Makefile from core

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>

Signed-off-by: Jari Kolehmainen <jari.kolehmainen@gmail.com>
This commit is contained in:
Jari Kolehmainen authored and GitHub committed 2023-01-24 10:46:26 -08:00
1 parent 0066ca4ea2
commit 2657df2293
3321 files changed
+28699 -11447

No files matched your search

@@ -0,0 +1,23 @@
/**
* 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 observableHistoryInjectable from "./observable-history.injectable";
import type { PageParamDependencies, PageParamInit } from "./page-param";
import { PageParam } from "./page-param";
export type CreatePageParam = <Value = string>(init: PageParamInit<Value>) => PageParam<Value>;
const createPageParamInjectable = getInjectable({
id: "create-page-param",
instantiate: (di): CreatePageParam => {
const deps: PageParamDependencies = {
history: di.inject(observableHistoryInjectable),
};
return (init) => new PageParam(deps, init);
},
});
export default createPageParamInjectable;
@@ -0,0 +1,9 @@
/**
* Copyright (c) OpenLens Authors. All rights reserved.
* Licensed under MIT License. See LICENSE in root directory for more information.
*/
import { getGlobalOverride } from "../../common/test-utils/get-global-override";
import focusWindowInjectable from "./focus-window.injectable";
export default getGlobalOverride(focusWindowInjectable, () => () => {});
@@ -0,0 +1,13 @@
/**
* 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";
const focusWindowInjectable = getInjectable({
id: "focus-window",
instantiate: () => () => window.focus(),
causesSideEffects: true,
});
export default focusWindowInjectable;
@@ -0,0 +1,10 @@
/**
* Copyright (c) OpenLens Authors. All rights reserved.
* Licensed under MIT License. See LICENSE in root directory for more information.
*/
import { createMemoryHistory } from "history";
import { getGlobalOverride } from "../../common/test-utils/get-global-override";
import historyInjectable from "./history.injectable";
export default getGlobalOverride(historyInjectable, () => createMemoryHistory());
@@ -0,0 +1,14 @@
/**
* 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 { createBrowserHistory } from "history";
import type { History } from "history";
const historyInjectable = getInjectable({
id: "history",
instantiate: (): History => createBrowserHistory(),
});
export default historyInjectable;
@@ -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 type { RouteProps } from "react-router";
import matchRouteInjectable from "./match-route.injectable";
export type IsRouteActive = (route: string | string[] | RouteProps) => boolean;
const isActiveRouteInjectable = getInjectable({
id: "is-active-route",
instantiate: (di): IsRouteActive => {
const matchRoute = di.inject(matchRouteInjectable);
return (route) => Boolean(matchRoute(route));
},
});
export default isActiveRouteInjectable;
@@ -0,0 +1,21 @@
/**
* 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 type { match, RouteProps } from "react-router";
import { matchPath } from "react-router";
import observableHistoryInjectable from "./observable-history.injectable";
export type MatchRoute = <Params extends { [K in keyof Params]?: string }>(route: string | string[] | RouteProps) => match<Params> | null;
const matchRouteInjectable = getInjectable({
id: "match-route",
instantiate: (di): MatchRoute => {
const observableHistory = di.inject(observableHistoryInjectable);
return (route) => matchPath(observableHistory.location.pathname, route);
},
});
export default matchRouteInjectable;
@@ -0,0 +1,18 @@
/**
* 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 clusterViewRouteParametersInjectable from "../components/cluster-manager/cluster-view-route-parameters.injectable";
const matchedClusterIdInjectable = getInjectable({
id: "matched-cluster-id",
instantiate: (di) => {
const routeParameters = di.inject(clusterViewRouteParametersInjectable);
return routeParameters.clusterId;
},
});
export default matchedClusterIdInjectable;
@@ -0,0 +1,32 @@
/**
* 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 type { LocationDescriptor } from "history";
import { action } from "mobx";
import observableHistoryInjectable from "./observable-history.injectable";
import { createPath } from "history";
export type Navigate = (location: LocationDescriptor) => void;
const navigateInjectable = getInjectable({
id: "navigate",
instantiate: (di): Navigate => {
const observableHistory = di.inject(observableHistoryInjectable);
return action((location) => {
const currentLocation = createPath(observableHistory.location);
observableHistory.push(location);
const newLocation = createPath(observableHistory.location);
if (currentLocation === newLocation) {
observableHistory.goBack(); // prevent sequences of same url in history
}
});
},
});
export default navigateInjectable;
@@ -0,0 +1,40 @@
/**
* Copyright (c) OpenLens Authors. All rights reserved.
* Licensed under MIT License. See LICENSE in root directory for more information.
*/
import type { InjectionToken } from "@ogre-tools/injectable";
import { getInjectable } from "@ogre-tools/injectable";
import currentlyInClusterFrameInjectable from "../routes/currently-in-cluster-frame.injectable";
import { appNavigationChannel } from "../../common/front-end-routing/app-navigation-channel";
import { clusterFrameNavigationChannel } from "../../common/front-end-routing/cluster-frame-navigation-channel";
import focusWindowInjectable from "./focus-window.injectable";
import { navigateToUrlInjectionToken } from "../../common/front-end-routing/navigate-to-url-injection-token";
import type { MessageChannel, MessageChannelListener } from "../../common/utils/channel/message-channel-listener-injection-token";
import { messageChannelListenerInjectionToken } from "../../common/utils/channel/message-channel-listener-injection-token";
const navigationChannelListenerInjectable = getInjectable({
id: "navigation-channel-listener",
instantiate: (di) => {
const currentlyInClusterFrame = di.inject(currentlyInClusterFrameInjectable);
const focusWindow = di.inject(focusWindowInjectable);
const navigateToUrl = di.inject(navigateToUrlInjectionToken);
return {
channel: currentlyInClusterFrame
? clusterFrameNavigationChannel
: appNavigationChannel,
handler: (url: string) => {
navigateToUrl(url);
if (!currentlyInClusterFrame) {
focusWindow(); // make sure that the main frame is focused
}
},
};
},
injectionToken: messageChannelListenerInjectionToken as InjectionToken<MessageChannelListener<MessageChannel<string>>, void>,
});
export default navigationChannelListenerInjectable;
@@ -0,0 +1,23 @@
/**
* 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 { createObservableHistory } from "mobx-observable-history";
import { searchParamsOptions } from "./search-params";
import historyInjectable from "./history.injectable";
const observableHistoryInjectable = getInjectable({
id: "observable-history",
instantiate: (di) => {
const history = di.inject(historyInjectable);
const navigation = createObservableHistory(history, {
searchParams: searchParamsOptions,
});
return navigation;
},
});
export default observableHistoryInjectable;
@@ -0,0 +1,119 @@
/**
* Copyright (c) OpenLens Authors. All rights reserved.
* Licensed under MIT License. See LICENSE in root directory for more information.
*/
// Manage observable param from document's location.search
import { action, makeObservable } from "mobx";
import type { ObservableHistory } from "mobx-observable-history";
export interface PageParamInit<Value = any> {
name: string;
defaultValue?: Value; // multi-values param must be defined with array-value, e.g. []
parse?(value: string | string[]): Value; // from URL
stringify?(value: Value): string | string[]; // to URL
}
export interface PageParamDependencies {
readonly history: ObservableHistory<unknown>;
}
// TODO: write tests
export class PageParam<Value = any> {
readonly name: string;
readonly isMulti: boolean;
constructor(protected readonly dependencies: PageParamDependencies, private init: PageParamInit<Value>) {
makeObservable(this);
const { name, defaultValue } = init;
this.name = name;
this.isMulti = Array.isArray(defaultValue); // multi-values param
}
// should be a getter since `init.defaultValue` could be a getter too
get defaultValue(): Value | undefined {
return this.init.defaultValue;
}
parse(values: string | string[]): Value {
const { parse } = this.init;
if (parse) {
return parse(values);
}
// return as-is ("string"-value based params)
return values as unknown as Value;
}
stringify(value: Value = this.get()): string[] {
const { stringify } = this.init;
if (stringify) {
return [stringify(value)].flat();
}
return [value].flat().map(String);
}
get(): Value {
// TODO: cleanup
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
return this.parse(this.getRaw()) ?? this.defaultValue!;
}
@action
set(value: Value, { mergeGlobals = true, replaceHistory = false } = {}): void {
const search = this.toString({ mergeGlobals, value });
this.dependencies.history.merge({ search }, replaceHistory);
}
/**
* Set stringified raw value(s) and update `document.location.search`
* @param {string | string[]} value
*/
@action
setRaw(value: string | string[]): void {
const values: string[] = [value].flat();
if (this.isMulti) {
this.clear();
values.forEach(value => {
this.dependencies.history.searchParams.append(this.name, value);
});
} else {
this.dependencies.history.searchParams.set(this.name, values[0]);
}
}
/**
* Get stringified raw value(s) from `document.location.search`
*/
getRaw(): string | string[] {
const values: string[] = this.dependencies.history.searchParams.getAll(this.name);
return this.isMulti ? values : values[0];
}
@action
clear() {
this.dependencies.history.searchParams.delete(this.name);
}
toString({ mergeGlobals = true, value = this.get() } = {}): string {
let searchParams = new URLSearchParams();
if (mergeGlobals) {
searchParams = new URLSearchParams(this.dependencies.history.searchParams);
searchParams.delete(this.name);
}
this.stringify(value).forEach(value => {
searchParams.append(this.name, value);
});
return searchParams.toString();
}
}
@@ -0,0 +1,12 @@
/**
* Copyright (c) OpenLens Authors. All rights reserved.
* Licensed under MIT License. See LICENSE in root directory for more information.
*/
import type { ObservableSearchParamsOptions } from "mobx-observable-history";
export const searchParamsOptions: ObservableSearchParamsOptions = {
skipEmpty: true, // skip empty params, e.g. "?x=&y2=" will be "?y=2"
joinArrays: false, // join multiple params with same name, e.g. "?x=1&x=2" => "?x=1,2"
joinArraysWith: ",", // param values splitter, applicable only with {joinArrays:true}
};
@@ -0,0 +1,33 @@
/**
* 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 loggerInjectable from "../../common/logger.injectable";
import { beforeFrameStartsSecondInjectionToken } from "../before-frame-starts/tokens";
import observableHistoryInjectable from "./observable-history.injectable";
const setupLoggingForNavigationInjectable = getInjectable({
id: "setup-logging-for-navigation",
instantiate: (di) => ({
id: "setup-logging-for-navigation",
run: () => {
const logger = di.inject(loggerInjectable);
const observableHistory = di.inject(observableHistoryInjectable);
observableHistory.listen((location, action) => {
const isClusterView = !process.isMainFrame;
const domain = global.location.href;
logger.debug(`[NAVIGATION]: ${action}-ing. Current is now:`, {
isClusterView,
domain,
location,
});
});
},
}),
injectionToken: beforeFrameStartsSecondInjectionToken,
});
export default setupLoggingForNavigationInjectable;