mirror of
https://github.com/kubeshark/kubeshark.git
synced 2026-02-15 02:19:54 +00:00
Compare commits
16 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
a163f9cc0e | ||
|
|
2edb987c07 | ||
|
|
c0d7d0fe80 | ||
|
|
be5bd6a372 | ||
|
|
42df7aa42f | ||
|
|
9a9052198f | ||
|
|
2fb83c3642 | ||
|
|
d44674fe86 | ||
|
|
c57ed1efd3 | ||
|
|
c19cd00c77 | ||
|
|
39f8d40b76 | ||
|
|
bf731073c8 | ||
|
|
4bb68afaaf | ||
|
|
2126fc83a7 | ||
|
|
d0c1dbcd5e | ||
|
|
ad9dfbce40 |
@@ -144,6 +144,10 @@ var hubPodMappings = map[string]interface{}{
|
||||
"name": "SCRIPTING_SCRIPTS",
|
||||
"value": "[]",
|
||||
},
|
||||
{
|
||||
"name": "AUTH_APPROVED_DOMAINS",
|
||||
"value": "{{ gt (len .Values.tap.ingress.auth.approvedDomains) 0 | ternary (join \",\" .Values.tap.ingress.auth.approvedDomains) \"\" }}",
|
||||
},
|
||||
},
|
||||
"spec.containers[0].image": "{{ .Values.tap.docker.registry }}/hub:{{ .Values.tap.docker.tag }}",
|
||||
"spec.containers[0].imagePullPolicy": "{{ .Values.tap.docker.imagepullpolicy }}",
|
||||
@@ -158,6 +162,20 @@ var frontPodMappings = map[string]interface{}{
|
||||
"metadata.namespace": "{{ .Values.tap.selfnamespace }}",
|
||||
"spec.containers[0].image": "{{ .Values.tap.docker.registry }}/front:{{ .Values.tap.docker.tag }}",
|
||||
"spec.containers[0].imagePullPolicy": "{{ .Values.tap.docker.imagepullpolicy }}",
|
||||
"spec.containers[0].env": []map[string]interface{}{
|
||||
{
|
||||
"name": "REACT_APP_DEFAULT_FILTER",
|
||||
"value": " ",
|
||||
},
|
||||
{
|
||||
"name": "REACT_APP_HUB_HOST",
|
||||
"value": " ",
|
||||
},
|
||||
{
|
||||
"name": "REACT_APP_HUB_PORT",
|
||||
"value": "{{ .Values.tap.ingress.enabled | ternary \"80/api\" \"8898\" }}",
|
||||
},
|
||||
},
|
||||
}
|
||||
var frontServiceMappings = serviceAccountMappings
|
||||
var persistentVolumeMappings = map[string]interface{}{
|
||||
@@ -177,6 +195,13 @@ var workerDaemonSetMappings = map[string]interface{}{
|
||||
"spec.template.spec.containers[0].command[4]": "{{ .Values.tap.proxy.worker.srvport }}",
|
||||
"spec.template.spec.containers[0].command[6]": "{{ .Values.tap.packetcapture }}",
|
||||
}
|
||||
var ingressClassMappings = serviceAccountMappings
|
||||
var ingressMappings = map[string]interface{}{
|
||||
"metadata.namespace": "{{ .Values.tap.selfnamespace }}",
|
||||
"metadata.annotations[\"certmanager.k8s.io/cluster-issuer\"]": "{{ .Values.tap.ingress.certManager }}",
|
||||
"spec.rules[0].host": "{{ .Values.tap.ingress.host }}",
|
||||
"spec.tls": "{{ .Values.tap.ingress.tls | toYaml }}",
|
||||
}
|
||||
|
||||
func init() {
|
||||
rootCmd.AddCommand(helmChartCmd)
|
||||
@@ -193,6 +218,8 @@ func runHelmChart() {
|
||||
frontService,
|
||||
persistentVolume,
|
||||
workerDaemonSet,
|
||||
ingressClass,
|
||||
ingress,
|
||||
err := generateManifests()
|
||||
if err != nil {
|
||||
log.Error().Err(err).Send()
|
||||
@@ -210,6 +237,8 @@ func runHelmChart() {
|
||||
"07-front-service.yaml": template(frontService, frontServiceMappings),
|
||||
"08-persistent-volume-claim.yaml": template(persistentVolume, persistentVolumeMappings),
|
||||
"09-worker-daemon-set.yaml": template(workerDaemonSet, workerDaemonSetMappings),
|
||||
"10-ingress-class.yaml": template(ingressClass, ingressClassMappings),
|
||||
"11-ingress.yaml": template(ingress, ingressMappings),
|
||||
})
|
||||
if err != nil {
|
||||
log.Error().Err(err).Send()
|
||||
@@ -319,6 +348,16 @@ func handleDaemonSetManifest(manifest string) string {
|
||||
return strings.Join(lines, "\n")
|
||||
}
|
||||
|
||||
func handleIngressClass(manifest string) string {
|
||||
return fmt.Sprintf("{{- if .Values.tap.ingress.enabled }}\n%s{{- end }}\n", manifest)
|
||||
}
|
||||
|
||||
func handleIngress(manifest string) string {
|
||||
manifest = strings.Replace(manifest, "'{{ .Values.tap.ingress.tls | toYaml }}'", "{{ .Values.tap.ingress.tls | toYaml }}", 1)
|
||||
|
||||
return handleIngressClass(manifest)
|
||||
}
|
||||
|
||||
func dumpHelmChart(objects map[string]interface{}) error {
|
||||
folder := filepath.Join(".", "helm-chart")
|
||||
templatesFolder := filepath.Join(folder, "templates")
|
||||
@@ -363,6 +402,14 @@ func dumpHelmChart(objects map[string]interface{}) error {
|
||||
manifest = handleDaemonSetManifest(manifest)
|
||||
}
|
||||
|
||||
if filename == "10-ingress-class.yaml" {
|
||||
manifest = handleIngressClass(manifest)
|
||||
}
|
||||
|
||||
if filename == "11-ingress.yaml" {
|
||||
manifest = handleIngress(manifest)
|
||||
}
|
||||
|
||||
path := filepath.Join(templatesFolder, filename)
|
||||
err = os.WriteFile(path, []byte(manifestHeader+manifest), 0644)
|
||||
if err != nil {
|
||||
|
||||
@@ -15,6 +15,7 @@ import (
|
||||
"github.com/rs/zerolog/log"
|
||||
"github.com/spf13/cobra"
|
||||
v1 "k8s.io/api/core/v1"
|
||||
networking "k8s.io/api/networking/v1"
|
||||
rbac "k8s.io/api/rbac/v1"
|
||||
)
|
||||
|
||||
@@ -52,6 +53,8 @@ func runManifests() {
|
||||
frontService,
|
||||
persistentVolume,
|
||||
workerDaemonSet,
|
||||
ingressClass,
|
||||
ingress,
|
||||
err := generateManifests()
|
||||
if err != nil {
|
||||
log.Error().Err(err).Send()
|
||||
@@ -70,6 +73,8 @@ func runManifests() {
|
||||
"07-front-service.yaml": frontService,
|
||||
"08-persistent-volume-claim.yaml": persistentVolume,
|
||||
"09-worker-daemon-set.yaml": workerDaemonSet,
|
||||
"10-ingress-class.yaml": ingressClass,
|
||||
"11-ingress.yaml": ingress,
|
||||
})
|
||||
} else {
|
||||
err = printManifests([]interface{}{
|
||||
@@ -101,6 +106,8 @@ func generateManifests() (
|
||||
frontService *v1.Service,
|
||||
persistentVolumeClaim *v1.PersistentVolumeClaim,
|
||||
workerDaemonSet *kubernetes.DaemonSet,
|
||||
ingressClass *networking.IngressClass,
|
||||
ingress *networking.Ingress,
|
||||
err error,
|
||||
) {
|
||||
config.Config.License = ""
|
||||
@@ -173,6 +180,9 @@ func generateManifests() (
|
||||
return
|
||||
}
|
||||
|
||||
ingressClass = kubernetesProvider.BuildIngressClass()
|
||||
ingress = kubernetesProvider.BuildIngress()
|
||||
|
||||
config.Config.Tap.PersistentStorage = persistentStorage
|
||||
|
||||
return
|
||||
|
||||
@@ -60,5 +60,6 @@ func init() {
|
||||
tapCmd.Flags().Bool(configStructs.ServiceMeshLabel, defaultTapConfig.ServiceMesh, "Capture the encrypted traffic if the cluster is configured with a service mesh and with mTLS")
|
||||
tapCmd.Flags().Bool(configStructs.TlsLabel, defaultTapConfig.Tls, "Capture the traffic that's encrypted with OpenSSL or Go crypto/tls libraries")
|
||||
tapCmd.Flags().Bool(configStructs.IgnoreTaintedLabel, defaultTapConfig.IgnoreTainted, "Ignore tainted pods while running Worker DaemonSet")
|
||||
tapCmd.Flags().Bool(configStructs.IngressEnabledLabel, defaultTapConfig.Ingress.Enabled, "Enable Ingress")
|
||||
tapCmd.Flags().Bool(configStructs.DebugLabel, defaultTapConfig.Debug, "Enable the debug mode")
|
||||
}
|
||||
|
||||
@@ -113,7 +113,10 @@ func tap() {
|
||||
|
||||
// block until exit signal or error
|
||||
utils.WaitForTermination(ctx, cancel)
|
||||
printProxyCommandSuggestion()
|
||||
|
||||
if !config.Config.Tap.Ingress.Enabled {
|
||||
printProxyCommandSuggestion()
|
||||
}
|
||||
}
|
||||
|
||||
func printProxyCommandSuggestion() {
|
||||
@@ -315,7 +318,6 @@ func watchFrontPod(ctx context.Context, kubernetesProvider *kubernetes.Provider,
|
||||
Str("namespace", config.Config.Tap.SelfNamespace).
|
||||
Err(err).
|
||||
Msg("Failed creating pod.")
|
||||
cancel()
|
||||
|
||||
case <-timeAfter:
|
||||
if !isPodReady {
|
||||
@@ -458,7 +460,7 @@ func postHubStarted(ctx context.Context, kubernetesProvider *kubernetes.Provider
|
||||
connector.PostScriptDone()
|
||||
}
|
||||
|
||||
if !update {
|
||||
if !update && !config.Config.Tap.Ingress.Enabled {
|
||||
// Hub proxy URL
|
||||
url := kubernetes.GetLocalhostOnPort(config.Config.Tap.Proxy.Hub.Port)
|
||||
log.Info().Str("url", url).Msg(fmt.Sprintf(utils.Green, "Hub is available at:"))
|
||||
@@ -481,7 +483,12 @@ func postFrontStarted(ctx context.Context, kubernetesProvider *kubernetes.Provid
|
||||
"",
|
||||
)
|
||||
|
||||
url := kubernetes.GetLocalhostOnPort(config.Config.Tap.Proxy.Front.Port)
|
||||
var url string
|
||||
if config.Config.Tap.Ingress.Enabled {
|
||||
url = fmt.Sprintf("http://%s", config.Config.Tap.Ingress.Host)
|
||||
} else {
|
||||
url = kubernetes.GetLocalhostOnPort(config.Config.Tap.Proxy.Front.Port)
|
||||
}
|
||||
log.Info().Str("url", url).Msg(fmt.Sprintf(utils.Green, fmt.Sprintf("%s is available at:", misc.Software)))
|
||||
|
||||
if !config.Config.HeadlessMode {
|
||||
|
||||
@@ -5,6 +5,7 @@ import (
|
||||
"regexp"
|
||||
|
||||
v1 "k8s.io/api/core/v1"
|
||||
networking "k8s.io/api/networking/v1"
|
||||
)
|
||||
|
||||
const (
|
||||
@@ -25,6 +26,7 @@ const (
|
||||
ServiceMeshLabel = "servicemesh"
|
||||
TlsLabel = "tls"
|
||||
IgnoreTaintedLabel = "ignoreTainted"
|
||||
IngressEnabledLabel = "ingress-enabled"
|
||||
DebugLabel = "debug"
|
||||
ContainerPort = 80
|
||||
ContainerPortStr = "80"
|
||||
@@ -78,6 +80,18 @@ type ResourcesConfig struct {
|
||||
Hub ResourceRequirements `yaml:"hub"`
|
||||
}
|
||||
|
||||
type AuthConfig struct {
|
||||
ApprovedDomains []string `yaml:"approvedDomains"`
|
||||
}
|
||||
|
||||
type IngressConfig struct {
|
||||
Enabled bool `yaml:"enabled" default:"false"`
|
||||
Host string `yaml:"host" default:"ks.svc.cluster.local"`
|
||||
TLS []networking.IngressTLS `yaml:"tls"`
|
||||
Auth AuthConfig `yaml:"auth"`
|
||||
CertManager string `yaml:"certManager" default:"letsencrypt-prod"`
|
||||
}
|
||||
|
||||
type TapConfig struct {
|
||||
Docker DockerConfig `yaml:"docker"`
|
||||
Proxy ProxyConfig `yaml:"proxy"`
|
||||
@@ -96,6 +110,7 @@ type TapConfig struct {
|
||||
IgnoreTainted bool `yaml:"ignoreTainted" default:"false"`
|
||||
ResourceLabels map[string]string `yaml:"resourceLabels" default:"{}"`
|
||||
NodeSelectorTerms []v1.NodeSelectorTerm `yaml:"nodeSelectorTerms" default:"[]"`
|
||||
Ingress IngressConfig `yaml:"ingress"`
|
||||
Debug bool `yaml:"debug" default:"false"`
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
apiVersion: v2
|
||||
appVersion: "40.1"
|
||||
appVersion: "40.4"
|
||||
description: The API Traffic Analyzer for Kubernetes
|
||||
home: https://kubeshark.co
|
||||
keywords:
|
||||
@@ -22,4 +22,4 @@ name: kubeshark
|
||||
sources:
|
||||
- https://github.com/kubeshark/kubeshark/tree/master/helm-chart
|
||||
type: application
|
||||
version: "40.1"
|
||||
version: "40.4"
|
||||
|
||||
@@ -51,3 +51,21 @@ kubectl port-forward -n kubeshark service/kubeshark-front 8899:80
|
||||
```
|
||||
|
||||
Visit [localhost:8899](http://localhost:8899)
|
||||
|
||||
## Installing with Ingress Enabled
|
||||
|
||||
```shell
|
||||
helm install kubeshark kubeshark/kubeshark \
|
||||
--set tap.ingress.enabled=true \
|
||||
--set tap.ingress.host=ks.svc.cluster.local \
|
||||
--set "tap.ingress.auth.approvedDomains={gmail.com}" \
|
||||
--set license=LICENSE_GOES_HERE
|
||||
```
|
||||
|
||||
## Installing with Persistent Storage Enabled
|
||||
|
||||
```shell
|
||||
helm install kubeshark kubeshark/kubeshark \
|
||||
--set tap.persistentstorage=true \
|
||||
--set license=LICENSE_GOES_HERE
|
||||
```
|
||||
|
||||
@@ -15,11 +15,13 @@ rules:
|
||||
- ""
|
||||
- extensions
|
||||
- apps
|
||||
- networking.k8s.io
|
||||
resources:
|
||||
- pods
|
||||
- services
|
||||
- endpoints
|
||||
- persistentvolumeclaims
|
||||
- ingresses
|
||||
verbs:
|
||||
- list
|
||||
- get
|
||||
|
||||
@@ -25,6 +25,8 @@ spec:
|
||||
value: '{}'
|
||||
- name: SCRIPTING_SCRIPTS
|
||||
value: '[]'
|
||||
- name: AUTH_APPROVED_DOMAINS
|
||||
value: '{{ gt (len .Values.tap.ingress.auth.approvedDomains) 0 | ternary (join "," .Values.tap.ingress.auth.approvedDomains) "" }}'
|
||||
image: '{{ .Values.tap.docker.registry }}/hub:{{ .Values.tap.docker.tag }}'
|
||||
imagePullPolicy: '{{ .Values.tap.docker.imagepullpolicy }}'
|
||||
name: kubeshark-hub
|
||||
|
||||
@@ -16,6 +16,6 @@ spec:
|
||||
targetPort: 80
|
||||
selector:
|
||||
app: kubeshark-hub
|
||||
type: ClusterIP
|
||||
type: NodePort
|
||||
status:
|
||||
loadBalancer: {}
|
||||
|
||||
@@ -18,7 +18,7 @@ spec:
|
||||
- name: REACT_APP_HUB_HOST
|
||||
value: ' '
|
||||
- name: REACT_APP_HUB_PORT
|
||||
value: "8898"
|
||||
value: '{{ .Values.tap.ingress.enabled | ternary "80/api" "8898" }}'
|
||||
image: '{{ .Values.tap.docker.registry }}/front:{{ .Values.tap.docker.tag }}'
|
||||
imagePullPolicy: '{{ .Values.tap.docker.imagepullpolicy }}'
|
||||
name: kubeshark-front
|
||||
|
||||
@@ -16,6 +16,6 @@ spec:
|
||||
targetPort: 80
|
||||
selector:
|
||||
app: kubeshark-front
|
||||
type: ClusterIP
|
||||
type: NodePort
|
||||
status:
|
||||
loadBalancer: {}
|
||||
|
||||
16
helm-chart/templates/10-ingress-class.yaml
Normal file
16
helm-chart/templates/10-ingress-class.yaml
Normal file
@@ -0,0 +1,16 @@
|
||||
# THIS FILE IS AUTOMATICALLY GENERATED BY KUBESHARK CLI. DO NOT EDIT!
|
||||
---
|
||||
{{- if .Values.tap.ingress.enabled }}
|
||||
apiVersion: networking.k8s.io/v1
|
||||
kind: IngressClass
|
||||
metadata:
|
||||
creationTimestamp: null
|
||||
labels:
|
||||
kubeshark-cli-version: v1
|
||||
kubeshark-created-by: kubeshark
|
||||
kubeshark-managed-by: kubeshark
|
||||
name: kubeshark-ingress-class
|
||||
namespace: '{{ .Values.tap.selfnamespace }}'
|
||||
spec:
|
||||
controller: k8s.io/ingress-nginx
|
||||
{{- end }}
|
||||
40
helm-chart/templates/11-ingress.yaml
Normal file
40
helm-chart/templates/11-ingress.yaml
Normal file
@@ -0,0 +1,40 @@
|
||||
# THIS FILE IS AUTOMATICALLY GENERATED BY KUBESHARK CLI. DO NOT EDIT!
|
||||
---
|
||||
{{- if .Values.tap.ingress.enabled }}
|
||||
apiVersion: networking.k8s.io/v1
|
||||
kind: Ingress
|
||||
metadata:
|
||||
annotations:
|
||||
certmanager.k8s.io/cluster-issuer: '{{ .Values.tap.ingress.certManager }}'
|
||||
nginx.ingress.kubernetes.io/rewrite-target: /$2
|
||||
creationTimestamp: null
|
||||
labels:
|
||||
kubeshark-cli-version: v1
|
||||
kubeshark-created-by: kubeshark
|
||||
kubeshark-managed-by: kubeshark
|
||||
name: kubeshark-ingress
|
||||
namespace: '{{ .Values.tap.selfnamespace }}'
|
||||
spec:
|
||||
ingressClassName: kubeshark-ingress-class
|
||||
rules:
|
||||
- host: '{{ .Values.tap.ingress.host }}'
|
||||
http:
|
||||
paths:
|
||||
- backend:
|
||||
service:
|
||||
name: kubeshark-hub
|
||||
port:
|
||||
number: 80
|
||||
path: /api(/|$)(.*)
|
||||
pathType: Prefix
|
||||
- backend:
|
||||
service:
|
||||
name: kubeshark-front
|
||||
port:
|
||||
number: 80
|
||||
path: /()(.*)
|
||||
pathType: Prefix
|
||||
tls: {{ .Values.tap.ingress.tls | toYaml }}
|
||||
status:
|
||||
loadBalancer: {}
|
||||
{{- end }}
|
||||
@@ -43,6 +43,13 @@ tap:
|
||||
ignoreTainted: false
|
||||
resourceLabels: {}
|
||||
nodeSelectorTerms: []
|
||||
ingress:
|
||||
enabled: false
|
||||
host: ks.svc.cluster.local
|
||||
tls: []
|
||||
auth:
|
||||
approvedDomains: []
|
||||
certManager: letsencrypt-prod
|
||||
debug: false
|
||||
logs:
|
||||
file: ""
|
||||
|
||||
@@ -16,6 +16,8 @@ const (
|
||||
WorkerPodName = SelfResourcesPrefix + "worker"
|
||||
PersistentVolumeName = SelfResourcesPrefix + "persistent-volume"
|
||||
PersistentVolumeClaimName = SelfResourcesPrefix + "persistent-volume-claim"
|
||||
IngressName = SelfResourcesPrefix + "ingress"
|
||||
IngressClassName = SelfResourcesPrefix + "ingress-class"
|
||||
PersistentVolumeHostPath = "/app/data"
|
||||
MinKubernetesServerVersion = "1.16.0"
|
||||
)
|
||||
|
||||
@@ -20,6 +20,7 @@ import (
|
||||
"github.com/rs/zerolog/log"
|
||||
auth "k8s.io/api/authorization/v1"
|
||||
core "k8s.io/api/core/v1"
|
||||
networking "k8s.io/api/networking/v1"
|
||||
rbac "k8s.io/api/rbac/v1"
|
||||
k8serrors "k8s.io/apimachinery/pkg/api/errors"
|
||||
"k8s.io/apimachinery/pkg/api/resource"
|
||||
@@ -264,6 +265,10 @@ func (provider *Provider) BuildHubPod(opts *PodOptions) (*core.Pod, error) {
|
||||
Name: "SCRIPTING_SCRIPTS",
|
||||
Value: string(scriptsMarshalled),
|
||||
},
|
||||
{
|
||||
Name: "AUTH_APPROVED_DOMAINS",
|
||||
Value: strings.Join(config.Config.Tap.Ingress.Auth.ApprovedDomains, ","),
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
@@ -324,6 +329,10 @@ func (provider *Provider) BuildFrontPod(opts *PodOptions, hubHost string, hubPor
|
||||
volumeMounts := []core.VolumeMount{}
|
||||
volumes := []core.Volume{}
|
||||
|
||||
if config.Config.Tap.Ingress.Enabled {
|
||||
hubPort = "80/api"
|
||||
}
|
||||
|
||||
containers := []core.Container{
|
||||
{
|
||||
Name: opts.PodName,
|
||||
@@ -431,7 +440,7 @@ func (provider *Provider) BuildHubService(namespace string) *core.Service {
|
||||
Port: configStructs.ContainerPort,
|
||||
},
|
||||
},
|
||||
Type: core.ServiceTypeClusterIP,
|
||||
Type: core.ServiceTypeNodePort,
|
||||
Selector: map[string]string{"app": HubServiceName},
|
||||
},
|
||||
}
|
||||
@@ -456,12 +465,20 @@ func (provider *Provider) BuildFrontService(namespace string) *core.Service {
|
||||
Port: configStructs.ContainerPort,
|
||||
},
|
||||
},
|
||||
Type: core.ServiceTypeClusterIP,
|
||||
Type: core.ServiceTypeNodePort,
|
||||
Selector: map[string]string{"app": FrontServiceName},
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func (provider *Provider) CreateIngressClass(ctx context.Context, ingressClass *networking.IngressClass) (*networking.IngressClass, error) {
|
||||
return provider.clientSet.NetworkingV1().IngressClasses().Create(ctx, ingressClass, metav1.CreateOptions{})
|
||||
}
|
||||
|
||||
func (provider *Provider) CreateIngress(ctx context.Context, namespace string, ingress *networking.Ingress) (*networking.Ingress, error) {
|
||||
return provider.clientSet.NetworkingV1().Ingresses(namespace).Create(ctx, ingress, metav1.CreateOptions{})
|
||||
}
|
||||
|
||||
func (provider *Provider) CreateService(ctx context.Context, namespace string, service *core.Service) (*core.Service, error) {
|
||||
return provider.clientSet.CoreV1().Services(namespace).Create(ctx, service, metav1.CreateOptions{})
|
||||
}
|
||||
@@ -534,6 +551,87 @@ func (provider *Provider) doesResourceExist(resource interface{}, err error) (bo
|
||||
return resource != nil, nil
|
||||
}
|
||||
|
||||
func (provider *Provider) BuildIngressClass() *networking.IngressClass {
|
||||
return &networking.IngressClass{
|
||||
TypeMeta: metav1.TypeMeta{
|
||||
Kind: "IngressClass",
|
||||
APIVersion: "networking.k8s.io/v1",
|
||||
},
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: IngressClassName,
|
||||
Namespace: config.Config.Tap.SelfNamespace,
|
||||
Labels: buildWithDefaultLabels(map[string]string{
|
||||
fmt.Sprintf("%s-cli-version", misc.Program): misc.RBACVersion,
|
||||
}, provider),
|
||||
},
|
||||
Spec: networking.IngressClassSpec{
|
||||
Controller: "k8s.io/ingress-nginx",
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func (provider *Provider) BuildIngress() *networking.Ingress {
|
||||
pathTypePrefix := networking.PathTypePrefix
|
||||
ingressClassName := IngressClassName
|
||||
|
||||
return &networking.Ingress{
|
||||
TypeMeta: metav1.TypeMeta{
|
||||
Kind: "Ingress",
|
||||
APIVersion: "networking.k8s.io/v1",
|
||||
},
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: IngressName,
|
||||
Namespace: config.Config.Tap.SelfNamespace,
|
||||
Labels: buildWithDefaultLabels(map[string]string{
|
||||
fmt.Sprintf("%s-cli-version", misc.Program): misc.RBACVersion,
|
||||
}, provider),
|
||||
Annotations: map[string]string{
|
||||
"nginx.ingress.kubernetes.io/rewrite-target": "/$2",
|
||||
"certmanager.k8s.io/cluster-issuer": config.Config.Tap.Ingress.CertManager,
|
||||
},
|
||||
},
|
||||
Spec: networking.IngressSpec{
|
||||
IngressClassName: &ingressClassName,
|
||||
TLS: config.Config.Tap.Ingress.TLS,
|
||||
Rules: []networking.IngressRule{
|
||||
{
|
||||
Host: config.Config.Tap.Ingress.Host,
|
||||
IngressRuleValue: networking.IngressRuleValue{
|
||||
HTTP: &networking.HTTPIngressRuleValue{
|
||||
Paths: []networking.HTTPIngressPath{
|
||||
{
|
||||
Path: "/api(/|$)(.*)",
|
||||
PathType: &pathTypePrefix,
|
||||
Backend: networking.IngressBackend{
|
||||
Service: &networking.IngressServiceBackend{
|
||||
Name: HubServiceName,
|
||||
Port: networking.ServiceBackendPort{
|
||||
Number: configStructs.ContainerPort,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
Path: "/()(.*)",
|
||||
PathType: &pathTypePrefix,
|
||||
Backend: networking.IngressBackend{
|
||||
Service: &networking.IngressServiceBackend{
|
||||
Name: FrontServiceName,
|
||||
Port: networking.ServiceBackendPort{
|
||||
Number: configStructs.ContainerPort,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func (provider *Provider) BuildServiceAccount() *core.ServiceAccount {
|
||||
return &core.ServiceAccount{
|
||||
TypeMeta: metav1.TypeMeta{
|
||||
@@ -569,12 +667,14 @@ func (provider *Provider) BuildClusterRole() *rbac.ClusterRole {
|
||||
"",
|
||||
"extensions",
|
||||
"apps",
|
||||
"networking.k8s.io",
|
||||
},
|
||||
Resources: []string{
|
||||
"pods",
|
||||
"services",
|
||||
"endpoints",
|
||||
"persistentvolumeclaims",
|
||||
"ingresses",
|
||||
},
|
||||
Verbs: []string{
|
||||
"list",
|
||||
@@ -634,6 +734,11 @@ func (provider *Provider) CreateSelfRBAC(ctx context.Context, namespace string)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (provider *Provider) RemoveIngressClass(ctx context.Context, name string) error {
|
||||
err := provider.clientSet.NetworkingV1().IngressClasses().Delete(ctx, name, metav1.DeleteOptions{})
|
||||
return provider.handleRemovalError(err)
|
||||
}
|
||||
|
||||
func (provider *Provider) RemoveNamespace(ctx context.Context, name string) error {
|
||||
err := provider.clientSet.CoreV1().Namespaces().Delete(ctx, name, metav1.DeleteOptions{})
|
||||
return provider.handleRemovalError(err)
|
||||
|
||||
@@ -15,11 +15,13 @@ rules:
|
||||
- ""
|
||||
- extensions
|
||||
- apps
|
||||
- networking.k8s.io
|
||||
resources:
|
||||
- pods
|
||||
- services
|
||||
- endpoints
|
||||
- persistentvolumeclaims
|
||||
- ingresses
|
||||
verbs:
|
||||
- list
|
||||
- get
|
||||
|
||||
@@ -23,6 +23,7 @@ spec:
|
||||
value: '{}'
|
||||
- name: SCRIPTING_SCRIPTS
|
||||
value: '[]'
|
||||
- name: AUTH_APPROVED_DOMAINS
|
||||
image: docker.io/kubeshark/hub:latest
|
||||
imagePullPolicy: Always
|
||||
name: kubeshark-hub
|
||||
|
||||
@@ -16,6 +16,6 @@ spec:
|
||||
targetPort: 80
|
||||
selector:
|
||||
app: kubeshark-hub
|
||||
type: ClusterIP
|
||||
type: NodePort
|
||||
status:
|
||||
loadBalancer: {}
|
||||
|
||||
@@ -16,6 +16,6 @@ spec:
|
||||
targetPort: 80
|
||||
selector:
|
||||
app: kubeshark-front
|
||||
type: ClusterIP
|
||||
type: NodePort
|
||||
status:
|
||||
loadBalancer: {}
|
||||
|
||||
14
manifests/10-ingress-class.yaml
Normal file
14
manifests/10-ingress-class.yaml
Normal file
@@ -0,0 +1,14 @@
|
||||
# THIS FILE IS AUTOMATICALLY GENERATED BY KUBESHARK CLI. DO NOT EDIT!
|
||||
---
|
||||
apiVersion: networking.k8s.io/v1
|
||||
kind: IngressClass
|
||||
metadata:
|
||||
creationTimestamp: null
|
||||
labels:
|
||||
kubeshark-cli-version: v1
|
||||
kubeshark-created-by: kubeshark
|
||||
kubeshark-managed-by: kubeshark
|
||||
name: kubeshark-ingress-class
|
||||
namespace: kubeshark
|
||||
spec:
|
||||
controller: k8s.io/ingress-nginx
|
||||
37
manifests/11-ingress.yaml
Normal file
37
manifests/11-ingress.yaml
Normal file
@@ -0,0 +1,37 @@
|
||||
# THIS FILE IS AUTOMATICALLY GENERATED BY KUBESHARK CLI. DO NOT EDIT!
|
||||
---
|
||||
apiVersion: networking.k8s.io/v1
|
||||
kind: Ingress
|
||||
metadata:
|
||||
annotations:
|
||||
certmanager.k8s.io/cluster-issuer: letsencrypt-prod
|
||||
nginx.ingress.kubernetes.io/rewrite-target: /$2
|
||||
creationTimestamp: null
|
||||
labels:
|
||||
kubeshark-cli-version: v1
|
||||
kubeshark-created-by: kubeshark
|
||||
kubeshark-managed-by: kubeshark
|
||||
name: kubeshark-ingress
|
||||
namespace: kubeshark
|
||||
spec:
|
||||
ingressClassName: kubeshark-ingress-class
|
||||
rules:
|
||||
- host: ks.svc.cluster.local
|
||||
http:
|
||||
paths:
|
||||
- backend:
|
||||
service:
|
||||
name: kubeshark-hub
|
||||
port:
|
||||
number: 80
|
||||
path: /api(/|$)(.*)
|
||||
pathType: Prefix
|
||||
- backend:
|
||||
service:
|
||||
name: kubeshark-front
|
||||
port:
|
||||
number: 80
|
||||
path: /()(.*)
|
||||
pathType: Prefix
|
||||
status:
|
||||
loadBalancer: {}
|
||||
12
manifests/tls/certificate.yaml
Normal file
12
manifests/tls/certificate.yaml
Normal file
@@ -0,0 +1,12 @@
|
||||
apiVersion: cert-manager.io/v1
|
||||
kind: Certificate
|
||||
metadata:
|
||||
name: kubeshark-tls
|
||||
namespace: default
|
||||
spec:
|
||||
issuerRef:
|
||||
name: letsencrypt-prod
|
||||
kind: ClusterIssuer
|
||||
secretName: cert-kubeshark
|
||||
dnsNames:
|
||||
- ks.svc.cluster.local
|
||||
14
manifests/tls/cluster-issuer.yaml
Normal file
14
manifests/tls/cluster-issuer.yaml
Normal file
@@ -0,0 +1,14 @@
|
||||
apiVersion: cert-manager.io/v1
|
||||
kind: ClusterIssuer
|
||||
metadata:
|
||||
name: letsencrypt-prod
|
||||
spec:
|
||||
acme:
|
||||
server: https://acme-v02.api.letsencrypt.org/directory
|
||||
email: info@kubeshark.com
|
||||
privateKeySecretRef:
|
||||
name: letsencrypt-prod-key
|
||||
solvers:
|
||||
- http01:
|
||||
ingress:
|
||||
class: kubeshark-ingress-class
|
||||
15
manifests/tls/run.sh
Executable file
15
manifests/tls/run.sh
Executable file
@@ -0,0 +1,15 @@
|
||||
#!/bin/bash
|
||||
|
||||
__dir="$(cd -P -- "$(dirname -- "$0")" && pwd -P)"
|
||||
|
||||
helm repo add jetstack https://charts.jetstack.io
|
||||
helm repo update
|
||||
kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/v1.9.1/cert-manager.crds.yaml
|
||||
helm install \
|
||||
cert-manager jetstack/cert-manager \
|
||||
--namespace cert-manager \
|
||||
--create-namespace \
|
||||
--version v1.9.1
|
||||
|
||||
kubectl apply -f ${__dir}/cluster-issuer.yaml
|
||||
kubectl apply -f ${__dir}/certificate.yaml
|
||||
@@ -44,7 +44,7 @@ func CheckNewerVersion() {
|
||||
} else {
|
||||
downloadCommand = fmt.Sprintf("sh <(curl -Ls %s/install)", misc.Website)
|
||||
}
|
||||
msg := fmt.Sprintf("There is a new release! %v -> %v run:", misc.Ver, latestVersion)
|
||||
msg := fmt.Sprintf("There is a new release! %v -> %v Please upgrade to the latest release, as new releases are not always backward compatible. Run:", misc.Ver, latestVersion)
|
||||
log.Warn().Str("command", downloadCommand).Msg(fmt.Sprintf(utils.Yellow, msg))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -35,6 +35,11 @@ func CleanUpSelfResources(ctx context.Context, cancel context.CancelFunc, kubern
|
||||
func cleanUpNonRestrictedMode(ctx context.Context, cancel context.CancelFunc, kubernetesProvider *kubernetes.Provider, selfResourcesNamespace string) []string {
|
||||
leftoverResources := make([]string, 0)
|
||||
|
||||
if err := kubernetesProvider.RemoveIngressClass(ctx, kubernetes.IngressClassName); err != nil {
|
||||
resourceDesc := kubernetes.IngressClassName
|
||||
handleDeletionError(err, resourceDesc, &leftoverResources)
|
||||
}
|
||||
|
||||
if err := kubernetesProvider.RemoveNamespace(ctx, selfResourcesNamespace); err != nil {
|
||||
resourceDesc := fmt.Sprintf("Namespace %s", selfResourcesNamespace)
|
||||
handleDeletionError(err, resourceDesc, &leftoverResources)
|
||||
|
||||
@@ -58,21 +58,32 @@ func CreateHubResources(ctx context.Context, kubernetesProvider *kubernetes.Prov
|
||||
return selfServiceAccountExists, err
|
||||
}
|
||||
|
||||
// TODO: Why the port values need to be 80?
|
||||
_, err = kubernetesProvider.CreateService(ctx, selfNamespace, kubernetesProvider.BuildHubService(selfNamespace))
|
||||
if err != nil {
|
||||
return selfServiceAccountExists, err
|
||||
}
|
||||
|
||||
log.Info().Str("service", kubernetes.HubServiceName).Msg("Successfully created a service.")
|
||||
|
||||
_, err = kubernetesProvider.CreateService(ctx, selfNamespace, kubernetesProvider.BuildFrontService(selfNamespace))
|
||||
if err != nil {
|
||||
return selfServiceAccountExists, err
|
||||
}
|
||||
|
||||
log.Info().Str("service", kubernetes.FrontServiceName).Msg("Successfully created a service.")
|
||||
|
||||
if config.Config.Tap.Ingress.Enabled {
|
||||
_, err = kubernetesProvider.CreateIngressClass(ctx, kubernetesProvider.BuildIngressClass())
|
||||
if err != nil {
|
||||
return selfServiceAccountExists, err
|
||||
}
|
||||
log.Info().Str("ingress-class", kubernetes.IngressClassName).Msg("Successfully created an ingress class.")
|
||||
|
||||
_, err = kubernetesProvider.CreateIngress(ctx, selfNamespace, kubernetesProvider.BuildIngress())
|
||||
if err != nil {
|
||||
return selfServiceAccountExists, err
|
||||
}
|
||||
log.Info().Str("ingress", kubernetes.IngressName).Msg("Successfully created an ingress.")
|
||||
}
|
||||
|
||||
return selfServiceAccountExists, nil
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user