diff --git a/etherpad/defaults/main.yml b/etherpad/defaults/main.yml
new file mode 100644
index 0000000000000000000000000000000000000000..bc8f5b041605529c98c7cd941493ee86dcf59359
--- /dev/null
+++ b/etherpad/defaults/main.yml
@@ -0,0 +1,17 @@
+---
+
+etherpad_web_root: "/opt/etherpad"
+etherpad_version: "HEAD"
+
+etherpads: []
+
+# etherpads:
+#   - name: identifier
+#     db_type: mysql
+#     db_name: etherpad
+#     db_user: etherpad
+#     db_password: {{…}}
+#     apikey: {{…}}
+#     edit_only: false
+#     require_auth: false
+#
diff --git a/etherpad/handlers/main.yml b/etherpad/handlers/main.yml
new file mode 100644
index 0000000000000000000000000000000000000000..c84b2bfa20581fb612cff843701ee5cc114a42c9
--- /dev/null
+++ b/etherpad/handlers/main.yml
@@ -0,0 +1,14 @@
+---
+
+- name: create tmpfiles
+  command: systemd-tmpfiles --create
+
+- name: reload systemd daemons
+  systemd:
+    daemon_reload: true
+
+- name: restart etherpad
+  debug:
+    var: item
+  when: item.changed
+  loop: etherpad_config.results
diff --git a/etherpad/tasks/main.yml b/etherpad/tasks/main.yml
new file mode 100644
index 0000000000000000000000000000000000000000..b060a0b391158ce4b896fbb77ce066efe4207b6e
--- /dev/null
+++ b/etherpad/tasks/main.yml
@@ -0,0 +1,121 @@
+---
+
+- name: ensure nodejs is installed
+  apt:
+    name:
+      - nodejs
+      - npm
+    state: present
+
+- name: ensure we have a group for etherpads
+  group:
+    name: etherpad
+    state: present
+    system: true
+
+- name: ensure we have a user for etherpads
+  user:
+    name: etherpad
+    group: etherpad
+    state: present
+    system: true
+    shell: /usr/bin/nologin
+    home: "{{etherpad_web_root}}"
+    createhome: false
+
+- name: ensure we have a directory for the etherpad software
+  file:
+    path: "{{etherpad_web_root}}/repository"
+    state: directory
+    owner: etherpad
+    group: etherpad
+    mode: 0755
+
+- name: ensure we have the etherpad software
+  git:
+    repo: https://github.com/ether/etherpad-lite.git
+    dest: "{{etherpad_web_root}}/repository"
+    version: "{{etherpad_version|default('HEAD')}}"
+  become: true
+  become_user: etherpad
+
+- name: ensure we have a directory for etherpad configuration files
+  file:
+    path: /etc/etherpad
+    state: directory
+    owner: root
+    group: etherpad
+    mode: 0750
+
+- name: ensure we have a mysql database for the etherpad
+  mysql_db:
+    name: "{{item.db_name}}"
+    state: present
+    login_user: root
+    login_password: "{{mysql_root_password}}"
+  with_items: "{{etherpads}}"
+  when: item.db_type == 'mysql'
+  no_log: true
+
+- name: ensure we have a mysql database user for the etherpad
+  mysql_user:
+    name: "{{item.db_user}}"
+    password: "{{item.db_password}}"
+    state: present
+    login_user: root
+    login_password: "{{mysql_root_password}}"
+    priv: "{{item.db_name}}.*:ALL"
+  with_items: "{{etherpads}}"
+  when: item.db_type == 'mysql'
+  no_log: true
+
+- name: ensure we have a settings file
+  template:
+    src: settings.json.j2
+    dest: "/etc/etherpad/{{item.name}}-settings.json"
+    owner: root
+    group: etherpad
+    mode: 0640
+  register: etherpad_config
+  with_items: "{{etherpads}}"
+  notify: restart etherpad
+  no_log: true
+
+- name: ensure we have a directory for the socket
+  template:
+    src: tmpfiles.conf.j2
+    dest: /etc/tmpfiles.d/10-etherpad.conf
+    owner: root
+    group: root
+    mode: '0644'
+  notify: create tmpfiles
+
+- name: ensure we have an apikey file
+  template:
+    src: apikey.txt.j2
+    dest: /etc/etherpad/{{item.name}}-apikey.txt
+    owner: root
+    group: etherpad
+    mode: 0640
+    force: false
+  with_items: "{{etherpads}}"
+  no_log: true
+
+- name: ensure we have a systemd unit
+  template:
+    src: etherpad@.service.j2
+    dest: /etc/systemd/system/etherpad@.service
+    owner: root
+    group: root
+    mode: 0644
+  notify: reload systemd daemons
+
+- meta: flush_handlers
+
+- name: make sure the unit is running
+  systemd:
+    name: "etherpad@{{item.name}}"
+    state: started
+    enabled: true
+  with_items: "{{etherpads}}"
+  no_log: true
diff --git a/etherpad/templates/apikey.txt.j2 b/etherpad/templates/apikey.txt.j2
new file mode 100644
index 0000000000000000000000000000000000000000..557d7ad400646826477df22ff35471abc106990f
--- /dev/null
+++ b/etherpad/templates/apikey.txt.j2
@@ -0,0 +1 @@
+{{item.apikey}}
diff --git a/etherpad/templates/etherpad@.service.j2 b/etherpad/templates/etherpad@.service.j2
new file mode 100644
index 0000000000000000000000000000000000000000..d51a802203a1ce4b4742171962cb674b03c4666f
--- /dev/null
+++ b/etherpad/templates/etherpad@.service.j2
@@ -0,0 +1,28 @@
+[Unit]
+Description=Etherpad Lite
+After=syslog.target network.target
+After=network-online.target mysql.service
+Wants=network-online.target mysql.service
+
+[Service]
+Type=simple
+User=etherpad
+Group=etherpad
+UMask=0002
+ExecStartPre={{etherpad_web_root}}/repository/bin/installDeps.sh
+ExecStart={{etherpad_web_root}}/repository/node_modules/ep_etherpad-lite/node/server.js --settings /etc/etherpad/%i-settings.json --apikey /etc/etherpad/%i-apikey.txt
+ExecStoPPost=rm -f /run/etherpad/%i.socket
+WorkingDirectory={{etherpad_web_root}}/repository
+Restart=on-failure
+RestartSec=3
+Environment="NODE_ENV=production"
+StandardError=syslog
+KillSignal=SIGINT
+PrivateDevices=yes
+PrivateTmp=yes
+ProtectSystem=full
+ProtectHome=yes
+NoNewPrivileges=yes
+
+[Install]
+WantedBy=multi-user.target
diff --git a/etherpad/templates/settings.json.j2 b/etherpad/templates/settings.json.j2
new file mode 100644
index 0000000000000000000000000000000000000000..7df90387fe2b9fa78e69d709cc0987160eb7daef
--- /dev/null
+++ b/etherpad/templates/settings.json.j2
@@ -0,0 +1,154 @@
+{
+  "title": "{{item.name}}",
+
+  "favicon": "favicon.ico",
+
+  "skinName": "colibris",
+
+  "skinVariants": "super-light-toolbar super-light-editor light-background",
+
+  "ip": "",
+  "port": "/run/etherpad/{{item.name}}.socket",
+
+  "showSettingsInAdminPage": true,
+
+  "dbType": "{{item.db_type}}",
+  "dbSettings": {
+    "user": "{{item.db_user}}",
+    "host": "localhost",
+    "port": 3306,
+    "password": "{{item.db_password}}",
+    "database": "{{item.name}}",
+    "charset": "utf8mb4"
+  },
+
+  "defaultPadText" : "Welcome to Etherpad!\n\nThis pad text is synchronized as you type, so that everyone viewing this page sees the same text. This allows you to collaborate seamlessly on documents!\n\nGet involved with Etherpad at https:\/\/etherpad.org\n",
+
+  "padOptions": {
+    "noColors":         false,
+    "showControls":     true,
+    "showChat":         true,
+    "showLineNumbers":  true,
+    "useMonospaceFont": false,
+    "userName":         false,
+    "userColor":        false,
+    "rtl":              false,
+    "alwaysShowChat":   false,
+    "chatAndUsers":     false,
+    "lang":             "en-gb"
+  },
+
+  "padShortcutEnabled" : {
+    "altF9":     true, /* focus on the File Menu and/or editbar */
+    "altC":      true, /* focus on the Chat window */
+    "cmdShift2": true, /* shows a gritter popup showing a line author */
+    "delete":    true,
+    "return":    true,
+    "esc":       true, /* in mozilla versions 14-19 avoid reconnecting pad */
+    "cmdS":      true, /* save a revision */
+    "tab":       true, /* indent */
+    "cmdZ":      true, /* undo/redo */
+    "cmdY":      true, /* redo */
+    "cmdI":      true, /* italic */
+    "cmdB":      true, /* bold */
+    "cmdU":      true, /* underline */
+    "cmd5":      true, /* strike through */
+    "cmdShiftL": true, /* unordered list */
+    "cmdShiftN": true, /* ordered list */
+    "cmdShift1": true, /* ordered list */
+    "cmdShiftC": true, /* clear authorship */
+    "cmdH":      true, /* backspace */
+    "ctrlHome":  true, /* scroll to top of pad */
+    "pageUp":    true,
+    "pageDown":  true
+  },
+
+  "suppressErrorsInPadText": false,
+
+  "requireSession": false,
+
+  "editOnly": {{item.edit_only|default(false)|lower}},
+
+  "sessionNoPassword": false,
+
+  "minify": true,
+
+  "maxAge": 21600, // 60 * 60 * 6 = 6 hours
+
+  "abiword": null,
+
+  "soffice": null,
+
+  "tidyHtml": null,
+
+  "allowUnknownFileEnds": true,
+
+  "requireAuthentication": {{item.require_auth|default(false)|lower}},
+
+  "requireAuthorization": false,
+
+  "trustProxy": true,
+
+  "disableIPlogging": false,
+
+  "automaticReconnectionTimeout": 0,
+
+  "scrollWhenFocusLineIsOutOfViewport": {
+
+    "percentage": {
+      "editionAboveViewport": 0,
+      "editionBelowViewport": 0
+    },
+
+    "duration": 0,
+
+    "scrollWhenCaretIsInTheLastLineOfViewport": false,
+
+    "percentageToScrollWhenUserPressesArrowUp": 0
+  },
+
+  "loadTest": false,
+
+  "importExportRateLimiting": {
+    // duration of the rate limit window (milliseconds)
+    "windowMs": 900,
+
+    // maximum number of requests per IP to allow during the rate limit window
+    "max": 100
+  },
+
+  "importMaxFileSize": 52428800, // 50 * 1024 * 1024
+
+  "exposeVersion": false,
+
+  /*
+   * The log level we are using.
+   *
+   * Valid values: DEBUG, INFO, WARN, ERROR
+   */
+  "loglevel": "INFO",
+
+  /*
+   * Logging configuration. See log4js documentation for further information:
+   * https://github.com/nomiddlename/log4js-node
+   *
+   * You can add as many appenders as you want here.
+   */
+  "logconfig" :
+    { "appenders": [
+        { "type": "console"
+        //, "category": "access"// only logs pad access
+        }
+
+      /*
+      , { "type": "file"
+      , "filename": "your-log-file-here.log"
+      , "maxLogSize": 1024
+      , "backups": 3 // how many log files there're gonna be at max
+      //, "category": "test" // only log a specific category
+        }
+      */
+
+      ]
+    } // logconfig
+}
diff --git a/etherpad/templates/tmpfiles.conf.j2 b/etherpad/templates/tmpfiles.conf.j2
new file mode 100644
index 0000000000000000000000000000000000000000..2dce14b7a620d88704d83d65614c1a386edababa
--- /dev/null
+++ b/etherpad/templates/tmpfiles.conf.j2
@@ -0,0 +1 @@
+d /run/etherpad 2775 etherpad nginx-proxy - -