Compare commits

..
5 changed files with 44 additions and 56 deletions

No files matched your search

+9 -7
View File
@@ -1,22 +1,24 @@
# Since .env is gitignored, you can use .env.example to build a new `.env` file when you clone the repo. # Since .env is gitignored, you can use .env.example to build a new `.env` file when you clone the repo.
# Keep this file up-to-date when you add new variables to \`.env\`. # Keep this file up-to-date when you add new variables to `.env`.
# This file will be committed to version control, so make sure not to have any secrets in it. # This file will be committed to version control, so make sure not to have any secrets in it.
# If you are cloning this repo, create a copy of this file named `.env` and populate it with your secrets. # If you are cloning this repo, create a copy of this file named `.env` and populate it with your secrets.
# The below secret is not used anywhere but required for Auth.js (Would encrypt JWTs and Mail hashes, both not used) # Generate two different 64-character hex values with `openssl rand -hex 32` before starting Homarr.
AUTH_SECRET="supersecret" # Never reuse these values or commit the populated `.env` file.
AUTH_SECRET=
# The below secret is used to encrypt integration secrets in the database. # The below secret is used to encrypt integration secrets in the database.
# It should be a 32-byte string, generated by running `openssl rand -hex 32` on Unix # Homarr will reject an empty or invalid value and print a randomly generated candidate.
# or starting the project without any (which will show a randomly generated one). SECRET_ENCRYPTION_KEY=
SECRET_ENCRYPTION_KEY=0000000000000000000000000000000000000000000000000000000000000000
LOG_LEVEL='info' LOG_LEVEL='info'
# This is how you can use the sqlite driver: # This is how you can use the sqlite driver:
DB_DRIVER='better-sqlite3' DB_DRIVER='better-sqlite3'
DB_URL='FULL_PATH_TO_YOUR_SQLITE_DB_FILE' # Safe local source-development path. SQLite files are ignored by Git.
# Container images use /appdata/db/db.sqlite by default instead.
DB_URL='./db.sqlite'
# Those are the two ways to use the mysql2 driver: # Those are the two ways to use the mysql2 driver:
# 1. Using the URL format: # 1. Using the URL format:
@@ -244,18 +244,21 @@ Homarr supports multiple authentication options, from internal userbase (credent
- Create a group (e.g., `homarr-admins`) and assign users who require admin access. - Create a group (e.g., `homarr-admins`) and assign users who require admin access.
**2. Example .env file:** **2. Example .env file:**
Generate `SECRET_ENCRYPTION_KEY` with `openssl rand -hex 32`; do not copy an example key between installs.
```env ```env
OIDC_CLIENT_ID=identificationid #OIDC client ID OIDC_CLIENT_ID=<REPLACE_WITH_OIDC_CLIENT_ID>
OIDC_CLIENT_SECRET=secretsecretsecret #OIDC client secret OIDC_CLIENT_SECRET=<REPLACE_WITH_OIDC_CLIENT_SECRET>
OIDC_SLUG=homarr #Application slug in Authentik OIDC_SLUG=homarr #Application slug in Authentik
AUTH_DOMAIN=auth.example.com #Authentik FQDN AUTH_DOMAIN=auth.example.com #Authentik FQDN
ADMIN_GROUP=homarr-admins #Authentik group for Homarr admins ADMIN_GROUP=homarr-admins #Authentik group for Homarr admins
HOMARR_FQDN=homarr.example.com #Homarr FQDN HOMARR_FQDN=homarr.example.com #Homarr FQDN
SECRET_ENCRYPTION_KEY=encryptencryptencrypt #Homarr encryption key SECRET_ENCRYPTION_KEY=<REPLACE_WITH_64_HEX_CHARACTERS>
``` ```
**3. Example Docker Compose configuration:** **3. Example Docker Compose configuration:**
```yaml {14-26} ```yaml {14-24}
services: services:
homarr: homarr:
image: ghcr.io/homarr-labs/homarr:latest image: ghcr.io/homarr-labs/homarr:latest
@@ -269,8 +272,6 @@ Homarr supports multiple authentication options, from internal userbase (credent
environment: environment:
- TZ=America/Los_Angeles - TZ=America/Los_Angeles
- SECRET_ENCRYPTION_KEY=${SECRET_ENCRYPTION_KEY} - SECRET_ENCRYPTION_KEY=${SECRET_ENCRYPTION_KEY}
- BASE_URL=https://${HOMARR_FQDN}
- NEXTAUTH_URL=https://${HOMARR_FQDN}
- AUTH_PROVIDERS=oidc #(optional: include ',credentials' to keep local accounts as fallback) - AUTH_PROVIDERS=oidc #(optional: include ',credentials' to keep local accounts as fallback)
- AUTH_OIDC_CLIENT_ID=${OIDC_CLIENT_ID} - AUTH_OIDC_CLIENT_ID=${OIDC_CLIENT_ID}
- AUTH_OIDC_CLIENT_SECRET=${OIDC_CLIENT_SECRET} - AUTH_OIDC_CLIENT_SECRET=${OIDC_CLIENT_SECRET}
@@ -322,15 +323,18 @@ Homarr supports multiple authentication options, from internal userbase (credent
- Record the `Client-ID` and `Client Key` (secret). - Record the `Client-ID` and `Client Key` (secret).
**2. Example .env file (Homarr):** **2. Example .env file (Homarr):**
Generate `SECRET_ENCRYPTION_KEY` with `openssl rand -hex 32`; do not copy an example key between installs.
```env ```env
OIDC_CLIENT_ID=identificationid #Google Client-ID OIDC_CLIENT_ID=<REPLACE_WITH_GOOGLE_CLIENT_ID>
OIDC_CLIENT_SECRET=secretsecretsecret #Google Client Key (secret) OIDC_CLIENT_SECRET=<REPLACE_WITH_GOOGLE_CLIENT_SECRET>
HOMARR_FQDN=homarr.example.com #Homarr FQDN HOMARR_FQDN=homarr.example.com #Homarr FQDN
SECRET_ENCRYPTION_KEY=encryptencryptencrypt #Homarr encryption key SECRET_ENCRYPTION_KEY=<REPLACE_WITH_64_HEX_CHARACTERS>
``` ```
**3. Example Docker Compose configuration (Homarr):** **3. Example Docker Compose configuration (Homarr):**
```yaml {16-22} ```yaml {14-20}
services: services:
homarr: homarr:
image: ghcr.io/homarr-labs/homarr:latest image: ghcr.io/homarr-labs/homarr:latest
@@ -344,8 +348,6 @@ Homarr supports multiple authentication options, from internal userbase (credent
environment: environment:
- TZ=Europe/Berlin - TZ=Europe/Berlin
- SECRET_ENCRYPTION_KEY=${SECRET_ENCRYPTION_KEY} - SECRET_ENCRYPTION_KEY=${SECRET_ENCRYPTION_KEY}
- BASE_URL=https://${HOMARR_FQDN}
- NEXTAUTH_URL=https://${HOMARR_FQDN}
- AUTH_PROVIDERS=oidc #(optional: include ',credentials' to keep local accounts as fallback) - AUTH_PROVIDERS=oidc #(optional: include ',credentials' to keep local accounts as fallback)
- AUTH_OIDC_CLIENT_ID=${OIDC_CLIENT_ID} - AUTH_OIDC_CLIENT_ID=${OIDC_CLIENT_ID}
- AUTH_OIDC_CLIENT_SECRET=${OIDC_CLIENT_SECRET} - AUTH_OIDC_CLIENT_SECRET=${OIDC_CLIENT_SECRET}
@@ -38,13 +38,14 @@ This method is only useful, when you want to develop on Homarr or extend it with
Install all dependencies using <code>pnpm install</code> Install all dependencies using <code>pnpm install</code>
</li> </li>
<li> <li>
Copy the `.env.example` file to `.env` and replace `DB_URL` with the full path you want to use for the sqlite Copy the `.env.example` file to `.env`. Its `DB_URL='./db.sqlite'` value is ready for local use and stores the
database file. For example `DB_URL='/home/username/homarr/db.sqlite` database in the cloned repository. Replace it with an absolute writable path such as
`DB_URL='/home/username/homarr/db.sqlite'` if you want to store the database elsewhere.
</li> </li>
<li> <li>
Replace `AUTH_SECRET` and `SECRET_ENCRYPTION_KEY` both with a secure random string by using `openssl rand -hex 32` Run `openssl rand -hex 32` twice and set `AUTH_SECRET` and `SECRET_ENCRYPTION_KEY` to the two different generated
values. Keep both values secret and preserve `SECRET_ENCRYPTION_KEY` with your backups.
</li> </li>
<li>Replace `CRON_JOB_API_KEY` with a secure random string by using `openssl rand -base64 32`</li>
<li>Run `pnpm run db:migration:sqlite:run` and wait that it completes</li> <li>Run `pnpm run db:migration:sqlite:run` and wait that it completes</li>
<li>Build the source using `pnpm build`</li> <li>Build the source using `pnpm build`</li>
<li> <li>
+8 -8
View File
@@ -74,7 +74,7 @@
</a> </a>
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/archiveteam-warrior" target="_blank" rel="noreferrer noopener"> <a href="null" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/selfhst/icons/png/archiveteam-warrior.png" alt="ArchiveTeam Warrior" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/selfhst/icons/png/archiveteam-warrior.png" alt="ArchiveTeam Warrior" width="90" height="90" />
<br/> <br/>
<p align="center">ArchiveTeam<br/>Warrior</p> <p align="center">ArchiveTeam<br/>Warrior</p>
@@ -88,7 +88,7 @@
</a> </a>
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/audiobookshelf" target="_blank" rel="noreferrer noopener"> <a href="null" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/audiobookshelf.svg" alt="Audiobookshelf" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/audiobookshelf.svg" alt="Audiobookshelf" width="90" height="90" />
<br/> <br/>
<p align="center">Audiobookshelf</p> <p align="center">Audiobookshelf</p>
@@ -137,7 +137,7 @@
</a> </a>
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/glances" target="_blank" rel="noreferrer noopener"> <a href="null" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/glances.svg" alt="Glances" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/glances.svg" alt="Glances" width="90" height="90" />
<br/> <br/>
<p align="center">Glances</p> <p align="center">Glances</p>
@@ -200,7 +200,7 @@
</a> </a>
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/navidrome" target="_blank" rel="noreferrer noopener"> <a href="null" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/navidrome.svg" alt="Navidrome" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/navidrome.svg" alt="Navidrome" width="90" height="90" />
<br/> <br/>
<p align="center">Navidrome</p> <p align="center">Navidrome</p>
@@ -249,7 +249,7 @@
</a> </a>
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/paperless-ngx" target="_blank" rel="noreferrer noopener"> <a href="null" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/paperless-ngx.svg" alt="Paperless-ngx" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/paperless-ngx.svg" alt="Paperless-ngx" width="90" height="90" />
<br/> <br/>
<p align="center">Paperless-ngx</p> <p align="center">Paperless-ngx</p>
@@ -263,7 +263,7 @@
</a> </a>
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/peanut" target="_blank" rel="noreferrer noopener"> <a href="null" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/peanut.svg" alt="PeaNUT" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/peanut.svg" alt="PeaNUT" width="90" height="90" />
<br/> <br/>
<p align="center">PeaNUT</p> <p align="center">PeaNUT</p>
@@ -313,7 +313,7 @@
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/readarr" target="_blank" rel="noreferrer noopener"> <a href="https://homarr.dev/docs/integrations/readarr" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@main/png/readarr.png" alt="Readarr" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/readarr.svg" alt="Readarr" width="90" height="90" />
<br/> <br/>
<p align="center">Readarr</p> <p align="center">Readarr</p>
</a> </a>
@@ -424,7 +424,7 @@
</a> </a>
</td> </td>
<td align="center"> <td align="center">
<a href="https://homarr.dev/docs/integrations/uptime-kuma" target="_blank" rel="noreferrer noopener"> <a href="null" target="_blank" rel="noreferrer noopener">
<img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/uptime-kuma.svg" alt="Uptime Kuma" width="90" height="90" /> <img src="https://cdn.jsdelivr.net/gh/homarr-labs/dashboard-icons@master/svg/uptime-kuma.svg" alt="Uptime Kuma" width="90" height="90" />
<br/> <br/>
<p align="center">Uptime<br/>Kuma</p> <p align="center">Uptime<br/>Kuma</p>
+8 -25
View File
@@ -1,9 +1,5 @@
import { readFile, writeFile } from "fs/promises"; import { readFile, writeFile } from "fs/promises";
import { import { integrationDefs } from "../packages/definitions/src/integration";
getIntegrationDocumentationUrl,
integrationDefs,
integrationKinds,
} from "../packages/definitions/src/integration";
const FILE = "docs/README.md"; const FILE = "docs/README.md";
const MAX_COLUMNS_PER_ROW = 7; const MAX_COLUMNS_PER_ROW = 7;
@@ -25,29 +21,19 @@ async function updateIntegrationList() {
} }
// Generate the new integration list // Generate the new integration list
const integrations = integrationKinds const integrations = Object.values(integrationDefs)
.filter((kind) => kind !== "mock") .filter((def) => def.name !== "Mock")
.map((kind) => ({ .sort((a, b) => a.name.localeCompare(b.name));
...integrationDefs[kind],
documentationUrl: getIntegrationDocumentationUrl(kind),
}))
.toSorted((a, b) => a.name.localeCompare(b.name));
const tableRows: string[] = []; const tableRows: string[] = [];
let currentRow: string[] = []; let currentRow: string[] = [];
integrations.forEach((integration) => { integrations.forEach((integration) => {
const cellBody = ` currentRow.push(`<td align="center">
<a href="${integration.documentationUrl}" target="_blank" rel="noreferrer noopener">
<img src="${integration.iconUrl}" alt="${integration.name}" width="90" height="90" /> <img src="${integration.iconUrl}" alt="${integration.name}" width="90" height="90" />
<br/> <br/>
<p align="center">${integration.name.replaceAll(" ", "<br/>")}</p> <p align="center">${integration.name.replaceAll(" ", "<br/>")}</p>
`; </a>
let cellContent = `<div>${cellBody}</div>`;
if (integration.documentationUrl !== null) {
cellContent = `<a href="${integration.documentationUrl}" target="_blank" rel="noreferrer noopener">${cellBody}</a>`;
}
currentRow.push(`<td align="center">
${cellContent}
</td>`); </td>`);
if (currentRow.length === MAX_COLUMNS_PER_ROW) { if (currentRow.length === MAX_COLUMNS_PER_ROW) {
@@ -81,7 +67,4 @@ ${endMarker}`;
await writeFile(FILE, newContent, "utf8"); await writeFile(FILE, newContent, "utf8");
} }
updateIntegrationList().catch((error: unknown) => { updateIntegrationList().catch(console.error);
console.error(error);
process.exitCode = 1;
});