原生部署Bitwarden_rs教程(MacOS为例)

前言

本文主要介绍开源密码管理软件Bitwarden(_rs)的部署和使用。

简介

现在各种各样的APP越来越多,很多都需要帐号才能正常使用,而网络环境又比较糟糕,各种拖库、撞库、用户信息泄露的事情屡见不鲜,所以出于安全的考虑,最好在不同的网站使用不同的帐号(用户名+密码),并且定期更换密码。但是,怎么“编造”还得记住这些密码就成了一个让人头疼的问题。

一个比较简单的解决办法就是使用密码管理软件。此类软件产品很多,比较出名的有1Password、Keepass、LastPass等。之前我一直用的是LastPass的免费帐户,体验还是挺好的,但是最新的使用政策对免费帐户做了限制,未来也不排除进一步的限制,所以想干脆自己进行密码的管理。选来选去,就选中了Bitwarden。

image-20210309114225314

Bitwarden(_rs)简介

根据维基百科的介绍,“Bitwarden是一款自由且开源的密码管理服务,用户可在加密的保管库中存储敏感信息。Bitwarden平台提供有多种客户端应用程序,包括网页用户界面、桌面应用,浏览器扩展、移动应用以及命令行界面。Bitwarden提供云托管服务,并支持自行部署解决方案。”

选择Bitwarden,主要是看中了它的这几个优点:

  1. 开源,所以不太担心程序中“后门”的问题;
  2. 跨平台同步,提供PC端、移动端、网页扩展等多种形式的访问方式;
  3. 支持自行部署服务端,这样就可以把数据存放在自己的数据库中。

但是,Bitwarden的服务端采用.Net + MS SQL的方案,对于个人使用来说不太友好。好在,有大神采用Rust重写了Bitwarden服务端,即Bitwarden_rs,不仅降低了对配置的要求,并且实现了官方只有付费版本才具有的一些功能,当然也是开源的。

/pexels-pixabay-60504.jpeg

原生部署Bitwarden_rs

之所以强调“原生”,是因为Bitwarden_rs可以采用Docker或者原生两种方式,但是绝大多数的中文教程里都是直接采用Docker方式进行部署的,那么我们在这里提供从源代码开始编译、部署的方法。接下来,我将以MacOS作为基础环境完成部署,Linux系统可以参照这个过程进行部署。

此外,为了提供网页端的功能,还需要安装Bitwarden Web Vault,这个是由Bitwarden官方提供的,同样也是开源的,可以与Bitwarden_rs无缝配合。

安装依赖

Bitwarden_rs的编译、部署和运行主要会用到以下依赖:

  1. 编译环境,既然是Rust编写的,所以编译肯定需要用到Rust Nightly,推荐使用rustup安装Rustp:

    1
    brew install rustup-init
  2. 数据库,Bitwarden_rs支持SQLite、PostgreSQL和MySQL,可以根据需要安装相应的数据库,此外编译时也可能用到相应的依赖。以SQLite为例:

    1
    brew install sqlite3
  3. 服务端JavaScript环境Node.js,提供Bitwarden Web Vault相关的服务功能:

    1
    brew install nodejs
  4. 密码库OpenSSL,MacOS一般自带;

  5. Nginx,用来实现反向代理等功能(非必需):

    1
    brew install nginx

完成以上依赖的安装后,就可以正式进入Bitwarden的编译了。

注意:建议申请一个自己的域名,用作后面使用。

Bitwarden_rs及Web Vault编译

  1. 编译Bitwarden_rs(以SQLite为后端):

    1
    2
    3
    4
    5
    6
    7
    # 将源代码复制到本地
    git clone https://github.com/dani-garcia/bitwarden_rs ./bitwarden_rs
    cd bitwarden_rs
    # 选择最新版本
    git checkout "$(git tag --sort=v:refname | tail -n1)"
    # 编译SQLite后端,(编译后二进制文件位于bitwarden_rs/target/release/bitwarden_rs)
    cargo build --features sqlite --release

    正常情况下,如果编译成功,会有如下信息:

  2. 编译Bitwarden Web Vault:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    # 复制源代码至本地
    git clone --recurse-submodules https://github.com/bitwarden/web.git web-vault
    cd web-vault
    # 切换至最新版本
    git checkout "$(git tag --sort=v:refname | tail -n1)"

    # 从dani-garcia/bw_web_builds下载相应的补丁文件
    # 假设Web Vault最新版本号为vX.Y.Z,则应该选择相应的补丁或者版本号小于但是最接近当前版本号的补丁
    # 在web-vault内打补丁

    export WEB_VERSION=vX.Y.Z
    curl https://raw.githubusercontent.com/dani-garcia/bw_web_builds/master/patches/${WEB_VERSION}.patch >${WEB_VERSION}.patch
    git apply ${WEB_VERSION}.patch -v

    # 编译
    npm install
    npm run dist

    与Bitwarden_rs的编译相比,这一步相对麻烦而且费时费力,可以直接从网上下载:dani-garcia/bw_web_builds。实际上,我自己也没有编译而是直接用的现成的:D

配置启动Bitwarden_rs

  1. 我们要将编译后的文件放到合适的文件夹,假设为/data:

    1
    2
    cp -R 当前路径/bitwarden_rs/target/release /data/bitwarden/rs
    cp -R 当前路径/web-vault/build /data/bitwarden_rs/web-vault
  2. 将bitwarden_rs 提供的环境变量模板复制到程序文件夹(此处即/data/bitwarden_rs中:

    1
    cp PATH/binwarden_rs/.env.template /data/bitwarden_rs/.env
  3. 修改.env中的相关内容,重点包括:

    • DATABASE_URL
    • WEB_VAULT_ENABLED
    • ROCKET_ADDRESS
    • DOMAIN

    其他变量,例如端口号、WebSocket等可根据需求修改

  4. 安装为MacOS服务(保证开机启动)

    • 创建plist

      1
      sudo touch /Library/LaunchDaemons/bitwarden_rs.plist
    • 写入以下内容,修改UserNameGroupNameProgramArguments的相关内容:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19
      20
      21
      22
      23
      24
      25
      26
      27
      28
      29
      <?xml version="1.0" encoding="UTF-8"?>
      <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
      <plist version="1.0">
      <dict>
      <key>Label</key>
      <string>bitwarden_rs</string>
      <key>RunAtLoad</key>
      <true/>
      <key>KeepAlive</key>
      <true/>
      <key>UserName</key>
      <string>用户名/string>
      <key>GroupName</key>
      <string>群组名</string>
      <key>EnvironmentVariables</key>
      <dict>
      <key>PATH</key>
      <string>/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin</string>
      <key>SHELL</key>
      <string>/bin/bash</string>
      </dict>
      <key>ProgramArguments</key>
      <array>
      <string>/data/bitwarden_rs/bitwarden_rs</string>
      </array>
      <key>WorkingDirectory</key>
      <string>/data/bitwarden_rs</string>
      </dict>
      </plist>
    • 手动加载启动

      1
      sudo launchctl load /Library/LauchDaemons/bitwarden_rs.plist

配置HTTPS访问

运行bitwarden_rs以后会发现,必须要通过https访问才能进行真正的操作,可以采用Nginx配置https。

20210307150609.png

如果在MacOS中使用了Nginx,可以进行如下配置:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
# 将HTTP请求重定向为HTTPS请求
server {

if ($host = sub.example.com) {
return 301 https://$host$request_uri;
} # managed by Certbot
# 对外暴露的端口号
listen 8000;
server_name sub.example.com;
}

server {
listen 443 ssl http2;
# 设置域名
server_name sub.example.com;
# 设置证书
ssl_certificate /data/letsencrypt/live/sub.example.com/fullchain.pem; # managed by Certbot
ssl_certificate_key /data/letsencrypt/live/sub.example.com/privkey.pem; # managed by Certbot
ssl_dhparam /data/letsencrypt/dhparams.pem;
ssl_session_cache shared:SSL:10m;
ssl_session_timeout 5m;
add_header Alternate-Protocol 443:npn-spdy/3;
add_header Strict-Transport-Security "max-age=63072000; includeSubdomains; preload";
ssl_protocols TLSv1.2 TLSv1.3;
ssl_prefer_server_ciphers on;
ssl_ciphers 'TLS-CHACHA20-POLY1305-SHA256:TLS-AES-256-GCM-SHA384:TLS-AES-128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256';
ssl_early_data on;
ssl_ecdh_curve secp384r1;
server_tokens off;
add_header X-Content-Type-Options nosniff;
add_header X-XSS-Protection "1; mode=block";
add_header Referrer-Policy no-referrer-when-downgrade;
add_header X-Frame-Options "SAMEORIGIN" always;

ssl_stapling on;
ssl_stapling_verify on;

error_page 500 502 503 504 /50x.html;
location = /50x.html {
root /usr/local/opt/nginx/html;
}

location /robots.txt {
return 200 "User-agent: *\nDisallow: /";
}

location / {
# 修改为bitwarden web vault 静态资源的路径
root /data/bitwarden_rs/web-vault;
# 修改为bitwarden web vault的监听地址
proxy_pass http://10.0.1.2:9000;
client_max_body_size 100M; # Limit Document size to 100MB
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}

接下来就可以用前面配置的URL访问Bitwarden了。

locks.JPG

参考资料

  1. https://www.reddit.com/r/selfhosted/comments/fn1fsh/macos_tutorial_to_run_bitwarden_rs_with_optional/
  2. https://github.com/dinger1986/bitwardenrs_install_script/blob/master/install.sh
  3. https://github.com/dani-garcia/bitwarden_rs/wiki/Building-binary
  4. https://github.com/dani-garcia/bitwarden_rs/wiki/Enabling-HTTPS