mirror of
https://github.com/lensapp/lens.git
synced 2025-05-20 05:10:56 +00:00
Signed-off-by: Roman <ixrock@gmail.com>
This commit is contained in:
parent
531e445981
commit
8ba78d9a10
@ -1,23 +1,39 @@
|
|||||||
// TODO: add more common re-usable UI components + refactor interfaces (Props -> ComponentProps)
|
// Common UI components
|
||||||
|
|
||||||
export * from "../../renderer/components/icon"
|
// layouts
|
||||||
export * from "../../renderer/components/checkbox"
|
export * from "../../renderer/components/layout/page-layout"
|
||||||
export * from "../../renderer/components/tooltip"
|
export * from "../../renderer/components/layout/wizard-layout"
|
||||||
|
export * from "../../renderer/components/layout/tab-layout"
|
||||||
|
|
||||||
|
// form-controls
|
||||||
export * from "../../renderer/components/button"
|
export * from "../../renderer/components/button"
|
||||||
|
export * from "../../renderer/components/checkbox"
|
||||||
|
export * from "../../renderer/components/radio"
|
||||||
|
export * from "../../renderer/components/select"
|
||||||
|
export * from "../../renderer/components/slider"
|
||||||
|
export * from "../../renderer/components/input/input"
|
||||||
|
|
||||||
|
// other components
|
||||||
|
export * from "../../renderer/components/icon"
|
||||||
|
export * from "../../renderer/components/tooltip"
|
||||||
export * from "../../renderer/components/tabs"
|
export * from "../../renderer/components/tabs"
|
||||||
export * from "../../renderer/components/badge"
|
export * from "../../renderer/components/badge"
|
||||||
export * from "../../renderer/components/layout/page-layout"
|
|
||||||
export * from "../../renderer/components/drawer"
|
export * from "../../renderer/components/drawer"
|
||||||
|
export * from "../../renderer/components/dialog"
|
||||||
|
export * from "../../renderer/components/confirm-dialog";
|
||||||
|
export * from "../../renderer/components/line-progress"
|
||||||
|
export * from "../../renderer/components/menu"
|
||||||
|
export * from "../../renderer/components/notifications"
|
||||||
|
export * from "../../renderer/components/spinner"
|
||||||
|
export * from "../../renderer/components/stepper"
|
||||||
|
|
||||||
// kube helpers
|
// kube helpers
|
||||||
export { KubeObjectDetailsProps, KubeObjectMenuProps } from "../../renderer/components/kube-object"
|
export * from "../../renderer/components/kube-object"
|
||||||
export { KubeObjectMeta } from "../../renderer/components/kube-object/kube-object-meta"
|
export * from "../../renderer/components/kube-object/kube-object-meta"
|
||||||
export { KubeObjectListLayout, KubeObjectListLayoutProps } from "../../renderer/components/kube-object/kube-object-list-layout";
|
export * from "../../renderer/components/kube-object/kube-object-list-layout";
|
||||||
export { KubeEventDetails } from "../../renderer/components/+events/kube-event-details"
|
export * from "../../renderer/components/+events/kube-event-details"
|
||||||
|
|
||||||
// specific exports
|
// specific exports
|
||||||
export { ConfirmDialog } from "../../renderer/components/confirm-dialog";
|
export * from "../../renderer/components/status-brick";
|
||||||
export { MenuItem, SubMenu } from "../../renderer/components/menu";
|
|
||||||
export { StatusBrick } from "../../renderer/components/status-brick";
|
|
||||||
export { terminalStore, createTerminalTab } from "../../renderer/components/dock/terminal.store";
|
export { terminalStore, createTerminalTab } from "../../renderer/components/dock/terminal.store";
|
||||||
export { createPodLogsTab } from "../../renderer/components/dock/pod-logs.store";
|
export { createPodLogsTab } from "../../renderer/components/dock/pod-logs.store";
|
||||||
|
|||||||
@ -6,15 +6,14 @@ import { Trans } from "@lingui/macro";
|
|||||||
import { KubeObject } from "../../api/kube-object";
|
import { KubeObject } from "../../api/kube-object";
|
||||||
import { DrawerItem, DrawerTitle } from "../drawer";
|
import { DrawerItem, DrawerTitle } from "../drawer";
|
||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
import { Icon } from "../icon";
|
|
||||||
import { eventStore } from "./event.store";
|
import { eventStore } from "./event.store";
|
||||||
|
|
||||||
interface Props {
|
export interface KubeEventDetailsProps {
|
||||||
object: KubeObject;
|
object: KubeObject;
|
||||||
}
|
}
|
||||||
|
|
||||||
@observer
|
@observer
|
||||||
export class KubeEventDetails extends React.Component<Props> {
|
export class KubeEventDetails extends React.Component<KubeEventDetailsProps> {
|
||||||
async componentDidMount() {
|
async componentDidMount() {
|
||||||
eventStore.loadAll();
|
eventStore.loadAll();
|
||||||
}
|
}
|
||||||
|
|||||||
@ -12,7 +12,7 @@ import { Icon } from "../icon";
|
|||||||
import { Input } from "../input";
|
import { Input } from "../input";
|
||||||
import { cssNames, prevDefault } from "../../utils";
|
import { cssNames, prevDefault } from "../../utils";
|
||||||
import { Button } from "../button";
|
import { Button } from "../button";
|
||||||
import { isRequired, Validator } from "../input/input_validators";
|
import { isRequired, InputValidator } from "../input/input_validators";
|
||||||
|
|
||||||
@observer
|
@observer
|
||||||
export class Workspaces extends React.Component {
|
export class Workspaces extends React.Component {
|
||||||
@ -122,7 +122,7 @@ export class Workspaces extends React.Component {
|
|||||||
editing: isEditing,
|
editing: isEditing,
|
||||||
default: isDefault,
|
default: isDefault,
|
||||||
});
|
});
|
||||||
const existenceValidator: Validator = {
|
const existenceValidator: InputValidator = {
|
||||||
message: () => `Workspace '${name}' already exists`,
|
message: () => `Workspace '${name}' already exists`,
|
||||||
validate: value => !workspaceStore.getByName(value.trim())
|
validate: value => !workspaceStore.getByName(value.trim())
|
||||||
}
|
}
|
||||||
|
|||||||
@ -4,13 +4,13 @@ import React from "react";
|
|||||||
import { cssNames } from "../../utils/cssNames";
|
import { cssNames } from "../../utils/cssNames";
|
||||||
import { TooltipDecoratorProps, withTooltip } from "../tooltip";
|
import { TooltipDecoratorProps, withTooltip } from "../tooltip";
|
||||||
|
|
||||||
interface Props extends React.HTMLAttributes<any>, TooltipDecoratorProps {
|
export interface BadgeProps extends React.HTMLAttributes<any>, TooltipDecoratorProps {
|
||||||
small?: boolean;
|
small?: boolean;
|
||||||
label?: React.ReactNode;
|
label?: React.ReactNode;
|
||||||
}
|
}
|
||||||
|
|
||||||
@withTooltip
|
@withTooltip
|
||||||
export class Badge extends React.Component<Props> {
|
export class Badge extends React.Component<BadgeProps> {
|
||||||
render() {
|
render() {
|
||||||
const { className, label, small, children, ...elemProps } = this.props;
|
const { className, label, small, children, ...elemProps } = this.props;
|
||||||
return <>
|
return <>
|
||||||
|
|||||||
@ -2,7 +2,7 @@ import './checkbox.scss'
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import { autobind, cssNames } from "../../utils";
|
import { autobind, cssNames } from "../../utils";
|
||||||
|
|
||||||
interface Props<T = boolean> {
|
export interface CheckboxProps<T = boolean> {
|
||||||
theme?: "dark" | "light";
|
theme?: "dark" | "light";
|
||||||
className?: string;
|
className?: string;
|
||||||
label?: React.ReactNode;
|
label?: React.ReactNode;
|
||||||
@ -12,7 +12,7 @@ interface Props<T = boolean> {
|
|||||||
onChange?(value: T, evt: React.ChangeEvent<HTMLInputElement>): void;
|
onChange?(value: T, evt: React.ChangeEvent<HTMLInputElement>): void;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Checkbox extends React.PureComponent<Props> {
|
export class Checkbox extends React.PureComponent<CheckboxProps> {
|
||||||
private input: HTMLInputElement;
|
private input: HTMLInputElement;
|
||||||
|
|
||||||
@autobind()
|
@autobind()
|
||||||
|
|||||||
@ -9,7 +9,10 @@ import { Button, ButtonProps } from "../button";
|
|||||||
import { Dialog, DialogProps } from "../dialog";
|
import { Dialog, DialogProps } from "../dialog";
|
||||||
import { Icon } from "../icon";
|
import { Icon } from "../icon";
|
||||||
|
|
||||||
export interface IConfirmDialogParams {
|
export interface ConfirmDialogProps extends Partial<DialogProps> {
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface ConfirmDialogParams {
|
||||||
ok?: () => void;
|
ok?: () => void;
|
||||||
labelOk?: ReactNode;
|
labelOk?: ReactNode;
|
||||||
labelCancel?: ReactNode;
|
labelCancel?: ReactNode;
|
||||||
@ -19,17 +22,14 @@ export interface IConfirmDialogParams {
|
|||||||
cancelButtonProps?: Partial<ButtonProps>
|
cancelButtonProps?: Partial<ButtonProps>
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Props extends Partial<DialogProps> {
|
|
||||||
}
|
|
||||||
|
|
||||||
@observer
|
@observer
|
||||||
export class ConfirmDialog extends React.Component<Props> {
|
export class ConfirmDialog extends React.Component<ConfirmDialogProps> {
|
||||||
@observable static isOpen = false;
|
@observable static isOpen = false;
|
||||||
@observable.ref static params: IConfirmDialogParams;
|
@observable.ref static params: ConfirmDialogParams;
|
||||||
|
|
||||||
@observable isSaving = false;
|
@observable isSaving = false;
|
||||||
|
|
||||||
static open(params: IConfirmDialogParams) {
|
static open(params: ConfirmDialogParams) {
|
||||||
ConfirmDialog.isOpen = true;
|
ConfirmDialog.isOpen = true;
|
||||||
ConfirmDialog.params = params;
|
ConfirmDialog.params = params;
|
||||||
}
|
}
|
||||||
@ -38,14 +38,14 @@ export class ConfirmDialog extends React.Component<Props> {
|
|||||||
ConfirmDialog.isOpen = false;
|
ConfirmDialog.isOpen = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public defaultParams: IConfirmDialogParams = {
|
public defaultParams: ConfirmDialogParams = {
|
||||||
ok: noop,
|
ok: noop,
|
||||||
labelOk: <Trans>Ok</Trans>,
|
labelOk: <Trans>Ok</Trans>,
|
||||||
labelCancel: <Trans>Cancel</Trans>,
|
labelCancel: <Trans>Cancel</Trans>,
|
||||||
icon: <Icon big material="warning"/>,
|
icon: <Icon big material="warning"/>,
|
||||||
};
|
};
|
||||||
|
|
||||||
get params(): IConfirmDialogParams {
|
get params(): ConfirmDialogParams {
|
||||||
return Object.assign({}, this.defaultParams, ConfirmDialog.params);
|
return Object.assign({}, this.defaultParams, ConfirmDialog.params);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -2,11 +2,11 @@ import React from "react";
|
|||||||
import { DrawerItem, DrawerItemProps } from "./drawer-item";
|
import { DrawerItem, DrawerItemProps } from "./drawer-item";
|
||||||
import { Badge } from "../badge";
|
import { Badge } from "../badge";
|
||||||
|
|
||||||
interface Props extends DrawerItemProps {
|
export interface DrawerItemLabelsProps extends DrawerItemProps {
|
||||||
labels: string[];
|
labels: string[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export function DrawerItemLabels(props: Props) {
|
export function DrawerItemLabels(props: DrawerItemLabelsProps) {
|
||||||
const { labels, ...itemProps } = props;
|
const { labels, ...itemProps } = props;
|
||||||
if (!labels || !labels.length) {
|
if (!labels || !labels.length) {
|
||||||
return null;
|
return null;
|
||||||
|
|||||||
@ -5,14 +5,14 @@ import { Icon } from "../icon";
|
|||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
import { _i18n } from "../../i18n";
|
import { _i18n } from "../../i18n";
|
||||||
|
|
||||||
interface Props {
|
export interface DrawerParamTogglerProps {
|
||||||
label: string | number;
|
label: string | number;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface State {
|
interface State {
|
||||||
open?: boolean;
|
open?: boolean;
|
||||||
}
|
}
|
||||||
export class DrawerParamToggler extends React.Component<Props, State> {
|
export class DrawerParamToggler extends React.Component<DrawerParamTogglerProps, State> {
|
||||||
public state: State = {}
|
public state: State = {}
|
||||||
|
|
||||||
toggle = () => {
|
toggle = () => {
|
||||||
|
|||||||
@ -2,12 +2,12 @@ import "./drawer-title.scss";
|
|||||||
import React from "react";
|
import React from "react";
|
||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
|
|
||||||
interface Props {
|
export interface DrawerTitleProps {
|
||||||
className?: string;
|
className?: string;
|
||||||
title?: React.ReactNode;
|
title?: React.ReactNode;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class DrawerTitle extends React.Component<Props> {
|
export class DrawerTitle extends React.Component<DrawerTitleProps> {
|
||||||
render() {
|
render() {
|
||||||
const { title, children, className } = this.props
|
const { title, children, className } = this.props
|
||||||
return (
|
return (
|
||||||
|
|||||||
@ -3,13 +3,16 @@ import "./input.scss";
|
|||||||
import React, { DOMAttributes, InputHTMLAttributes, TextareaHTMLAttributes } from "react";
|
import React, { DOMAttributes, InputHTMLAttributes, TextareaHTMLAttributes } from "react";
|
||||||
import { autobind, cssNames, debouncePromise } from "../../utils";
|
import { autobind, cssNames, debouncePromise } from "../../utils";
|
||||||
import { Icon } from "../icon";
|
import { Icon } from "../icon";
|
||||||
import { conditionalValidators, Validator } from "./input_validators";
|
import * as Validators from "./input_validators";
|
||||||
|
import { InputValidator } from "./input_validators";
|
||||||
import isString from "lodash/isString"
|
import isString from "lodash/isString"
|
||||||
import isFunction from "lodash/isFunction"
|
import isFunction from "lodash/isFunction"
|
||||||
import isBoolean from "lodash/isBoolean"
|
import isBoolean from "lodash/isBoolean"
|
||||||
import uniqueId from "lodash/uniqueId"
|
import uniqueId from "lodash/uniqueId"
|
||||||
|
|
||||||
type Omit<T, K extends keyof T> = Pick<T, Exclude<keyof T, K>>
|
const { conditionalValidators, ...InputValidators } = Validators;
|
||||||
|
export { InputValidators, InputValidator }
|
||||||
|
|
||||||
type InputElement = HTMLInputElement | HTMLTextAreaElement;
|
type InputElement = HTMLInputElement | HTMLTextAreaElement;
|
||||||
type InputElementProps = InputHTMLAttributes<InputElement> & TextareaHTMLAttributes<InputElement> & DOMAttributes<InputElement>;
|
type InputElementProps = InputHTMLAttributes<InputElement> & TextareaHTMLAttributes<InputElement> & DOMAttributes<InputElement>;
|
||||||
|
|
||||||
@ -24,7 +27,7 @@ export type InputProps<T = string> = Omit<InputElementProps, "onChange" | "onSub
|
|||||||
showValidationLine?: boolean; // show animated validation line for async validators
|
showValidationLine?: boolean; // show animated validation line for async validators
|
||||||
iconLeft?: string | React.ReactNode; // material-icon name in case of string-type
|
iconLeft?: string | React.ReactNode; // material-icon name in case of string-type
|
||||||
iconRight?: string | React.ReactNode;
|
iconRight?: string | React.ReactNode;
|
||||||
validators?: Validator | Validator[];
|
validators?: InputValidator | InputValidator[];
|
||||||
onChange?(value: T, evt: React.ChangeEvent<InputElement>): void;
|
onChange?(value: T, evt: React.ChangeEvent<InputElement>): void;
|
||||||
onSubmit?(value: T): void;
|
onSubmit?(value: T): void;
|
||||||
}
|
}
|
||||||
@ -49,7 +52,7 @@ export class Input extends React.Component<InputProps, State> {
|
|||||||
static defaultProps = defaultProps as object;
|
static defaultProps = defaultProps as object;
|
||||||
|
|
||||||
public input: InputElement;
|
public input: InputElement;
|
||||||
public validators: Validator[] = [];
|
public validators: InputValidator[] = [];
|
||||||
|
|
||||||
public state: State = {
|
public state: State = {
|
||||||
dirty: !!this.props.dirty,
|
dirty: !!this.props.dirty,
|
||||||
@ -149,7 +152,7 @@ export class Input extends React.Component<InputProps, State> {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
private getValidatorError(value: string, { message }: Validator) {
|
private getValidatorError(value: string, { message }: InputValidator) {
|
||||||
if (isFunction(message)) return message(value, this.props)
|
if (isFunction(message)) return message(value, this.props)
|
||||||
return message || "";
|
return message || "";
|
||||||
}
|
}
|
||||||
@ -288,9 +291,9 @@ export class Input extends React.Component<InputProps, State> {
|
|||||||
return (
|
return (
|
||||||
<div className={className}>
|
<div className={className}>
|
||||||
<label className="input-area flex gaps align-center">
|
<label className="input-area flex gaps align-center">
|
||||||
{isString(iconLeft) ? <Icon material={iconLeft} /> : iconLeft}
|
{isString(iconLeft) ? <Icon material={iconLeft}/> : iconLeft}
|
||||||
{multiLine ? <textarea {...inputProps as any} /> : <input {...inputProps as any} />}
|
{multiLine ? <textarea {...inputProps as any} /> : <input {...inputProps as any} />}
|
||||||
{isString(iconRight) ? <Icon material={iconRight} /> : iconRight}
|
{isString(iconRight) ? <Icon material={iconRight}/> : iconRight}
|
||||||
</label>
|
</label>
|
||||||
<div className="input-info flex gaps">
|
<div className="input-info flex gaps">
|
||||||
{!valid && dirty && (
|
{!valid && dirty && (
|
||||||
|
|||||||
@ -4,26 +4,26 @@ import { t } from "@lingui/macro";
|
|||||||
import { _i18n } from '../../i18n';
|
import { _i18n } from '../../i18n';
|
||||||
import fse from "fs-extra";
|
import fse from "fs-extra";
|
||||||
|
|
||||||
export interface Validator {
|
export interface InputValidator {
|
||||||
debounce?: number; // debounce for async validators in ms
|
debounce?: number; // debounce for async validators in ms
|
||||||
condition?(props: InputProps): boolean; // auto-bind condition depending on input props
|
condition?(props: InputProps): boolean; // auto-bind condition depending on input props
|
||||||
message?: ReactNode | ((value: string, props?: InputProps) => ReactNode | string);
|
message?: ReactNode | ((value: string, props?: InputProps) => ReactNode | string);
|
||||||
validate(value: string, props?: InputProps): boolean | Promise<any>; // promise can throw error message
|
validate(value: string, props?: InputProps): boolean | Promise<any>; // promise can throw error message
|
||||||
}
|
}
|
||||||
|
|
||||||
export const isRequired: Validator = {
|
export const isRequired: InputValidator = {
|
||||||
condition: ({ required }) => required,
|
condition: ({ required }) => required,
|
||||||
message: () => _i18n._(t`This field is required`),
|
message: () => _i18n._(t`This field is required`),
|
||||||
validate: value => !!value.trim(),
|
validate: value => !!value.trim(),
|
||||||
};
|
};
|
||||||
|
|
||||||
export const isEmail: Validator = {
|
export const isEmail: InputValidator = {
|
||||||
condition: ({ type }) => type === "email",
|
condition: ({ type }) => type === "email",
|
||||||
message: () => _i18n._(t`Wrong email format`),
|
message: () => _i18n._(t`Wrong email format`),
|
||||||
validate: value => !!value.match(/^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/),
|
validate: value => !!value.match(/^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/),
|
||||||
};
|
};
|
||||||
|
|
||||||
export const isNumber: Validator = {
|
export const isNumber: InputValidator = {
|
||||||
condition: ({ type }) => type === "number",
|
condition: ({ type }) => type === "number",
|
||||||
message: () => _i18n._(t`Invalid number`),
|
message: () => _i18n._(t`Invalid number`),
|
||||||
validate: (value, { min, max }) => {
|
validate: (value, { min, max }) => {
|
||||||
@ -36,37 +36,37 @@ export const isNumber: Validator = {
|
|||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
export const isUrl: Validator = {
|
export const isUrl: InputValidator = {
|
||||||
condition: ({ type }) => type === "url",
|
condition: ({ type }) => type === "url",
|
||||||
message: () => _i18n._(t`Wrong url format`),
|
message: () => _i18n._(t`Wrong url format`),
|
||||||
validate: value => !!value.match(/^$|^http(s)?:\/\/\w+(\.\w+)*(:[0-9]+)?\/?(\/[\w\-\._~:/?#[\]@!\$&'\(\)\*\+,;=.]*)*$/),
|
validate: value => !!value.match(/^$|^http(s)?:\/\/\w+(\.\w+)*(:[0-9]+)?\/?(\/[\w\-\._~:/?#[\]@!\$&'\(\)\*\+,;=.]*)*$/),
|
||||||
};
|
};
|
||||||
|
|
||||||
export const isPath: Validator = {
|
export const isPath: InputValidator = {
|
||||||
condition: ({ type }) => type === "text",
|
condition: ({ type }) => type === "text",
|
||||||
message: () => _i18n._(t`This field must be a valid path`),
|
message: () => _i18n._(t`This field must be a valid path`),
|
||||||
validate: value => !value || fse.pathExistsSync(value),
|
validate: value => !value || fse.pathExistsSync(value),
|
||||||
}
|
}
|
||||||
|
|
||||||
export const minLength: Validator = {
|
export const minLength: InputValidator = {
|
||||||
condition: ({ minLength }) => !!minLength,
|
condition: ({ minLength }) => !!minLength,
|
||||||
message: (value, { minLength }) => _i18n._(t`Minimum length is ${minLength}`),
|
message: (value, { minLength }) => _i18n._(t`Minimum length is ${minLength}`),
|
||||||
validate: (value, { minLength }) => value.length >= minLength,
|
validate: (value, { minLength }) => value.length >= minLength,
|
||||||
};
|
};
|
||||||
|
|
||||||
export const maxLength: Validator = {
|
export const maxLength: InputValidator = {
|
||||||
condition: ({ maxLength }) => !!maxLength,
|
condition: ({ maxLength }) => !!maxLength,
|
||||||
message: (value, { maxLength }) => _i18n._(t`Maximum length is ${maxLength}`),
|
message: (value, { maxLength }) => _i18n._(t`Maximum length is ${maxLength}`),
|
||||||
validate: (value, { maxLength }) => value.length <= maxLength,
|
validate: (value, { maxLength }) => value.length <= maxLength,
|
||||||
};
|
};
|
||||||
|
|
||||||
const systemNameMatcher = /^[a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*$/;
|
const systemNameMatcher = /^[a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*$/;
|
||||||
export const systemName: Validator = {
|
export const systemName: InputValidator = {
|
||||||
message: () => _i18n._(t`A System Name must be lowercase DNS labels separated by dots. DNS labels are alphanumerics and dashes enclosed by alphanumerics.`),
|
message: () => _i18n._(t`A System Name must be lowercase DNS labels separated by dots. DNS labels are alphanumerics and dashes enclosed by alphanumerics.`),
|
||||||
validate: value => !!value.match(systemNameMatcher),
|
validate: value => !!value.match(systemNameMatcher),
|
||||||
};
|
};
|
||||||
|
|
||||||
export const accountId: Validator = {
|
export const accountId: InputValidator = {
|
||||||
message: () => _i18n._(t`Invalid account ID`),
|
message: () => _i18n._(t`Invalid account ID`),
|
||||||
validate: value => (isEmail.validate(value) || systemName.validate(value))
|
validate: value => (isEmail.validate(value) || systemName.validate(value))
|
||||||
};
|
};
|
||||||
|
|||||||
@ -5,7 +5,7 @@ import React, { ReactNode } from "react";
|
|||||||
import { computed, observable, reaction, toJS, when } from "mobx";
|
import { computed, observable, reaction, toJS, when } from "mobx";
|
||||||
import { disposeOnUnmount, observer } from "mobx-react";
|
import { disposeOnUnmount, observer } from "mobx-react";
|
||||||
import { Plural, Trans } from "@lingui/macro";
|
import { Plural, Trans } from "@lingui/macro";
|
||||||
import { ConfirmDialog, IConfirmDialogParams } from "../confirm-dialog";
|
import { ConfirmDialog, ConfirmDialogParams } from "../confirm-dialog";
|
||||||
import { SortingCallback, Table, TableCell, TableCellProps, TableHead, TableProps, TableRow, TableRowProps } from "../table";
|
import { SortingCallback, Table, TableCell, TableCellProps, TableHead, TableProps, TableRow, TableRowProps } from "../table";
|
||||||
import { autobind, createStorage, cssNames, IClassName, isReactNode, noop, prevDefault, stopPropagation } from "../../utils";
|
import { autobind, createStorage, cssNames, IClassName, isReactNode, noop, prevDefault, stopPropagation } from "../../utils";
|
||||||
import { AddRemoveButtons, AddRemoveButtonsProps } from "../add-remove-buttons";
|
import { AddRemoveButtons, AddRemoveButtonsProps } from "../add-remove-buttons";
|
||||||
@ -67,7 +67,7 @@ export interface ItemListLayoutProps<T extends ItemObject = ItemObject> {
|
|||||||
onDetails?: (item: T) => void;
|
onDetails?: (item: T) => void;
|
||||||
|
|
||||||
// other
|
// other
|
||||||
customizeRemoveDialog?: (selectedItems: T[]) => Partial<IConfirmDialogParams>;
|
customizeRemoveDialog?: (selectedItems: T[]) => Partial<ConfirmDialogParams>;
|
||||||
renderFooter?: (parent: ItemListLayout) => React.ReactNode;
|
renderFooter?: (parent: ItemListLayout) => React.ReactNode;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -2,17 +2,16 @@ import React from "react";
|
|||||||
import { Trans } from "@lingui/macro";
|
import { Trans } from "@lingui/macro";
|
||||||
import { IKubeMetaField, KubeObject } from "../../api/kube-object";
|
import { IKubeMetaField, KubeObject } from "../../api/kube-object";
|
||||||
import { DrawerItem, DrawerItemLabels } from "../drawer";
|
import { DrawerItem, DrawerItemLabels } from "../drawer";
|
||||||
import { WorkloadKubeObject } from "../../api/workload-kube-object";
|
|
||||||
import { getDetailsUrl } from "../../navigation";
|
import { getDetailsUrl } from "../../navigation";
|
||||||
import { lookupApiLink } from "../../api/kube-api";
|
import { lookupApiLink } from "../../api/kube-api";
|
||||||
import { Link } from "react-router-dom";
|
import { Link } from "react-router-dom";
|
||||||
|
|
||||||
export interface Props {
|
export interface KubeObjectMetaProps {
|
||||||
object: KubeObject;
|
object: KubeObject;
|
||||||
hideFields?: IKubeMetaField[];
|
hideFields?: IKubeMetaField[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export class KubeObjectMeta extends React.Component<Props> {
|
export class KubeObjectMeta extends React.Component<KubeObjectMetaProps> {
|
||||||
static defaultHiddenFields: IKubeMetaField[] = [
|
static defaultHiddenFields: IKubeMetaField[] = [
|
||||||
"uid", "resourceVersion", "selfLink"
|
"uid", "resourceVersion", "selfLink"
|
||||||
];
|
];
|
||||||
|
|||||||
@ -12,14 +12,14 @@ export interface TabRoute extends RouteProps {
|
|||||||
url: string;
|
url: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Props {
|
export interface TabLayoutProps {
|
||||||
children: ReactNode;
|
children: ReactNode;
|
||||||
className?: any;
|
className?: any;
|
||||||
tabs?: TabRoute[];
|
tabs?: TabRoute[];
|
||||||
contentClass?: string;
|
contentClass?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const TabLayout = observer(({ className, contentClass, tabs, children }: Props) => {
|
export const TabLayout = observer(({ className, contentClass, tabs, children }: TabLayoutProps) => {
|
||||||
const routePath = navigation.location.pathname;
|
const routePath = navigation.location.pathname;
|
||||||
return (
|
return (
|
||||||
<div className={cssNames("TabLayout", className)}>
|
<div className={cssNames("TabLayout", className)}>
|
||||||
|
|||||||
@ -3,7 +3,7 @@ import React from "react";
|
|||||||
import { observer } from "mobx-react";
|
import { observer } from "mobx-react";
|
||||||
import { cssNames, IClassName } from "../../utils";
|
import { cssNames, IClassName } from "../../utils";
|
||||||
|
|
||||||
interface Props extends React.DOMAttributes<any> {
|
export interface WizardLayoutProps extends React.DOMAttributes<any> {
|
||||||
className?: IClassName;
|
className?: IClassName;
|
||||||
header?: React.ReactNode;
|
header?: React.ReactNode;
|
||||||
headerClass?: IClassName;
|
headerClass?: IClassName;
|
||||||
@ -15,7 +15,7 @@ interface Props extends React.DOMAttributes<any> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@observer
|
@observer
|
||||||
export class WizardLayout extends React.Component<Props> {
|
export class WizardLayout extends React.Component<WizardLayoutProps> {
|
||||||
render() {
|
render() {
|
||||||
const {
|
const {
|
||||||
className, contentClass, infoPanelClass, infoPanel, header, headerClass, centered,
|
className, contentClass, infoPanelClass, infoPanel, header, headerClass, centered,
|
||||||
|
|||||||
@ -3,7 +3,7 @@ import React from "react";
|
|||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
import { TooltipDecoratorProps, withTooltip } from "../tooltip";
|
import { TooltipDecoratorProps, withTooltip } from "../tooltip";
|
||||||
|
|
||||||
interface Props extends React.HTMLProps<any>, TooltipDecoratorProps {
|
export interface LineProgressProps extends React.HTMLProps<any>, TooltipDecoratorProps {
|
||||||
value: number;
|
value: number;
|
||||||
min?: number;
|
min?: number;
|
||||||
max?: number;
|
max?: number;
|
||||||
@ -12,8 +12,8 @@ interface Props extends React.HTMLProps<any>, TooltipDecoratorProps {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@withTooltip
|
@withTooltip
|
||||||
export class LineProgress extends React.PureComponent<Props> {
|
export class LineProgress extends React.PureComponent<LineProgressProps> {
|
||||||
static defaultProps: Props = {
|
static defaultProps: LineProgressProps = {
|
||||||
value: 0,
|
value: 0,
|
||||||
min: 0,
|
min: 0,
|
||||||
max: 100,
|
max: 100,
|
||||||
|
|||||||
@ -10,7 +10,7 @@ import debounce from "lodash/debounce"
|
|||||||
export const MenuContext = React.createContext<MenuContextValue>(null);
|
export const MenuContext = React.createContext<MenuContextValue>(null);
|
||||||
export type MenuContextValue = Menu;
|
export type MenuContextValue = Menu;
|
||||||
|
|
||||||
interface MenuPosition {
|
export interface MenuPosition {
|
||||||
left?: boolean;
|
left?: boolean;
|
||||||
top?: boolean;
|
top?: boolean;
|
||||||
right?: boolean;
|
right?: boolean;
|
||||||
|
|||||||
@ -5,7 +5,7 @@ import uniqueId from "lodash/uniqueId";
|
|||||||
|
|
||||||
// todo: refactor with contexts
|
// todo: refactor with contexts
|
||||||
|
|
||||||
interface RadioGroupProps {
|
export interface RadioGroupProps {
|
||||||
className?: any;
|
className?: any;
|
||||||
value?: any;
|
value?: any;
|
||||||
asButtons?: boolean;
|
asButtons?: boolean;
|
||||||
@ -35,7 +35,7 @@ export class RadioGroup extends React.Component<RadioGroupProps, {}> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
type RadioProps = React.HTMLProps<any> & {
|
export type RadioProps = React.HTMLProps<any> & {
|
||||||
name?: string;
|
name?: string;
|
||||||
label?: React.ReactNode | any;
|
label?: React.ReactNode | any;
|
||||||
value?: any;
|
value?: any;
|
||||||
|
|||||||
@ -4,20 +4,20 @@ import "./slider.scss";
|
|||||||
|
|
||||||
import React, { Component } from "react";
|
import React, { Component } from "react";
|
||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
import MaterialSlider, { SliderClassKey, SliderProps } from "@material-ui/core/Slider";
|
import MaterialSlider, { SliderClassKey, SliderProps as MaterialSliderProps } from "@material-ui/core/Slider";
|
||||||
|
|
||||||
interface Props extends Omit<SliderProps, "onChange"> {
|
export interface SliderProps extends Omit<MaterialSliderProps, "onChange"> {
|
||||||
className?: string;
|
className?: string;
|
||||||
onChange?(evt: React.FormEvent<any>, value: number): void;
|
onChange?(evt: React.FormEvent<any>, value: number): void;
|
||||||
}
|
}
|
||||||
|
|
||||||
const defaultProps: Partial<Props> = {
|
const defaultProps: Partial<SliderProps> = {
|
||||||
step: 1,
|
step: 1,
|
||||||
min: 0,
|
min: 0,
|
||||||
max: 100,
|
max: 100,
|
||||||
};
|
};
|
||||||
|
|
||||||
export class Slider extends Component<Props> {
|
export class Slider extends Component<SliderProps> {
|
||||||
static defaultProps = defaultProps as object;
|
static defaultProps = defaultProps as object;
|
||||||
|
|
||||||
private classNames: Partial<{ [P in SliderClassKey]: string }> = {
|
private classNames: Partial<{ [P in SliderClassKey]: string }> = {
|
||||||
|
|||||||
@ -2,12 +2,12 @@ import './cube-spinner.scss'
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
|
|
||||||
interface Props {
|
export interface CubeSpinnerProps {
|
||||||
className?: string;
|
className?: string;
|
||||||
center?: boolean;
|
center?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class CubeSpinner extends React.Component<Props> {
|
export class CubeSpinner extends React.Component<CubeSpinnerProps> {
|
||||||
render() {
|
render() {
|
||||||
const { className, center } = this.props;
|
const { className, center } = this.props;
|
||||||
return (
|
return (
|
||||||
|
|||||||
@ -3,12 +3,12 @@ import './spinner.scss'
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
|
|
||||||
interface Props extends React.HTMLProps<any> {
|
export interface SpinnerProps extends React.HTMLProps<any> {
|
||||||
singleColor?: boolean;
|
singleColor?: boolean;
|
||||||
center?: boolean;
|
center?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Spinner extends React.Component<Props, {}> {
|
export class Spinner extends React.Component<SpinnerProps, {}> {
|
||||||
private elem: HTMLElement;
|
private elem: HTMLElement;
|
||||||
|
|
||||||
static defaultProps = {
|
static defaultProps = {
|
||||||
|
|||||||
@ -4,11 +4,11 @@ import React from "react";
|
|||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
import { TooltipDecoratorProps, withTooltip } from "../tooltip";
|
import { TooltipDecoratorProps, withTooltip } from "../tooltip";
|
||||||
|
|
||||||
interface Props extends React.HTMLAttributes<any>, TooltipDecoratorProps {
|
export interface StatusBrickProps extends React.HTMLAttributes<any>, TooltipDecoratorProps {
|
||||||
}
|
}
|
||||||
|
|
||||||
@withTooltip
|
@withTooltip
|
||||||
export class StatusBrick extends React.Component<Props> {
|
export class StatusBrick extends React.Component<StatusBrickProps> {
|
||||||
render() {
|
render() {
|
||||||
const { className, ...elemProps } = this.props
|
const { className, ...elemProps } = this.props
|
||||||
return (
|
return (
|
||||||
|
|||||||
@ -2,7 +2,7 @@ import "./stepper.scss";
|
|||||||
import React from "react";
|
import React from "react";
|
||||||
import { cssNames } from "../../utils";
|
import { cssNames } from "../../utils";
|
||||||
|
|
||||||
interface Props extends React.HTMLProps<any> {
|
export interface StepperProps extends React.HTMLProps<any> {
|
||||||
step: number;
|
step: number;
|
||||||
steps: Step[];
|
steps: Step[];
|
||||||
}
|
}
|
||||||
@ -11,7 +11,7 @@ interface Step {
|
|||||||
title?: string;
|
title?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Stepper extends React.Component<Props, {}> {
|
export class Stepper extends React.Component<StepperProps, {}> {
|
||||||
render() {
|
render() {
|
||||||
const { className, steps, ...props } = this.props;
|
const { className, steps, ...props } = this.props;
|
||||||
const stepsCount = steps.length;
|
const stepsCount = steps.length;
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user