GithubHelp home page GithubHelp logo

slok / agebox Goto Github PK

View Code? Open in Web Editor NEW
204.0 4.0 15.0 348 KB

Age based repository file encryption gitops tool

License: Apache License 2.0

Makefile 1.20% Go 96.85% Dockerfile 0.70% Shell 1.25%
encryption age repository-secrets secrets secrets-management git-crypt blackbox sops gitops security

agebox's Introduction

agebox

agebox

CI Go Report Card Apache 2 licensed GitHub release (latest SemVer)

Easy and simple file repository encryption tool based on Age.

Have you ever thought "this should be simple" while you were using tools like Blackbox , Git-crypt or Sops? This is what agebox is. A tool on top of Age's security system that encrypts/decrypts your repository files, focused on simplicity and gitops.

Features

  • Secure (Agebox delegates security to Age).
  • Tracks encrypted files in repository.
  • No PGP and no agents, just simple SSH and Age key files.
  • File flexibility (encrypts/decrypts recursive paths, multiple/single files, all tracked files...).
  • Reencrypts all tracked files with a single command.
  • Focused on Gitops, CI flows and simplicity.
  • Works with any file (doesn't understand formats like JSON, YAML...).
  • Single binary/executable.
  • No side effects like VCS commands (e.g: doesn't execute Git commands for you).

Get agebox

Getting started

Initialize agebox tracking file.

agebox init

Encrypt (and track) multiple files.

agebox encrypt ./app1/secret1.yaml ./app2/secret1.yaml

Encrypt (and track) a directory in dry-run to see what would be encrypted before doing it.

agebox encrypt ./secrets --dry-run

Encrypt (and track) a directory and only (filter regex used) the secret named yaml files.

agebox encrypt ./manifests --filter ".*secret(\.yaml|\.yml)$"

Decrypt a subset of tracked secrets and a file.

agebox decrypt ./secrets/team-1 ./secrets/secret1.yaml

Decrypt only (filter regex used) team-a tracked files.

agebox decrypt ./secrets --filter ".*team-a.*"

Force decryption of all tracked files.

agebox decrypt --all --force

Validate tracked secrets are encrypted and not decrypted (without decrypt validation).

agebox validate --no-decrypt

Cat multiple encrypted files and print them to stdout.

agebox cat ./secrets/secret1.yaml.agebox ./secrets/secret2.json.agebox --no-log

Reencrypt all files.

agebox reencrypt

Untrack multiple files.

agebox untrack ./secrets/secret1.yaml ./secrets/secret2.yaml

Untrack and delete file.

agebox untrack ./secrets/secret1.yaml --delete

How does it work

When you initialize agebox on a repository it will create a file (.ageboxreg.yml) that will track all the encrypted files in the repository.

From now on if you encrypt files with agebox from the root of the repository it will:

  • Track the files if not already tracked.
  • Encrypt the files with the public keys in ./keys or --public-keys as recipients.
  • If is a directory it will expand to all the files in the directory and subdirectories.

As a regular flow of agebox usage examples, you can:

  • Decrypt tracked files as a single file, multiple files, a directory and its subdirectories...
  • Decrypt all tracked files (--all).
  • Reencrypt all tracked files with the public key recipients.
  • Encrypt all tracked files (--all) that are decrypted in the repository.
  • Untrack a file (and optionally delete from the file system).
  • Encrypt/decrypt in dry-run to validate (handy en CI for checking).
  • Cat encrypted files to stdout.
  • Validate tracked files are encrypted and not decrypted (useful on CI, git hooks...).

Check the Getting started section for specific commands.

Keys

Agebox supports the same asymmetric keys Age does:

  • X25519 (Age).
  • RSA SSH.
  • Ed25519 SSH.

Agebox knows how to discover keys in directories (recursively).

Public keys

The public keys are the recipients of the encrypted files. With their respective private keys, users will be able to decrypt the files.

Public keys should be on a directory relative to the root of the repository (by default ./keys) at the moment of invoking encryption commands, this simplifies the usage of keys by not requiring pgp keys or agents.

Agebox will encrypt with the loaded public keys, this means that when we add or remove any public key we should reencrypt the tracked files.

In case you don't want to have all the public keys in all the repositories that are managed by agebox, you could centralize these keys in another repository andgetting them before invoking agebox. Some usage examples:

  • Git submodule git pull --recurse-submodules.
  • Git repo and previous agebox command invoke git clone/pull.
  • Download public keys from S3.

You can configure this with --public-keys flag or AGEBOX_PUBLIC_KEYS env var.

You can have multiple public keys in a file (one per line), like Age recipients file.

Private keys

By default Agebox will try loading all the valid private keys from HOME/.ssh, however you can configure this with --private-keys flag or AGEBOX_PRIVATE_KEYS env var to point to specific directory with the keys (or a path to a single key).

Alternatives

  • Blackbox: Uses PGP (requires an agent), complex and sometimes has undesired side effects (e.g git commands execution).
  • Sops: Lots of features and very complex for simple use cases.
  • Git-crypt: Uses PGP (requires an agent), complex, 100% tied to Git.

Kudos

Thanks to @FiloSottile, @Benjojo12 and all the other contributors of Age.

Without Age, Agebox would not exist.

agebox's People

Contributors

cezarmathe avatar dependabot[bot] avatar matir avatar slok 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

agebox's Issues

[ENHANCEMENT] Add releases to AUR / Chocolatey

I wish to say thanks a lot to maintainers for a very promising project, that solves a very common problem via something easy-to-understand non-complex concepts, I enjoyed a lot to work with it after I understood some of the projects ideas.

However, I wish agebox to be presented in package managers of systems I use and I feel kinda lazy to download binary from releases page and find where could I put it on my $PATH folders. I guess, that would be the first huge step for project to become mature, to be used by huge amount of people (developers).

Thanks in advance, sorry for my english.

[feature] allow users to communicate private key passphases more securely

This Issue was originally going to be "please allow private-key operations to be delegated to an ssh-agent", but having read the ssh-agent protocol, it appears that that isn't possible. The only private key operation available is signing something, not encrypting it.

The root cause of the above request was me trying to solve the problem that building a developer/ops workflow around agebox is currently more annoying and fiddly than it could be. This is because a script that does any repeated validation/etc of encrypted files (e.g. working out which files need to be re-encrypted, versus those that could be git restored) will ask for the ssh passphrase on every agebox invocation.

To avoid this, I could use the --passphrase=FOO parameter. But this isn't a great solution, for a few reasons:

  • it temporarily exposes the passphrase in the machine's process table, which might be a poor idea for shared/CI/etc machines
  • it requires me/the-script to solve the quoting problem for every possible set of shell meta-characters that /might/ exist in a passphrase
  • it leaves the passphrase in the shell's history file, if used interactively

Other tools have solved this problem in a couple of different ways:

  • sigtool uses environment variable indirection: https://github.com/opencoff/sigtool/blob/master/sigtool.go#L98
    • NB this isn't simply foo-tool --passphrase $ENVVAR. It communicates the name of the envvar that the process should look up, independently, not the value: e.g. foo-tool --passphrase-envvar-name ENVVAR
  • a variety of tools implement a flag that means "read STDIN and assume that a machine/script is talking to you, not a human, so don't output any prompts/etc"

Whilst the envvar-name-indirection route is probably the more useful one, I can see arguments for using STDIN from a security perspective. It'd be great to have either of these -- or both! -- as options for agebox :-)

[feature] Reword "Invalid secret"

Does agebox validate's "Invalid secret" wording communicate the most useful message to the user?

image

This makes me, An Ops, think that perhaps something's been corrupted in the file.

Perhaps "Plaintext secret" might communicate the real "problem" better, here. But that's just an idea. I do think "invalid" is scary and doesn't help the new-adopter-user :-)

cannot decrypt file after encryption using personal RSA keys

I have a key pair that I use for everything, I wanted to test this out with it but I it will not decrypt:

$ agebox validate
INFO[0000] Using 1 tracked files                         version=0.6.1
WARN[0000] Could not load private key: invalid private key  key=/home/michael/.ssh/michael_rsa svc=storage.fs.KeyRepository version=0.6.1
WARN[0000] Could not load private key: invalid private key  key=/home/michael/.ssh/michael_rsa.pub svc=storage.fs.KeyRepository version=0.6.1
INFO[0000] Loaded private keys                           keys=2 svc=storage.fs.KeyRepository version=0.6.1
ERRO[0000] Invalid secret: could not decrypt secret: age could not decrypt the secret: no identity matched any of the recipients  secret-id=nixops/secrets/localstate.nixops svc=box.validate.Service version=0.6.1

yes, this key has a password on it, but it doesn't work with the --passphrase flag either.
I've used this key for so many things, I must be doing something wrong here.

Thanks!

Add validation command

Validation command for now should validate the tracked files:

  • Can be decrypted (optional).
  • Tracked files are encrypted.
  • Tracked files are not decrypted.

This command can be useful for CI and git hooks.

OpenSSH ControlMaster sockets cause agebox errors

I use the OpenSSH ControlMaster feature which allows multiple SSH sessions to share a single connection by providing a UNIX domain socket for additional connections. Because agebox walks all files when loading key files and attempting to open these files as plain files fails with an error, it causes agebox in general to fail when decrypting:

error: "decrypt" command failed: could not decrypt: could not get private key: could not read private key "/home/matir/.ssh/master/[email protected]:22" data from file: open /home/matir/.ssh/master/[email protected]:22: no such device or address

I'm sending a PR momentarily to skip sockets.

[feature] Don't output logs for every non-private-key in ~/.ssh

Hi πŸ‘‹ Thanks for making a really useful tool!

[This is the first of a few quality-of-life feature Issues I'm going to file today. I hope they make sense :-)]

Everyone has at least a few non-private-keys in their .ssh directory, from pubkeys to ssh config to authorized_keys files. Right now, on encrypt and decrypt operation, agebox's output is really messy, which obscures the important detail about what it's actually doing.

Here's a screenshot of it in action ... (NB there is no problem with seemingly valid private keys being reported as invalid, here. That's expected in my setup, and is not part of the issue I'm reporting here!)

image

I think it would be really useful if:

  • operations that don't need private keys (e.g encrypt/reencrypt) shouldn't report these warnings at all
  • operations that need private keys (decrypt) only report these warnings if given a --verbose flag.

I note that, with a default keys/ directory in a repo that's properly populated with public keys, the encrypt operation still reports all the files it couldn't parse in ~/.ssh. To my mind, adhering to agebox's default setup should be a signal to the tool that I don't want it to go looking in ~/.ssh during encryption!

I am aware that flags and envvars can be used to teach agebox more detail about my setup :-) I still think the default logging is too noisy and, in the case of re/encrypt, it's flat out wrong to report private key "problems", at any log level!

Why is the .agebox file deleted on decrypt?

Hello πŸ‘‹

I am playing around with agebox to track secrets in a git repository, and I am surprised by the fact that the .agebox file is deleted on decrypt.

Used in git, this means that if I decrypt the file to feed it to my tool, I'm then going to need to git restore it each time before committing. Encrypting the file again is not really an option either since that's going to change the file even if there are no changes.

There is the cat command, but in various situations it's cumbersome to have to deal with stdout for secret import, where having them in a file is straightforward (one can redirect cat to a file, but that’s again some unneeded ceremony from my point of view).

Am I using agebox wrong in some way? πŸ€”

I think having an option to keep the .agebox files on decrypting would make sense, with maybe an additional command that delete any unencrypted tracked secret file as a simple and VCS agnostic way of preventing those from lying around.

Add passphrase support on SSH keys

We come from #61

Apart from stdin we should support passing the passphrase using a flag or an env var so we don't require the user to use Agebox in a interactive way

Sanitize Age `X25519` keys on load

On private keys:

  • Remove lines that start with #.
  • Trim new lines and spaces.

On public keys:

  • Remove # public key: so the user can use the output of age-keygen directly.
  • Trim new lines and spaces.

agebox cannot be used to encrypt content for yubikey-backed keys

When given a public key created with the age-plugin-yubikey plugin, agebox refuses to encrypt for it:

WARN[0000] Could not load public key: invalid public key  key=keys/charles.age svc=storage.fs.KeyRepository version=0.6.1

...this means that even someone willing to use non-agebox tools to decrypt their content (in the interim pending plugin support available in the decryption path for agebox itself) cannot encrypt their content with such a key.

[ENHANCEMENT] Management of .gitignore in case of present git repository

Hi.
I think it would be a great addition if agebox could manage the adding/removing of the unencrypted filenames not only in .agebox.yml but also in the .gitignore file.

This is the only feature I am missing from blackbox ATM.

I know that this is strictly speaking not the job of agebox but I would really really like to remove blackbox from my system ;)

Again thank you for being so responsive.

[bug/feature] `--no-color` changes more than just the color/no-color of the log output

As I'm reporting a few Issues with agebox today, I find myself using screenshots rather than simply capturing the text output of the tool. This is because:

  • the "normal" user interaction, at the shell, is via colorized logs
  • diverting colorized output into a file, for copy'n'pasting here in github, includes color-related escape codes (yes, the're removable with sed/etc, but still ...)
  • using the --no-color output option does more than simply stripping the color-related escape codes from the log output - it changes the logging format such that it's not representative of the "normal" user experience any longer.

Here's a screenshot :-)

image

This is somewhat annoying for filing github Issues.

But more than that, it stops a color-intolerant user (or build system, or script, etc etc) from being able to access the "normal" format of the logs.

Request: make --no-color do only the single job of not outputting color-related escape codes. Leave the log format modifications to other flags.

Loading invalid public keys should not error

When we try loading public keys from a directory if any of the keys are not valid keys for agebox it will return an error.

A better UX would be to warn that the keys being loaded can't are not correct and use the ones loaded correctly.

During the process, if we don't have enough keys it should fail.

What private key format does agebox expect?

I tried decrypting a file with the private key stored in the file generated by age-keygen -o key.txt and it just won't work.

age version: devel (package version: 1.0.0rc.1-2, Arch Linux)
agebox version: dev (installed with go install github.com/slok/agebox/cmd/[email protected])

[QUESTION] How to use ssh-rsa/ed25519 keys?

Hello!

I'm evaluating agebox as an alternative to the currently used "blackbox" scripts.

This is where I found that I can encrypt files using my ed25519 based ssh key but the decryption fails. I have tested this on MacOS (10.15.7) and Linux:

> mkdir agebox-test
> cd agebox-test
> echo "HELLO" > testfile
> agebox init

> mkdir keys
> ssh-keygen -t ed25519 -N "passphrase"
# copy id_es25519.pub to ./keys

> agebox encrypt testfile
INFO[0000] Loaded public keys                            keys=1 svc=storage.fs.KeyRepository version=v0.2.0
INFO[0000] Secret encrypted                              secret-id=testfile svc=box.encrypt.Service version=v0.2.0
> agebox decrypt testfile.agebox --private-key id_es25519 # private key file is present in this directory

error: "decrypt" command failed: could not decrypt: could not get private key: could not load private key in "id_es25519": invalid private key

Can you help me finding out what I do wrong?

Thank you for building agebox and for you help
Frank

[Feature] rencrypt all files (only if the decrypted file changed)

I use this workflow (i use a command from my Makefile (see bellow) )

  • git checkout/pull project
  • unlock all files with make secret-unlock
  • work on my project
  • lock all files with make secret-lock secret-check
  • commit all my works

But If the decrypted files not changed and if i use make secret-lock the content of encrypted files has changed, is it possible to store de SHA1 in the encrypted file (or tempory hidden file during decryption step) and reencrypt only if SHA1 changed and restore encrypted file git state if SHA1 is identical

secret-lock: requirements-check ## lock all files from repository
    agebox reencrypt

secret-unlock: requirements-check ## unlock all files from repository
    agebox decrypt --all

secret-check: requirements-check ## Verify all secrets is in agebox vault
    agebox validate --no-decrypt

Discover private keys from a path

At this moment we were discovering public keys from a directory, however, the private key was a single file.

Would be helpful to discover N private keys and use them to decrypt.

By default, we could use $HOME/.ssh.

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.