mirror of
https://github.com/lensapp/lens.git
synced 2025-05-20 05:10:56 +00:00
Add links for ingresses
Signed-off-by: Sebastian Malton <sebastian@malton.name>
This commit is contained in:
parent
a76fc6df84
commit
d8a50bc0ec
@ -4,7 +4,7 @@
|
||||
*/
|
||||
|
||||
import { KubeObject } from "../kube-object";
|
||||
import { autoBind } from "../../utils";
|
||||
import { autoBind, iter } from "../../utils";
|
||||
import { IMetrics, metricsApi } from "./metrics.api";
|
||||
import { KubeApi } from "../kube-api";
|
||||
import type { KubeJsonApiData } from "../kube-json-api";
|
||||
@ -61,23 +61,30 @@ export interface IIngressService {
|
||||
};
|
||||
}
|
||||
|
||||
export const getBackendServiceNamePort = (backend: IIngressBackend) => {
|
||||
/**
|
||||
* Format an ingress backend into the name of the service and port
|
||||
* @param backend The ingress target
|
||||
*/
|
||||
export function getBackendServiceNamePort(backend: IIngressBackend): string {
|
||||
// .service is available with networking.k8s.io/v1, otherwise using extensions/v1beta1 interface
|
||||
const serviceName = "service" in backend ? backend.service.name : backend.serviceName;
|
||||
// Port is specified either with a number or name
|
||||
const servicePort = "service" in backend ? backend.service.port.number ?? backend.service.port.name : backend.servicePort;
|
||||
|
||||
return { serviceName, servicePort };
|
||||
};
|
||||
if ("service" in backend) {
|
||||
const { name, port } = backend.service;
|
||||
|
||||
return `${name}:${port.number ?? port.name}`;
|
||||
}
|
||||
|
||||
return `${backend.serviceName}:${backend.servicePort}`;
|
||||
}
|
||||
|
||||
export interface Ingress {
|
||||
spec: {
|
||||
tls: {
|
||||
tls?: {
|
||||
secretName: string;
|
||||
}[];
|
||||
rules?: {
|
||||
host?: string;
|
||||
http: {
|
||||
http?: {
|
||||
paths: {
|
||||
path?: string;
|
||||
backend: IIngressBackend;
|
||||
@ -106,6 +113,11 @@ export interface Ingress {
|
||||
};
|
||||
}
|
||||
|
||||
export interface ComputedIngressRoute {
|
||||
url: string;
|
||||
service: string;
|
||||
}
|
||||
|
||||
export class Ingress extends KubeObject {
|
||||
static kind = "Ingress";
|
||||
static namespaced = true;
|
||||
@ -116,30 +128,22 @@ export class Ingress extends KubeObject {
|
||||
autoBind(this);
|
||||
}
|
||||
|
||||
getRoutes() {
|
||||
const { spec: { tls, rules }} = this;
|
||||
getRoutes(): string[] {
|
||||
return this.getRouteDecls().map(({ url, service }) => `${url} ⇢ ${service}`);
|
||||
}
|
||||
|
||||
if (!rules) return [];
|
||||
getRouteDecls(): ComputedIngressRoute[] {
|
||||
const { spec: { tls = [], rules = [] }} = this;
|
||||
const protocol = tls.length === 0
|
||||
? "http"
|
||||
: "https";
|
||||
|
||||
let protocol = "http";
|
||||
const routes: string[] = [];
|
||||
|
||||
if (tls && tls.length > 0) {
|
||||
protocol += "s";
|
||||
}
|
||||
rules.map(rule => {
|
||||
const host = rule.host ? rule.host : "*";
|
||||
|
||||
if (rule.http && rule.http.paths) {
|
||||
rule.http.paths.forEach(path => {
|
||||
const { serviceName, servicePort } = getBackendServiceNamePort(path.backend);
|
||||
|
||||
routes.push(`${protocol}://${host}${path.path || "/"} ⇢ ${serviceName}:${servicePort}`);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
return routes;
|
||||
return rules.flatMap(({ host = "*", http: { paths } = { paths: [] }}) => (
|
||||
paths.map(({ path = "/", backend }) => ({
|
||||
url: `${protocol}://${host}${path}`,
|
||||
service: getBackendServiceNamePort(backend),
|
||||
}))
|
||||
));
|
||||
}
|
||||
|
||||
getServiceNamePort(): IExtensionsBackend {
|
||||
@ -155,11 +159,9 @@ export class Ingress extends KubeObject {
|
||||
}
|
||||
|
||||
getHosts() {
|
||||
const { spec: { rules }} = this;
|
||||
const { spec: { rules = [] }} = this;
|
||||
|
||||
if (!rules) return [];
|
||||
|
||||
return rules.filter(rule => rule.host).map(rule => rule.host);
|
||||
return [...iter.filterMap(rules, rule => rule.host)];
|
||||
}
|
||||
|
||||
getPorts() {
|
||||
|
||||
@ -49,44 +49,51 @@ export class IngressDetails extends React.Component<IngressDetailsProps> {
|
||||
}
|
||||
|
||||
renderPaths(ingress: Ingress) {
|
||||
const { spec: { rules }} = ingress;
|
||||
const { spec: { rules = [], tls = [] }} = ingress;
|
||||
const protocol = tls.length === 0
|
||||
? "http"
|
||||
: "https";
|
||||
|
||||
if (!rules || !rules.length) return null;
|
||||
|
||||
return rules.map((rule, index) => {
|
||||
return (
|
||||
<div className="rules" key={index}>
|
||||
{rule.host && (
|
||||
<div className="host-title">
|
||||
<>Host: {rule.host}</>
|
||||
</div>
|
||||
)}
|
||||
{rule.http && (
|
||||
<Table className="paths">
|
||||
<TableHead>
|
||||
<TableCell className="path">Path</TableCell>
|
||||
<TableCell className="backends">Backends</TableCell>
|
||||
</TableHead>
|
||||
{
|
||||
rule.http.paths.map((path, index) => {
|
||||
const { serviceName, servicePort } = getBackendServiceNamePort(path.backend);
|
||||
const backend = `${serviceName}:${servicePort}`;
|
||||
return rules.map((rule, index) => (
|
||||
<div className="rules" key={index}>
|
||||
{rule.host && (
|
||||
<div className="host-title">
|
||||
<>Host: {rule.host}</>
|
||||
</div>
|
||||
)}
|
||||
{rule.http && (
|
||||
<Table className="paths">
|
||||
<TableHead>
|
||||
<TableCell className="path">Path</TableCell>
|
||||
<TableCell className="link">Link</TableCell>
|
||||
<TableCell className="backends">Backends</TableCell>
|
||||
</TableHead>
|
||||
{
|
||||
rule.http.paths
|
||||
.map(({ path = "/", backend }, index) => {
|
||||
const link = `${protocol}://${rule.host || "*"}${path}`;
|
||||
|
||||
return (
|
||||
<TableRow key={index}>
|
||||
<TableCell className="path">{path.path || ""}</TableCell>
|
||||
<TableCell className="backends">
|
||||
<p key={backend}>{backend}</p>
|
||||
<TableCell className="path">{path}</TableCell>
|
||||
<TableCell className="link">
|
||||
<a
|
||||
href={link}
|
||||
rel="noreferrer"
|
||||
target="_blank"
|
||||
>
|
||||
{link}
|
||||
</a>
|
||||
</TableCell>
|
||||
<TableCell className="backends">{getBackendServiceNamePort(backend)}</TableCell>
|
||||
</TableRow>
|
||||
);
|
||||
})
|
||||
}
|
||||
</Table>
|
||||
)}
|
||||
</div>
|
||||
);
|
||||
});
|
||||
}
|
||||
</Table>
|
||||
)}
|
||||
</div>
|
||||
));
|
||||
}
|
||||
|
||||
renderIngressPoints(ingressPoints: ILoadBalancerIngress[]) {
|
||||
@ -99,15 +106,14 @@ export class IngressDetails extends React.Component<IngressDetailsProps> {
|
||||
<TableCell className="name">Hostname</TableCell>
|
||||
<TableCell className="ingresspoints">IP</TableCell>
|
||||
</TableHead>
|
||||
{ingressPoints.map(({ hostname, ip }, index) => {
|
||||
return (
|
||||
{
|
||||
ingressPoints.map(({ hostname, ip }, index) => (
|
||||
<TableRow key={index}>
|
||||
<TableCell className="name">{hostname ? hostname : "-"}</TableCell>
|
||||
<TableCell className="ingresspoints">{ip ? ip : "-"}</TableCell>
|
||||
</TableRow>
|
||||
);
|
||||
})
|
||||
})
|
||||
))
|
||||
}
|
||||
</Table>
|
||||
</div>
|
||||
);
|
||||
|
||||
@ -56,7 +56,17 @@ export class Ingresses extends React.Component<IngressesProps> {
|
||||
<KubeObjectStatusIcon key="icon" object={ingress} />,
|
||||
ingress.getNs(),
|
||||
ingress.getLoadBalancers().map(lb => <p key={lb}>{lb}</p>),
|
||||
ingress.getRoutes().map(route => <p key={route}>{route}</p>),
|
||||
ingress.getRouteDecls().map(route => (
|
||||
<a
|
||||
key={route.url}
|
||||
href={route.url}
|
||||
rel="noreferrer"
|
||||
target="_blank"
|
||||
onClick={e => e.stopPropagation()}
|
||||
>
|
||||
{route.url}
|
||||
</a>
|
||||
)),
|
||||
<KubeObjectAge key="age" object={ingress} />,
|
||||
]}
|
||||
tableProps={{
|
||||
|
||||
Loading…
Reference in New Issue
Block a user