[Plausible Community Edition (or CE for short)](https://plausible.io/blog/community-edition) is designed to be self-hosted through [Docker.](https://docs.docker.com/guides/get-started/) You don't have to be a Docker expert to launch your own instance, but you should have a basic understanding of the command-line and networking to successfully set it up.
The only thing you need to install Plausible CE is a server with Docker. The server must have a CPU with x86_64 or arm64 architecture and support for SSE 4.2 or equivalent NEON instructions. We recommend using a minimum of 4GB of RAM but the requirements will depend on your site traffic.
We've tested this on [Digital Ocean](https://m.do.co/c/91569eca0213) (affiliate link) but any hosting provider works. If your server doesn't come with Docker pre-installed, you can follow [their docs](https://docs.docker.com/get-docker/) to install it.
To make your Plausible CE instance accessible on a (sub)domain, you also need to be able to edit your DNS. Plausible CE isn't currently designed for subfolder installations.
To get started quickly, clone the [plausible/community-edition](https://github.com/plausible/community-edition) repo. It has everything you need to boot up your own Plausible CE server.
- [docker-compose.yml](./docker-compose.yml) — installs and orchestrates networking between your Plausible CE server, Postgres database, and Clickhouse database for stats.
If you're **opting out** of a reverse proxy and HTTPS, you'll need to adjust the Plausible service [configuration](./docker-compose.yml#L38) to ensure it's not limited to localhost (127.0.0.1). This change allows the service to be accessible from any network interface:
It takes some time to start PostgreSQL and ClickHouse, create the databases, and run the migrations. After about fifteen seconds you should be able to access your instance at the base URL and see the registration screen for the admin user.
> If something feels off, make sure to check out the logs with <kbd>docker compose logs</kbd> and start a [GitHub discussion.](https://github.com/plausible/analytics/discussions/categories/self-hosted-support)
Each new [release](https://github.com/plausible/analytics/releases) contains information on how to upgrade to it from the previous version. This section outlines the general steps and explains the versioning.
You can find available Plausible versions on [Github packages.](https://github.com/plausible/analytics/pkgs/container/community-edition) The default `latest` tag refers to the latest stable release tag. You can also pin your version:
None of the functionality is backported to older versions. If you wish to get the latest bug fixes and security updates you need to upgrade to a newer version.
New versions are published on [the releases page](https://github.com/plausible/analytics/releases) and their changes are documented in our [Changelog.](https://github.com/plausible/analytics/blob/master/CHANGELOG.md) Please note that database schema changes require running migrations when you're upgrading. However, we consider the schema as an internal API and therefore schema changes aren't considered a breaking change.
Changes in major versions would involve performing a data migration (e.g. [v2.0.0](https://github.com/plausible/analytics/releases/tag/v2.0.0)) or some other extra step.
Plausible is configured with environment variables, by default supplied via [plausible-conf.env](./plausible-conf.env) [env_file.](./docker-compose.yml#L38-L39)
> [!WARNING]
> Note that if you start a container with one set of ENV vars and then update the ENV vars and restart the container, they won't take effect due to the immutable nature of the containers. The container needs to be **recreated.**
Configures the secret used for sessions in the dashboard, doesn't have any defaults and needs to be provided in the ENV vars, can be generated with OpenSSL:
Configures the secret used for encrypting TOTP secrets at rest using AES256-GCM, doesn't have any defaults and needs to be provided in the ENV vars, can be generated with OpenSSL:
Restricts registration of new users. Possible values are `true` (full restriction), `false` (no restriction), and `invite_only` (only the invited users can register).
When enabled, new users need to verify their email addressby following a link delivered to their mailbox. Please configure your server for SMTP to receive this email. You can find Plausible's SMTP configuration options under [below.](#email)
> It is recommended to have all servers run on UTC time.
> If you do not run all servers on UTC time you can lose data based on your UTC offsite, e.g. if your UTC zone is +10 you will not receive analytics for a new site for 10 hours.
Plausible CE uses the country database created by [db-ip](https://db-ip.com/) for enriching analytics data with visitor countries. The database is shipped within the container image and country data collection happens automatically.
Optionally, you can provide a different database. For example, you can use [MaxMind](https://www.maxmind.com) services and enable city-level geolocation:
This database is used to lookup GeoName IDs for IP addresses. If not set, defaults to the [file](https://github.com/plausible/analytics/blob/v2.0.0/Dockerfile#L47) shipped within the container image.
This file is used to turn GeoName IDs into human readable strings for display on the dashboard. Defaults to the one shipped within the container image.
---
#### MAXMIND_LICENSE_KEY
If set, this ENV variable takes precedence over [IP_GEOLOCATION_DB](#ip_geolocation_db) and makes Plausible download (and keep up to date) a free MaxMind GeoLite2 MMDB of the selected edition. [See below](#maxmind-integration) for integration instructions.
---
#### MAXMIND_EDITION
Default: `GeoLite2-City`
MaxMind database edition to use (only if [MAXMIND_LICENSE_KEY](#maxmind_license_key) is set)
### Email
Plausible CE sends transactional emails e.g. account activation, password reset. In addition, it sends non-transactional emails like weekly or monthly reports.
It uses SMTP with an optional [relay](#smtp_host_addr) by default. Alternatively, you can use other [services](https://hexdocs.pm/bamboo/readme.html#available-adapters) such as Postmark, Mailgun, Mandrill or Send Grid to send emails.
[Here's](https://gist.github.com/ruslandoga/c94ce526231fb77930132aaeda3fc3c9) a short guide on using your Gmail account for email delivery.
Instead of the default, you can replace this with <kbd>Bamboo.PostmarkAdapter</kbd>, <kbd>Bamboo.MailgunAdapter</kbd>, <kbd>Bamboo.MandrillAdapter</kbd> or <kbd>Bamboo.SendGridAdapter</kbd> and add the appropriate variables.
Please try the new SMTP client introduced in [v2.1.0](https://github.com/plausible/analytics/discussions/4125) by setting MAILER_ADAPTER to `Bamboo.Mua`. All the `SMTP_*` environment variables can stay the same.
The email id to use for as _from_ address of all communications from Plausible.
#### MAILER_NAME
The display name for the sender (_from_).
---
#### SMTP_HOST_ADDR
The host address of your SMTP relay.
#### SMTP_HOST_PORT
Default: `25`
The port of your SMTP relay.
#### SMTP_USER_NAME
The username/email in case SMTP auth is required on your SMTP relay.
#### SMTP_USER_PWD
The password in case SMTP auth is required on your SMTP relay.
#### SMTP_HOST_SSL_ENABLED
Default: `false`
Configures whether SMTPS (SMTP over SSL) is enabled for SMTP connection, e.g. when you use port 465.
#### SMTP_RETRIES
Default: `2`
Number of retries to make until mailer gives up.
---
#### POSTMARK_API_KEY
Enter your Postmark API key.
> [!NOTE]
> You also have to set the [MAILER_EMAIL](#mailer_email) variable which needs to be configured in PostmarkApps sender signatures.
---
#### MAILGUN_API_KEY
Enter your Mailgun API key.
#### MAILGUN_DOMAIN
Enter your Mailgun domain.
#### MAILGUN_BASE_URI
Default: `https://api.mailgun.net/v3`
Mailgun makes a difference in the API base URL between sender domains from within the EU and outside. By default, the base URL is set to <kbd>https://api.mailgun.net/v3</kbd>. To override this you can pass <kbd>https://api.eu.mailgun.net/v3</kbd> if you are using an EU domain.
Go to [Google Cloud console,](http://console.cloud.google.com/) for example, by clicking <kbd>Go to console</kbd> on [Google Cloud landing page.](https://cloud.google.com) If Google asks you to register, just do it.
<imgsrc="./images/0-google-cloud.png">
Once there, select a project that you want to use for Plausible OAuth app.
<imgsrc="./images/1-project-select.png">
If you don't have a project already, or if you want to isolate Plausible from all your other Google Cloud things, you should create a new project.
---
<details><summary>Here's how to create a new Google Cloud project</summary>
In the <kbd>Select a project</kbd> pop-up, click <kbd>New project</kbd>
<imgsrc="./images/1-project-new.png">
Pick a descriptive name. Organizations don't matter.
<imgsrc="./images/1-project-create.png">
Once the project is created, select it and make sure all the other steps happen within that project. Google is tricky and sometimes switches you to a "default" project.
<imgsrc="./images/1-project-created.png">
And just like that, you have a new Google Cloud project! Please do make sure it stays selected.
</details>
---
#### Register an OAuth application for a domain
Search for <kbd>APIs & Services</kbd> or something like that.
Copy these to your [<kbd>plausible-conf.env</kbd>](./plausible-conf.env) and make sure to recreate the `plausible` container since the ENV vars provided on startup get "baked in"
> You can omit <kbd>-f docker-compose.yml -f reverse-proxy/docker-compose.caddy-gen.yml</kbd> if you are not using Caddy
#### Verify the chosen domain on Google Search console
Did you notice that during OAuth application registratation there was a note about Authorized URLs saying that they need to be verified? Nevermind, we are doing it now.
Once there, either ensure that you've already verified your domain by checking the properties in the <kbd>Select property</kbd> dropdown on the left or pick one of the two ways to verify it. I only have screenshots for the "Domain" type so that's what I'm picking.
<imgsrc="./images/4-search-console-new.png">
Whichever you pick, just follow the instruction in the pop-up, they are good.
<imgsrc="./images/4-search-console-verify.png">
Success looks like this.
<imgsrc="./images/4-search-console-verified.png">
With that, you are ready to integrate Plausible with Google Search and import Universal Analytics data. You can do both, neither, and anything in between.
### Integrate with Google Search
#### Enable APIs for Google Search integration
Go back to [Google Cloud,](https://console.cloud.google.com) ensure you have the correct project selected, and search for <kbd>Google Search Console API</kbd>
Go to the site settings on your Plausible dashboard.
<imgsrc="./images/6-plausible-settings-pick.png">
In the settings select <kbd>Search Console</kbd> and press <kbd>Continue with Google</kbd>
> If you see a warning instead, that means you haven't set the <kbd>GOOGLE_CLIENT_ID</kbd> and <kbd>GOOGLE_CLIENT_SECRET</kbd> environment variables [correctly.](#issue-an-oauth-client-and-key-for-that-application)
And now we should be able to drilldown into Google search terms like on [plausible.io](https://plausible.io/plausible.io/referrers/Google?source=Google)
### Import historical data from Universal Analytics
#### Enable APIs for exports on Google Cloud
Go back to [Google Cloud,](https://console.cloud.google.com) ensure you have the correct project selected, and search for <kbd>Google Analytics API</kbd>
<imgsrc="./images/7-analytics-api-search.png">
Enable it.
<imgsrc="./images/7-analytics-api-enable.png">
Next search for <kbd>Google Analytics Reporting API</kbd>
In the <kbd>General</kbd> settings section scroll down to <kbd>Data Import from Google Analytics</kbd> and press <kbd>Continue with Google</kbd> button.
> If you see a warning instead, that means you haven't set the <kbd>GOOGLE_CLIENT_ID</kbd> and <kbd>GOOGLE_CLIENT_SECRET</kbd> environment variables [correctly.](#issue-an-oauth-client-and-key-for-that-application)
<imgsrc="./images/6-data-import.png">
Choose the account that you added as the test user.
To use MaxMind you need to create an account [here.](https://www.maxmind.com/en/geolite2/signup) Once you have your account details, you can add [MAXMIND_LICENSE_KEY](#maxmind_license_key) and [MAXMIND_EDITION](#maxmind_edition) environmental valiables to your [plausible-conf.env](./plausible-conf.env) and the databases would be automatically downloaded and kept up to date. Note that using city-level databases like MaxMind's GeoLite2-City requires ~1GB more RAM.