Giter VIP home page Giter VIP logo

helm-operator-get-started's Introduction

Managing Helm releases the GitOps way

We are moving to Flux v2

⚠️ Please note: In preparation of Flux v2 GA this repository with Flux v1 examples has been archived. The Flux v2 equivalent of what is shown here can be found at flux2-kustomize-helm-example.

Thanks a lot for your interest.

What is GitOps?

GitOps is a way to do Continuous Delivery, it works by using Git as a source of truth for declarative infrastructure and workloads. For Kubernetes this means using git push instead of kubectl create/apply or helm install/upgrade.

In a traditional CICD pipeline, CD is an implementation extension powered by the continuous integration tooling to promote build artifacts to production. In the GitOps pipeline model, any change to production must be committed in source control (preferable via a pull request) prior to being applied on the cluster. This way rollback and audit logs are provided by Git. If the entire production state is under version control and described in a single Git repository, when disaster strikes, the whole infrastructure can be quickly restored from that repository.

To better understand the benefits of this approach to CD and what the differences between GitOps and Infrastructure-as-Code tools are, head to the Weaveworks website and read GitOps - What you need to know article.

In order to apply the GitOps pipeline model to Kubernetes you need three things:

  • a Git repository with your workloads definitions in YAML format, Helm charts and any other Kubernetes custom resource that defines your cluster desired state (I will refer to this as the config repository)
  • a container registry where your CI system pushes immutable images (no latest tags, use semantic versioning or git commit sha)
  • an operator that runs in your cluster and does a two-way synchronization:
    • watches the registry for new image releases and based on deployment policies updates the workload definitions with the new image tag and commits the changes to the config repository
    • watches for changes in the config repository and applies them to your cluster

I will be using GitHub to host the config repo, Docker Hub as the container registry and Flux as the GitOps Kubernetes Operator.

gitops

Prerequisites

You'll need a Kubernetes cluster v1.11 or newer, a GitHub account, git and kubectl installed locally.

Install Helm v3 and fluxctl for macOS with Homebrew:

brew install helm fluxctl

On Windows you can use Chocolatey:

choco install kubernetes-helm fluxctl

On Linux you can download the helm and fluxctl binaries from GitHub.

Install Flux

The first step in automating Helm releases with Flux is to create a Git repository with your charts source code.

On GitHub, fork this repository and clone it locally (replace fluxcd with your GitHub username):

git clone https://github.com/fluxcd/helm-operator-get-started
cd helm-operator-get-started

*If you fork, update the release definitions with your Docker Hub repository and GitHub username located in \releases(dev/stg/prod)\podinfo.yaml in your master branch before proceeding.

Add FluxCD repository to Helm repos:

helm repo add fluxcd https://charts.fluxcd.io

Create the fluxcd namespace:

kubectl create ns fluxcd

Install Flux by specifying your fork URL (replace fluxcd with your GitHub username):

helm upgrade -i flux fluxcd/flux --wait \
--namespace fluxcd \
--set [email protected]:fluxcd/helm-operator-get-started

Install the HelmRelease Kubernetes custom resource definition:

kubectl apply -f https://raw.githubusercontent.com/fluxcd/helm-operator/master/deploy/crds.yaml

Install Flux Helm Operator with Helm v3 support:

helm upgrade -i helm-operator fluxcd/helm-operator --wait \
--namespace fluxcd \
--set git.ssh.secretName=flux-git-deploy \
--set helm.versions=v3

The Flux Helm operator provides an extension to Flux that automates Helm Chart releases for it. A Chart release is described through a Kubernetes custom resource named HelmRelease. The Flux daemon synchronizes these resources from git to the cluster, and the Flux Helm operator makes sure Helm charts are released as specified in the resources.

Note that Flux Helm Operator works with Kubernetes 1.11 or newer.

At startup, Flux generates a SSH key and logs the public key. Find the public key with:

fluxctl identity --k8s-fwd-ns fluxcd

In order to sync your cluster state with Git you need to copy the public key and create a deploy key with write access on your GitHub repository.

Open GitHub, navigate to your fork, go to Setting > Deploy keys click on Add deploy key, check Allow write access, paste the Flux public key and click Add key.

GitOps pipeline example

The config repo has the following structure:

├── charts
│   └── podinfo
│       ├── Chart.yaml
│       ├── README.md
│       ├── templates
│       └── values.yaml
├── hack
│   ├── Dockerfile.ci
│   └── ci-mock.sh
├── namespaces
│   ├── dev.yaml
│   └── stg.yaml
└── releases
    ├── dev
    │   └── podinfo.yaml
    └── stg
        └── podinfo.yaml

I will be using podinfo to demonstrate a full CI/CD pipeline including promoting releases between environments.

I'm assuming the following Git branching model:

  • dev branch (feature-ready state)
  • stg branch (release-candidate state)
  • master branch (production-ready state)

When a PR is merged in the dev or stg branch will produce a immutable container image as in repo/app:branch-commitsha.

Inside the hack dir you can find a script that simulates the CI process for dev and stg. The ci-mock.sh script does the following:

  • pulls the podinfo source code from GitHub
  • generates a random string and modifies the code
  • generates a random Git commit short SHA
  • builds a Docker image with the format: yourname/podinfo:branch-sha
  • pushes the image to Docker Hub

Let's create an image corresponding to the dev branch (replace stefanprodan with your Docker Hub username):

$ cd hack && ./ci-mock.sh -r stefanprodan/podinfo -b dev

Sending build context to Docker daemon  4.096kB
Step 1/15 : FROM golang:1.13 as builder
....
Step 9/15 : FROM alpine:3.10
....
Step 12/15 : COPY --from=builder /go/src/github.com/stefanprodan/k8s-podinfo/podinfo .
....
Step 15/15 : CMD ["./podinfo"]
....
Successfully built 71bee4549fb2
Successfully tagged stefanprodan/podinfo:dev-kb9lm91e
The push refers to repository [docker.io/stefanprodan/podinfo]
36ced78d2ca2: Pushed

Inside the charts directory there is a podinfo Helm chart. Using this chart I want to create a release in the dev namespace with the image I've just published to Docker Hub. Instead of editing the values.yaml from the chart source, I create a HelmRelease definition (located in /releases/dev/podinfo.yaml):

apiVersion: helm.fluxcd.io/v1
kind: HelmRelease
metadata:
  name: podinfo-dev
  namespace: dev
  annotations:
    fluxcd.io/automated: "true"
    filter.fluxcd.io/chart-image: glob:dev-*
spec:
  releaseName: podinfo-dev
  chart:
    git: [email protected]:fluxcd/helm-operator-get-started
    path: charts/podinfo
    ref: master
  values:
    image:
      repository: stefanprodan/podinfo
      tag: dev-kb9lm91e
    replicaCount: 1

Flux Helm release fields:

  • metadata.name is mandatory and needs to follow Kubernetes naming conventions
  • metadata.namespace is optional and determines where the release is created
  • spec.releaseName is optional and if not provided the release name will be $namespace-$name
  • spec.chart.path is the directory containing the chart, given relative to the repository root
  • spec.values are user customizations of default parameter values from the chart itself

The options specified in the HelmRelease spec.values will override the ones in values.yaml from the chart source.

With the fluxcd.io/automated annotations I instruct Flux to automate this release. When a new tag with the prefix dev is pushed to Docker Hub, Flux will update the image field in the yaml file, will commit and push the change to Git and finally will apply the change on the cluster.

gitops-automation

When the podinfo-dev HelmRelease object changes inside the cluster, Kubernetes API will notify the Flux Helm Operator and the operator will perform a Helm release upgrade.

$ helm -n dev history podinfo-dev

REVISION	STATUS    	CHART        	DESCRIPTION
1       	superseded	podinfo-0.2.0	Install complete
2       	deployed  	podinfo-0.2.0	Upgrade complete

The Flux Helm Operator reacts to changes in the HelmRelease collection but will also detect changes in the charts source files. If I make a change to the podinfo chart, the operator will pick that up and run an upgrade.

gitops-chart-change

$ helm -n dev history podinfo-dev

REVISION	STATUS    	CHART        	DESCRIPTION
1       	superseded	podinfo-0.2.0	Install complete
2       	superseded	podinfo-0.2.0	Upgrade complete
3       	deployed  	podinfo-0.2.1	Upgrade complete

Now let's assume that I want to promote the code from the dev branch into a more stable environment for others to test it. I would create a release candidate by merging the podinfo code from dev into the stg branch. The CI would kick in and publish a new image:

$ cd hack && ./ci-mock.sh -r stefanprodan/podinfo -b stg

Successfully tagged stefanprodan/podinfo:stg-9ij63o4c
The push refers to repository [docker.io/stefanprodan/podinfo]
8f21c3669055: Pushed

Assuming the staging environment has some sort of automated load testing in place, I want to have a different configuration than dev:

apiVersion: helm.fluxcd.io/v1
kind: HelmRelease
metadata:
  name: podinfo-rc
  namespace: stg
  annotations:
    fluxcd.io/automated: "true"
    filter.fluxcd.io/chart-image: glob:stg-*
spec:
  releaseName: podinfo-rc
  chart:
    git: [email protected]:fluxcd/helm-operator-get-started
    path: charts/podinfo
    ref: master
  values:
    image:
      repository: stefanprodan/podinfo
      tag: stg-9ij63o4c
    replicaCount: 2
    hpa:
      enabled: true
      maxReplicas: 10
      cpu: 50
      memory: 128Mi

With Flux Helm releases it's easy to manage different configurations per environment. When adding a new option in the chart source make sure it's turned off by default so it will not affect all environments.

If I want to create a new environment, let's say for hotfixes testing, I would do the following:

  • create a new namespace definition in namespaces/hotfix.yaml
  • create a dir releases/hotfix
  • create a HelmRelease named podinfo-hotfix
  • set the automation filter to glob:hotfix-*
  • make the CI tooling publish images from my hotfix branch to stefanprodan/podinfo:hotfix-sha

Production promotions with sem ver

For production, instead of tagging the images with the Git commit, I will use Semantic Versioning.

Let's assume that I want to promote the code from the stg branch into master and do a production release. After merging stg into master via a pull request, I would cut a release by tagging master with version 0.4.10.

When I push the git tag, the CI will publish a new image in the repo/app:git_tag format:

$ cd hack && ./ci-mock.sh -r stefanprodan/podinfo -v 0.4.10

Successfully built f176482168f8
Successfully tagged stefanprodan/podinfo:0.4.10

If I want to automate the production deployment based on version tags, I would use semver filters instead of glob:

apiVersion: helm.fluxcd.io/v1
kind: HelmRelease
metadata:
  name: podinfo-prod
  namespace: prod
  annotations:
    fluxcd.io/automated: "true"
    filter.fluxcd.io/chart-image: semver:~0.4
spec:
  releaseName: podinfo-prod
  chart:
    git: [email protected]:fluxcd/helm-operator-get-started
    path: charts/podinfo
    ref: master
  values:
    image:
      repository: stefanprodan/podinfo
      tag: 0.4.10
    replicaCount: 3

Now if I release a new patch, let's say 0.4.11, Flux will automatically deploy it.

$ cd hack && ./ci-mock.sh -r stefanprodan/podinfo -v 0.4.11

Successfully tagged stefanprodan/podinfo:0.4.11

gitops-semver

Managing Kubernetes secrets

In order to store secrets safely in a public Git repo you can use the Bitnami Sealed Secrets controller and encrypt your Kubernetes Secrets into SealedSecrets. The SealedSecret can be decrypted only by the controller running in your cluster.

The Sealed Secrets Helm chart is available on Helm Hub, so I can use the Helm repository instead of a git repo. This is the sealed-secrets controller release:

apiVersion: helm.fluxcd.io/v1
kind: HelmRelease
metadata:
  name: sealed-secrets
  namespace: adm
spec:
  releaseName: sealed-secrets
  chart:
    repository: https://kubernetes-charts.storage.googleapis.com/
    name: sealed-secrets
    version: 1.6.1

Note that this release is not automated, since this is a critical component I prefer to update it manually.

Install the kubeseal CLI:

brew install kubeseal

At startup, the sealed-secrets controller generates a RSA key and logs the public key. Using kubeseal you can save your public key as pub-cert.pem, the public key can be safely stored in Git, and can be used to encrypt secrets without direct access to the Kubernetes cluster:

kubeseal --fetch-cert \
--controller-namespace=adm \
--controller-name=sealed-secrets \
> pub-cert.pem

You can generate a Kubernetes secret locally with kubectl and encrypt it with kubeseal:

kubectl -n dev create secret generic basic-auth \
--from-literal=user=admin \
--from-literal=password=admin \
--dry-run \
-o json > basic-auth.json

kubeseal --format=yaml --cert=pub-cert.pem < basic-auth.json > basic-auth.yaml

This generates a custom resource of type SealedSecret that contains the encrypted credentials:

apiVersion: bitnami.com/v1alpha1
kind: SealedSecret
metadata:
  name: basic-auth
  namespace: adm
spec:
  encryptedData:
    password: AgAR5nzhX2TkJ.......
    user: AgAQDO58WniIV3gTk.......

Delete the basic-auth.json file and push the pub-cert.pem and basic-auth.yaml to Git:

rm basic-auth.json
mv basic-auth.yaml /releases/dev/

git commit -a -m "Add basic auth credentials to dev namespace" && git push

Flux will apply the sealed secret on your cluster and sealed-secrets controller will then decrypt it into a Kubernetes secret.

SealedSecrets

To prepare for disaster recovery you should backup the sealed-secrets controller private key with:

kubectl get secret -n adm sealed-secrets-key -o yaml --export > sealed-secrets-key.yaml

To restore from backup after a disaster, replace the newly-created secret and restart the controller:

kubectl replace secret -n adm sealed-secrets-key -f sealed-secrets-key.yaml
kubectl delete pod -n adm -l app=sealed-secrets

Getting Help

If you have any questions about Helm Operator and continuous delivery:

Your feedback is always welcome!

helm-operator-get-started's People

Contributors

hiddeco avatar jwenz723 avatar kminehart avatar kylemartin901 avatar mmorejon avatar nickgamehive avatar ogerbron avatar patrickbadley avatar scottbrenner avatar stefanprodan avatar stephenmoloney avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

helm-operator-get-started's Issues

Question: How to handle sub charts in a HelmRelease?

trying to add Istio with a helmRelease. The helmRelease gets created but it fails along the way. The operator doesnt give any error but when getting the output of the helmRelease i find this:

"message": "could not update dependencies in /tmp/flux-working725546946/charts/istio: Error: no repository definition for , , , , , , , , , , , , , , . Please add them via 'helm repo add'\nNote that repositories must be URLs or aliases. For example, to refer to the stable\nrepository, use "https://kubernetes-charts.storage.googleapis.com/\" or "@stable" instead of\n"stable". Don't forget to add the repo, too ('helm repo add').\n",

Should not need Helm to install Helm Operator

I do not think it is a good prerequisite to make the user install helm, just to install the helm-operator. I understand the irony of that statement, but setup should be as simple as possible. Put simply, helm is completely unnecessary (not saying difficult to install or anything, just unnecessary).

Timeout error when performing step to install flux

I'm blindly following the walkthrough, and when I get to this step I get a timeout error. I did replace the repo URL to my forked repo, and am using my company's AWS EKS cluster that I set up, using Kubernetes v1.18.

$ helm upgrade -i flux fluxcd/flux --wait \
--namespace fluxcd \
--set [email protected]:zillag/helm-operator-get-started
Release "flux" does not exist. Installing it now.
Error: timed out waiting for the condition

What do I need to do to proceed?

How to specify ordering/dependencies for different releases

Hi Team,

We are doing a poc for installing essential services at the time of bootstrapping our kubernetes cluster. We have certain scenarios where some releases should deploy only after another release is deployed successfully.

For example we are installing sealed secrets and other chart uses it to get secrets so part of our requirement is that sealed secrets should be installed before other releases.

Other scenario is we want to install CRD's before installing charts so if we have everything committed on github and we try to bootstrap our cluster through flux then how flux ensures that first CRD is installed and only after it's installation chart gets installed?

Thanks,
Hussain

https://weaveworks.github.io/flux is not a valid chart repository

Running the following command fails:

helm repo add fluxcd https://weaveworks.github.io/flux

Error:

Error: Looks like "https://weaveworks.github.io/flux" is not a valid chart repository or cannot be reached: Failed to fetch https://weaveworks.github.io/flux/index.yaml : 404 Not Found

Microservices best practices with HelmOperator

I have an architectural question regarding flux and helm. I'm following the https://github.com/fluxcd/helm-operator-get-started/ tutorial.

In my project, I have tens of microservices which can not live without each other. What would be your suggestion? Should I create as many charts and HelmReleases as many microservice I have, or just create a generic chart, which contains all of the microservices helm yaml files (like deployment, service, etc...)?

Is chart's values.yaml used?

When I create a HelmRelease using the provided artifact (/blob/master/releases/dev/podinfo.yaml), the helm deployment only has the values provided inline, not using the values.yaml file.

/gitops-helm/releases/dev$ helm get values podinfo-dev
hpa:
  enabled: false
image: stefanprodan/podinfo:dev-hdtwcel9
replicaCount: 1

Docker Images Filtering Question

Hello Stefan, first of all, thanks for your work. We are testing the Helm Flux operator and works very well. We are using the following image: quay.io/weaveworks/helm-operator:0.2.1. Actually, this GitHub issue I'm creating is more like a question than a bug report (I think).

This is our scenario: we have created 2 namespaces: prod and qa (under "namespaces"). Then, under the "releases" directories we have created 2 releases for the same application (one per each environment).

This is the "prod" release (I'm obfuscating the AWS account number, we are using ECR):

---
apiVersion: helm.integrations.flux.weave.works/v1alpha2
kind: FluxHelmRelease
metadata:
  name: hello-prod
  namespace: prod
  annotations:
    flux.weave.works/automated: "true"
    flux.weave.works/tag.hello: glob:master-*
  labels:
    chart: hello
spec:
  chartGitPath: hello
  releaseName: hello-prod
  values:
    image: 999999999999.dkr.ecr.us-west-2.amazonaws.com/eks-bgl_dev:master-v1
    persistence:
      enabled: false

This is the "qa" release:

---
apiVersion: helm.integrations.flux.weave.works/v1alpha2
kind: FluxHelmRelease
metadata:
  name: hello-qa
  namespace: qa
  annotations:
    flux.weave.works/automated: "true"
    flux.weave.works/tag.hello: glob:qa-*
  labels:
    chart: hello
spec:
  chartGitPath: hello
  releaseName: hello-qa
  values:
    image: 999999999999.dkr.ecr.us-west-2.amazonaws.com/eks-bgl_dev:qa-v1
    persistence:
      enabled: false

So, manual upgrades (by editing the image version on the Yaml) works like a charm. Now we are trying to test the automated upgrades. For that reason we have added the annotations "automated: true" and "tag.hello: glob--*"

What we can see is that Flux is not applying such filters. So, if you push a Docker image tagged as "master-v2", both the "prod" and "qa" deployments are automatically upgraded. If you push a new Docker image tagged as "qa-v2", both the "prod" and "qa" environments are also upgraded. What we want to do is just upgrade one of both environments at the same time, based on these annotations.

On the Flux logs I see something like this (some info obfuscated):

ts=2018-09-13T15:16:01.833847609Z caller=images.go:79 component=sync-loop service=test:fluxhelmrelease/hello container=chart-image [...] pattern=glob:* [...] info="added update to automation run" new=[...] reason="latest v1 (2018-09-13 11:37:08.020861429 +0000 UTC) > current v5 (2018-09-13 11:37:08.020861429 +0000 UTC)"

I see that it says "pattern=glob:*". I guess that here is where I should see my branch filter instead right?

I have been trying to emulate what you did at https://github.com/stefanprodan/gitops-helm/blob/master/releases/dev/podinfo.yaml for example. Do you think that my configuration is wrong? Or it can be a bug?

Thank you very much in advance.

Cheers,
Leo

Dynamic Environments Support

Hello @stefanprodan, we have a new question, please (we are a consulting company trying to promote GitOps and Flux among our clients). I have posted this question on the Weave Slack, but didn't receive any feedback yet, so maybe you can help us.

We are testing the Weave Flux Helm Operator and it's working very well for a "static" configuration, by configuring via yaml files the namespaces (prod, qa, etc), and by also using Yaml to configure each release.

Our question is: there is any way to support "dynamic" environments? Suppose that a developer creates a new branch named "app-hot-fix" and push some commits on that branch. The CI process creates new docker images based on that branch. Could be awesome automatically create a new namespace ("app-hot-fix" namespace) for that topic branch and deploy the new Docker image. As far I know, to do that I need to create a new Yaml file to define the namespace, a new Yaml file to define the new release, etc. This configuration process is manual.

But since that branch will just exist for a few hours could be great if that process could be automatically performed by Flux (create the new namespace and release). Something like "GitOps by Convention" (a k8s namespace per Git branch). Are there any features (or tools) that could be used to automagically setup a new release on-the-fly, just based on the existing Git branches?

Thank you very much in advance!

Didn't see any changes after running ci-mock.sh?

I ran the following command, keeping in mind to use my dockerhub username, and it did push a Docker image with a dev-xxxx tag. What's supposed to happen isn't clear after that.

cd hack && ./ci-mock.sh -r zillag/podinfo -b dev

The walkthrough says

With the fluxcd.io/automated annotations I instruct Flux to automate this release. When a new tag with the prefix dev is pushed to Docker Hub, Flux will update the image field in the yaml file, will commit and push the change to Git and finally will apply the change on the cluster.

Some questions:

  • Should I create the dev (and stg later) branch first before running the mock script? (I did anyway.)
  • Should I expect the releases/dev/podinfo.yaml to change in my local repo, and pushed to my remote? IOW, I'm not clear about the interaction between my local files, Git remote, and Kubernetes. There were no steps outlined on what I should check after I run the mock script.

does this work fine with public helm charts?

The approach looks very interesting, before testing it, I wonder if (as I supposed from reading the configuration flow) this works fine also for public helm charts. Also for owned charts we would like to keep the git repo separate and only interact with the helm charts repo. Thanks for the advice!

chart install fails with "cluster-admin not found" error

Running minikube v0.25.2, helm 2.9.0:

ncc@mal:~$ minikube start --kubernetes-version v1.10.0
Starting local Kubernetes v1.10.0 cluster...
Starting VM...
Getting VM IP address...
Moving files into cluster...
Setting up certs...
Connecting to cluster...
Setting up kubeconfig...
Starting cluster components...
Kubectl is now configured to use the cluster.
Loading cached images from config file.

ncc@mal:~$ kubectl create clusterrolebinding tiller-cluster-rule \
>     --clusterrole=cluster-admin \
>     --serviceaccount=kube-system:tiller 
clusterrolebinding.rbac.authorization.k8s.io "tiller-cluster-rule" created

ncc@mal:~$ helm init --skip-refresh --upgrade --service-account tiller
$HELM_HOME has been configured at /home/ncc/.helm.

Tiller (the Helm server-side component) has been installed into your Kubernetes Cluster.

Please note: by default, Tiller is deployed with an insecure 'allow unauthenticated users' policy.
For more information on securing your installation see: https://docs.helm.sh/using_helm/#securing-your-helm-installation
Happy Helming!

ncc@mal:~$ helm repo add sp https://stefanprodan.github.io/k8s-podinfo
"sp" has been added to your repositories

ncc@mal:~$ helm install --name cd --set helmOperator.create=true --set [email protected]:ncabatoff/weave-flux-helm-demo --set git.chartsPath=charts sp/weave-flux
Error: release cd failed: clusterroles.rbac.authorization.k8s.io "cd-weave-flux" is forbidden: attempt to grant extra privileges: [PolicyRule{APIGroups:["*"], Resources:["*"], Verbs:["*"]} PolicyRule{NonResourceURLs:["*"], Verbs:["*"]}] user=&{system:serviceaccount:kube-system:tiller 537689e0-5603-11e8-955b-080027bc943f [system:serviceaccounts system:serviceaccounts:kube-system system:authenticated] map[]} ownerrules=[] ruleResolutionErrors=[clusterroles.rbac.authorization.k8s.io "cluster-admin" not found]

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.