Categorygithub.com/edgelevel/lastpass-operator
module
2.0.0+incompatible
Repository: https://github.com/edgelevel/lastpass-operator.git
Documentation: pkg.go.dev

# README

lastpass-operator

Build Status Docker Tag Docker Pulls

A Kubernetes Operator to manage secrets stored in LastPass password manager

How it works

Suppose you have some credentials stored in LastPass

$ lpass show example/my-secret --json
[
  {
    "id": "8190226423897406876",
    "name": "my-secret",
    "fullname": "example/my-secret",
    "username": "whoami",
    "password": "s3cr3t",
    "last_modified_gmt": "1562690587",
    "last_touch": "0",
    "group": "example",
    "url": "https://lastpass.com",
    "note": "{\"myKey\":\"myValue\"}"
  }
]

Define a LastPass or LastPassGroup Custom Resource to automatically manage the lifecycle of your secrets in Kubernetes

$ cat example/edgelevel_v1alpha1_lastpass_cr.yaml
apiVersion: edgelevel.com/v1alpha1
kind: LastPass
metadata:
  name: example-lastpass
spec:
  secretRef:
    group: example
    name: my-secret
    withUsername: true
    withPassword: true
    withUrl: true
    withNote: true
  syncPolicy:
    enabled: true
    refresh: 10

# create a custom resource
$ kubectl apply -f example/edgelevel_v1alpha1_lastpass_cr.yaml

NOTE: The LastPassGroup custom resource will sync all the secrets in a lastpass folder to kubernetes. The lastpass group will not sync subfolders.

$ cat example/edgelevel_v1alpha1_lastpassgroup_cr.yaml
apiVersion: edgelevel.com/v1alpha1
kind: LastPassGroup
metadata:
  name: example-lastpassgruop
spec:
  secretRef:
    group: example
    withUsername: true
    withPassword: true
    withUrl: true
    withNote: true
  syncPolicy:
    enabled: true
    refresh: 10

# create a custom resource
$ kubectl apply -f example/edgelevel_v1alpha1_lastpassgroup_cr.yaml

The operator will take care of create native Kubernetes secrets and keep them up to date that if they change

# verify
$ kubectl get lastpass
$ kubectl get secrets

# inspect
$ kubectl get secret example-lastpass-8190226423897406876 -o yaml
apiVersion: v1
data:
  NOTE: eyJteUtleSI6Im15VmFsdWUifQ==
  PASSWORD: czNjcjN0
  URL: aHR0cHM6Ly9sYXN0cGFzcy5jb20=
  USERNAME: d2hvYW1p
kind: Secret
metadata:
  annotations:
    fullname: example/my-secret
    group: example
    id: "8190226423897406876"
    lastModifiedGmt: "1562690587"
    lastTouch: "0"
    name: my-secret
  creationTimestamp: "2019-07-09T15:00:13Z"
  labels:
    app: lastpass-operator
  name: example-lastpass-8190226423897406876
  namespace: default
  ownerReferences:
  - apiVersion: edgelevel.com/v1alpha1
    blockOwnerDeletion: true
    controller: true
    kind: LastPass
    name: example-lastpass
    uid: 0687d5a7-5f02-4ee4-a6c4-011c734f4149
  resourceVersion: "113312"
  selfLink: /api/v1/namespaces/default/secrets/example-lastpass-8190226423897406876
  uid: 382008d2-8999-444d-86c8-e4f29eecbe9f
type: Opaque

# check values
$ echo 'czNjcjN0' | base64 --decode
s3cr3t
$ echo 'eyJteUtleSI6Im15VmFsdWUifQ==' | base64 --decode | jq -c
{"myKey":"myValue"}

Metrics are exposed by default in Prometheus format, see an example

# port forward
kubectl port-forward service/lastpass-operator -n lastpass 8080:8383

# request metrics
http :8080/metrics

Considerations

  • If you want to understand how the operator works, you should have a look at the Reconcile method defined in lastpass_controller and at the CustomResourceDefinition
  • The diagram below explains the core logic of the reconcile loop

reconcile-loop

  • The recommended way to install the operator in a cluster is by applying the provided Helm chart
  • TODO for a working example you should have a look at niqdev/do-k8s
  • This operator has been mainly developed to simplify the secret management of low security environments, if you are a security paranoid you should audit this project and assess if it meets the security standard of your organization
  • The operator, for obvious reasons, won't work if you have MFA enabled on LastPass or your credentials "Require Password Reprompt"
  • Once this Argo CD feature will be implemented it should allow to bind secrets directly to an Application

Development

# download source
mkdir -p $GOPATH/src/github.com/edgelevel && cd $_
git clone [email protected]:edgelevel/lastpass-operator.git
cd lastpass-operator

# install operator-sdk
.travis/install_operator_sdk.sh

# install dependencies
go mod download -x

Run locally outside the cluster on minkube

# requires virtualbox
minikube start

# run locally
export OPERATOR_NAME=lastpass-operator
export LASTPASS_USERNAME=myUsername
export LASTPASS_PASSWORD=myPassword

# Install CRDs into cluster
make install

# Start lastpass operator
make run

# Alternatively you can install and run with
make install run

Run as a Deployment inside the cluster

# apply chart
helm template \
  --values chart/values.yaml \
  --set lastpass.username="myUsername" \
  --set lastpass.password="myPassword" \
  chart/ | kubectl apply -n lastpass -f -

Debug issues

# verify logs
kubectl logs deployment/lastpass-operator -n lastpass -f

Publish a new version on DockerHub

# build and publish manually (unsafe)
make docker-build IMG=edgelevel/lastpass-operator:X.Y.Z
make docker-push IMG=edgelevel/lastpass-operator:X.Y.Z

# build and publish using travis
git tag vX.Y.Z
git push origin --tags

TODO

# Packages

No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author