Skip to content

cednore/trilium

Repository files navigation

License Language count Top language Contributors Stargazers Forks

trilium

Trilium server on AWS

Infrastructure Security Lint Current online status

AWS Docker Terraform Terragrunt Ansible

✨ Introduction

This project demonstrates how-to of hosting trilium on your AWS infrastructure. If you want to self-host your very own personal knowledge base on AWS, this project could be a good starting point. You can easily use this project as a boilerplate for managing your trilium hosting infrastructure in IaC way; automatic infrastructure provisioning, frequent drift-checking, security scanning and more. (I use this repository too for managing my own trilium hosting πŸ˜‰.)

Before you start, it is strongly recommended to read trilium wiki first, especially server installation/deployment page.

What's included πŸ—ƒοΈ

  1. A terragrunt project defining multi-staged hosting infrastructure and provisioners
  2. Auto-generated terraform documentation
  3. GitHub actions;
    • Infrastructure drift detection (on every push, scheduled)
    • Linting and formatting (terraform fmt, terragrunt hclfmt, tflint)
    • Security vulnerability scanning (checkov, tfsec)
  4. Time-saving development scripts by justfile
  5. Documentations, including self-start/forking guide

Infrastructure summary πŸ—οΈ

  1. Single VPC with 3 public/private subnets
  2. An EC2 instance (t3.micro as default), publicly accessible via SSH
  3. Dockerized app container (default zadam/trilium:0.55.1)
  4. HTTPS proxy powered by nginx (inside a docker container)
  5. CloudWatch log group to keep app logs and proxy logs
  6. S3 bucket to keep the app data backups
  7. Security groups for the app instance
  8. Route53 records for domain name registration (subdomain level as default)
  9. A SSL certificate issued by Let's Encrypt for the app domain name
  10. Ansible playbooks to install and configure trilium on the EC2 instance
  11. Everything is written in Terraform, highly modularized, wrapped by Terragrunt

🧱 Prerequisites

Cloud

  1. An AWS account + AWS CLI (with credentials configured)
  2. S3 backend (a S3 bucket and a DynamoDB table)
  3. A personal domain and a public Route53 hosted zone managing this personal domain
  4. A SSH keypair .keypair.pem, along with terraform state file inside the backend bucket, and an ASM secret for holding secrets and configurations (these will be read and downloaded while applying, see generate "secrets" block at terragrunt.hcl)
  5. .env file, for environment variables (see .env.example)

Development tools

  1. Terraform >= 1.3 + Terragrunt >= 0.38
  2. Ansible, for provisioning playbooks
  3. just, for running development scripts
  4. TFLint, for linting tf files
  5. terraform-docs, for generating terraform documentation (optional)
  6. tfsec and Checkov, for scanning security vulnerabilities (optional)
  7. SQLite DB Browser (optional, for manually tweaking app db)
  8. Code editor/IDE ofc πŸ˜‰

⚑ Getting started

1. Clone this repository

# clone from github
git clone git@github.com:cednore/trilium.git

# cd into repo directory
cd trilium

2. Configure project

Before start, prepare dotenv file at .env. If you don't have .env file, you can create a new one by cp .env.example .env and customize with your own settings.

3. Intialize project

just init

4. Try create an execution plan

just tg plan

πŸ”¨ Development scripts

just is being used to define and run development scripts. You can simply run just --list or see justfile to check out all of available development scripts.

$ just --list
Available recipes:
    check-output         # check if output.json file exists
    connect *args=''     # open a ssh session into app instance
    dbdump               # download app db file (sqlite)
    dbrestore            # upload app db file
    default              # list available recipes
    drift-check *args='' # check for infrastructure drift
    fmt                  # format tf and hcl files
    graph                # generate terraform graph and convert into svg format (requires graphviz)
    init *args=''        # initialize terragrunt project
    lint                 # lint project (by tflint)
    output-json          # terragrunt output in json format (into output.json)
    restart              # restart app container (this fixes broken notes and branches)
    tfdocs               # generate terraform documentation in markdown
    tg *args=''          # wrap terragrunt with dotenv loading
    trilium-install      # run trilium installer playbook from local
    upgrade *args=''     # upgrade providers
    validate *args=''    # validate terragrunt project

Basic terragrunt scripts

Terragrunt doesn't load dotenv file automatically (see gruntwork-io/terragrunt#1750), so I've wrapped all terragrunt commands with preloading of dotenv files (see justfile). Replace terragrunt with just tg to run your terragrunt commands with environment variables set from .env file.

# initialize terragrunt project
just init

# upgrade providers
just upgrade

# validate terragrunt project
just validate

# equivalent of `terragrunt plan` with dotenv loading
just tg plan

# equivalent of `terragrunt apply` with dotenv loading
just tg apply

# check for infrastructure drift
just drift-check

ℹ️ INFO: Environment variables inside .env file is mandatory for terragrunt to run. Terragrunt will go fail without them. If you are going to run terragrunt commands without just, You should use dotenv cli tools like dotenv-cli or python-dotenv.

Outputs

Automation pipelines and many development script uses terraform output file. Use below command to generate output in JSON format.

See outputs.tf file and check out what's being outputted.

⚠️ WARNING: The terraform output includes sensitive data. Please hide/mask sensitive values from being displayed in public place where everyone is accessible (e.g CI/CD pipelines' stdout and stderr).

# terragrunt output in json format (into output.json)
just output-json

ℹ️ INFO: output.json file is gitignored.

Generating terraform graph

Below command is used to generate a visual representation of terraform plan. The output is in DOT initially, and also SVG format, which is converted by GraphViz.

# generate terraform graph and convert into svg format (requires graphviz)
just graph

Formatting & linting

# format tf and hcl files
just fmt

# lint project (by tflint)
just lint

Terraform documentation

This project uses terraform-docs to auto-generate markdown document of terraform resources being used. You can run following command to run the generator.

# generate terraform documentation in markdown
just tfdocs

Generated document will be stored at docs/terraform.md.

Interacting with live server

Often, you might wanna login to app instance (EC2) and run a few commands or download/upload app data.

⚠️ WARNING: Below commands depends on terragrunt output file output.json. You can run just output to generate this file.

# run trilium installer playbook from local
just trilium-install

# open a ssh session into the app instance
just connect

# run a command remotely on the app instance
just connect free -hw

# restart app container
just restart

# download app db file (sqlite)
just dbdump

# upload app db file
just dbrestore

ℹ️ INFO: just restart command is useful when facing broken branch issue.

πŸ‘‹ Contributions

Contributions are welcome by opening issues and pull requests. See CONTRIBUTING.md file for details.

🚧 Roadmap

  • Automagical backup to S3 bucket
  • dbdump not working due to permission error
  • Self-starter/forking guide
  • Budget-tracking
  • SRE concepts; monitoring performance and more
  • Diagrams explaining the infrastructure
  • GitHub issue templates; bug, security, cost, feature and so on
  • GitHub PR template

πŸ“„ License

This project is licensed under the MIT License.

πŸ™‡ Credits

  • Credit to @zadam for building such a beautiful note-taking app. (and also powerful πŸ‹ image and documentation)
  • Special thanks to @geneccx for giving me this whole idea.
  • Thanks to gitmoji, I use it everyday.