Compare commits

...

4 Commits

8 changed files with 103 additions and 66 deletions

View File

@ -212,7 +212,7 @@ moodle_user_name: "{{administrator_username}}"
moodle_user_email: "{{administrator_email}}" moodle_user_email: "{{administrator_email}}"
#### Nextcloud #### Nextcloud
nextcloud_version: "production" # Danger: Nextcloud can't skipp major version updates. nextcloud_version: "production" # @see https://nextcloud.com/blog/nextcloud-release-channels-and-how-to-track-them/
#### Peertube #### Peertube
peertube_version: "bookworm" peertube_version: "bookworm"

View File

@ -15,6 +15,7 @@ This guide provides instructions for setting up, operating, and maintaining the
- [Testing](#testing) - [Testing](#testing)
- [Updates](#updates) - [Updates](#updates)
- [To-Do](#to-do) - [To-Do](#to-do)
- [Spam Issues][#spam-issues]
- [References](#references) - [References](#references)
## Setup ## Setup
@ -122,6 +123,25 @@ Use the following tools for testing:
For instructions on updating your Mailu setup, follow the official [Mailu maintenance guide](https://mailu.io/master/maintain.html). For instructions on updating your Mailu setup, follow the official [Mailu maintenance guide](https://mailu.io/master/maintain.html).
## Spam Issues
### Inspect
To inspect use:
- [Google Postmaster](https://postmaster.google.com/)
- [Yahoo Postmaster](https://postmaster.yahooinc.com)
### Blacklisted
It may be that your domain is blacklisted. In this case check out:
- [Spamhaus](https://check.spamhaus.org/)
- [Barracuda](https://www.barracudacentral.org/lookups)
### Reset
- [Cloudmark](https://csi.cloudmark.com/en/reset/)
## To-Do ## To-Do
- Implement two-factor authentication in Roundcube Webmail. More information can be found [here](https://blog.kuepper.nrw/2019/03/30/roundcube-webmail-mit-zwei-faktor-authentifizierung/). - Implement two-factor authentication in Roundcube Webmail. More information can be found [here](https://blog.kuepper.nrw/2019/03/30/roundcube-webmail-mit-zwei-faktor-authentifizierung/).

View File

@ -96,9 +96,17 @@
dest: "{{docker_compose_instance_directory}}docker-compose.yml" dest: "{{docker_compose_instance_directory}}docker-compose.yml"
notify: docker compose project setup notify: docker compose project setup
# Pull image when update is wished.
# @todo This should be moved to update-docker
- name: docker compose pull
command:
cmd: docker-compose -p "{{docker_compose_project_name}}" pull
chdir: "{{docker_compose_instance_directory}}"
when: mode_update | bool
- name: docker compose project setup - name: docker compose project setup
command: command:
cmd: docker-compose -p "{{docker_compose_project_name}}" up -d --force-recreate cmd: docker-compose -p "{{docker_compose_project_name}}" up -d
chdir: "{{docker_compose_instance_directory}}" chdir: "{{docker_compose_instance_directory}}"
environment: environment:
COMPOSE_HTTP_TIMEOUT: 600 COMPOSE_HTTP_TIMEOUT: 600

View File

@ -61,49 +61,50 @@ services:
retries: 3 retries: 3
{% include 'templates/docker/container/networks.yml.j2' %} {% include 'templates/docker/container/networks.yml.j2' %}
{% endfor %} {% endfor %}
# Deactivated chatgpt.
matrix-chatgpt-bot: # @todo needs to be reactivated as soon as bug is found
restart: {{docker_restart_policy}} # matrix-chatgpt-bot:
container_name: matrix-chatgpt # restart: {{docker_restart_policy}}
image: ghcr.io/matrixgpt/matrix-chatgpt-bot:latest # container_name: matrix-chatgpt
volumes: # image: ghcr.io/matrixgpt/matrix-chatgpt-bot:latest
- chatgpt_data:/storage # volumes:
environment: # - chatgpt_data:/storage
OPENAI_API_KEY: '{{matrix_chatgpt_bridge_openai_api_key}}' # environment:
# Uncomment the next two lines if you are using Azure OpenAI API # OPENAI_API_KEY: '{{matrix_chatgpt_bridge_openai_api_key}}'
# OPENAI_AZURE: 'false' # # Uncomment the next two lines if you are using Azure OpenAI API
# CHATGPT_REVERSE_PROXY: 'your-completion-endpoint-here' # # OPENAI_AZURE: 'false'
CHATGPT_CONTEXT: 'thread' # # CHATGPT_REVERSE_PROXY: 'your-completion-endpoint-here'
CHATGPT_API_MODEL: 'gpt-3.5-turbo' # CHATGPT_CONTEXT: 'thread'
# Uncomment and edit the next line if needed # CHATGPT_API_MODEL: 'gpt-3.5-turbo'
# CHATGPT_PROMPT_PREFIX: 'Instructions:\nYou are ChatGPT, a large language model trained by OpenAI.' # # Uncomment and edit the next line if needed
# CHATGPT_IGNORE_MEDIA: 'false' # # CHATGPT_PROMPT_PREFIX: 'Instructions:\nYou are ChatGPT, a large language model trained by OpenAI.'
CHATGPT_REVERSE_PROXY: 'https://api.openai.com/v1/chat/completions' # # CHATGPT_IGNORE_MEDIA: 'false'
# Uncomment and edit the next line if needed # CHATGPT_REVERSE_PROXY: 'https://api.openai.com/v1/chat/completions'
# CHATGPT_TEMPERATURE: '0.8' # # Uncomment and edit the next line if needed
# Uncomment and edit the next line if needed # # CHATGPT_TEMPERATURE: '0.8'
# CHATGPT_MAX_CONTEXT_TOKENS: '4097' # # Uncomment and edit the next line if needed
# CHATGPT_MAX_PROMPT_TOKENS: '3097' # #CHATGPT_MAX_CONTEXT_TOKENS: '4097'
KEYV_BACKEND: 'file' # CHATGPT_MAX_PROMPT_TOKENS: '3000'
KEYV_URL: '' # KEYV_BACKEND: 'file'
KEYV_BOT_ENCRYPTION: 'false' # KEYV_URL: ''
KEYV_BOT_STORAGE: 'true' # KEYV_BOT_ENCRYPTION: 'false'
MATRIX_HOMESERVER_URL: 'https://{{synapse_domain}}' # KEYV_BOT_STORAGE: 'true'
MATRIX_BOT_USERNAME: '@chatgptbot:{{matrix_server_name}}' # MATRIX_HOMESERVER_URL: 'https://{{synapse_domain}}'
MATRIX_ACCESS_TOKEN: '{{ matrix_chatgpt_bridge_access_token | default('') }}' # MATRIX_BOT_USERNAME: '@chatgptbot:{{matrix_server_name}}'
MATRIX_BOT_PASSWORD: '{{matrix_chatgpt_bridge_user_password}}' # MATRIX_ACCESS_TOKEN: '{{ matrix_chatgpt_bridge_access_token | default('') }}'
MATRIX_DEFAULT_PREFIX: '!chatgpt' # MATRIX_BOT_PASSWORD: '{{matrix_chatgpt_bridge_user_password}}'
MATRIX_DEFAULT_PREFIX_REPLY: 'false' # MATRIX_DEFAULT_PREFIX: '!chatgpt'
#MATRIX_BLACKLIST: '' # MATRIX_DEFAULT_PREFIX_REPLY: 'false'
MATRIX_WHITELIST: ':{{matrix_server_name}}' # #MATRIX_BLACKLIST: ''
MATRIX_AUTOJOIN: 'true' # MATRIX_WHITELIST: ':{{matrix_server_name}}'
MATRIX_ENCRYPTION: 'true' # MATRIX_AUTOJOIN: 'true'
MATRIX_THREADS: 'true' # MATRIX_ENCRYPTION: 'true'
MATRIX_PREFIX_DM: 'false' # MATRIX_THREADS: 'true'
MATRIX_RICH_TEXT: 'true' # MATRIX_PREFIX_DM: 'false'
# MATRIX_RICH_TEXT: 'true'
{% include 'templates/docker/compose/volumes.yml.j2' %} {% include 'templates/docker/compose/volumes.yml.j2' %}
synapse_data: synapse_data:
chatgpt_data: # chatgpt_data:
{% include 'templates/docker/compose/networks.yml.j2' %} {% include 'templates/docker/compose/networks.yml.j2' %}

View File

@ -21,10 +21,12 @@ bridges:
database_name: "mautrix_signal_bridge" database_name: "mautrix_signal_bridge"
bridge_name: "signal" bridge_name: "signal"
- database_password: "{{ mautrix_slack_bridge_database_password }}" # Deactivated temporary, due to bug which is hard to find
database_username: "mautrix_slack_bridge" # @todo Reactivate
database_name: "mautrix_slack_bridge" # - database_password: "{{ mautrix_slack_bridge_database_password }}"
bridge_name: "slack" # database_username: "mautrix_slack_bridge"
# database_name: "mautrix_slack_bridge"
# bridge_name: "slack"
- database_password: "{{ mautrix_facebook_bridge_database_password }}" - database_password: "{{ mautrix_facebook_bridge_database_password }}"
database_username: "mautrix_facebook_bridge" database_username: "mautrix_facebook_bridge"

View File

@ -17,6 +17,7 @@ services:
MYSQL_USER: "{{database_username}}" MYSQL_USER: "{{database_username}}"
MYSQL_PASSWORD: "{{database_password}}" MYSQL_PASSWORD: "{{database_password}}"
MYSQL_HOST: {{database_host}}:3306 MYSQL_HOST: {{database_host}}:3306
PHP_MEMORY_LIMIT: 1G # Required for plugin duplicate finder
{% include 'templates/docker/container/depends-on-database-redis.yml.j2' %} {% include 'templates/docker/container/depends-on-database-redis.yml.j2' %}
{% include 'templates/docker/container/networks.yml.j2' %} {% include 'templates/docker/container/networks.yml.j2' %}

View File

@ -12,7 +12,9 @@ events {
http { http {
include /etc/nginx/mime.types; include /etc/nginx/mime.types;
default_type application/octet-stream; default_type application/octet-stream;
types {
application/javascript mjs;
}
log_format main '$remote_addr - $remote_user [$time_local] "$request" ' log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" ' '$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"'; '"$http_user_agent" "$http_x_forwarded_for"';

View File

@ -22,7 +22,7 @@ def run_command(command):
if process and process.stdout: if process and process.stdout:
process.stdout.close() process.stdout.close()
def git_pull(directory): def git_pull():
""" """
Checks whether the Git repository in the specified directory is up to date and performs a git pull if necessary. Checks whether the Git repository in the specified directory is up to date and performs a git pull if necessary.
@ -32,8 +32,7 @@ def git_pull(directory):
Returns: Returns:
bool: True if a git pull was performed, otherwise False. bool: True if a git pull was performed, otherwise False.
""" """
os.chdir(directory) print(f"Checking if the git repository is up to date.")
print(f"Checking if the git repository in {directory} is up to date.")
local = subprocess.check_output("git rev-parse @", shell=True).decode().strip() local = subprocess.check_output("git rev-parse @", shell=True).decode().strip()
remote = subprocess.check_output("git rev-parse @{u}", shell=True).decode().strip() remote = subprocess.check_output("git rev-parse @{u}", shell=True).decode().strip()
@ -59,8 +58,7 @@ def get_image_digests(directory):
else: else:
raise # Other errors are still raised raise # Other errors are still raised
def is_any_service_up(directory): def is_any_service_up():
os.chdir(directory)
process = subprocess.Popen("docker-compose ps -q", shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) process = subprocess.Popen("docker-compose ps -q", shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
output, _ = process.communicate() output, _ = process.communicate()
service_ids = output.decode().strip().splitlines() service_ids = output.decode().strip().splitlines()
@ -70,26 +68,23 @@ def is_any_service_up(directory):
return False # No services are up return False # No services are up
return True # At least one service is up return True # At least one service is up
def pull_docker_images():
def update_docker(directory):
print(f"Checking for updates to Docker images in {directory}.")
os.chdir(directory)
before_digests = get_image_digests(directory)
print("Pulling docker images.") print("Pulling docker images.")
need_to_build=False
try: try:
run_command("docker-compose pull") run_command("docker-compose pull")
except subprocess.CalledProcessError as e: except subprocess.CalledProcessError as e:
if "pull access denied" in e.output.decode() or "must be built from source" in e.output.decode(): if "pull access denied" in e.output.decode() or "must be built from source" in e.output.decode():
print("Need to build the image from source.") print("Need to build the image from source.")
need_to_build=True return True
else: else:
print("Failed to pull images with unexpected error.") print("Failed to pull images with unexpected error.")
raise raise
return False
def update_docker(directory):
print(f"Checking for updates to Docker images in {directory}.")
before_digests = get_image_digests(directory)
need_to_build = pull_docker_images()
after_digests = get_image_digests(directory) after_digests = get_image_digests(directory)
if before_digests != after_digests: if before_digests != after_digests:
print("Changes detected in image digests. Rebuilding containers.") print("Changes detected in image digests. Rebuilding containers.")
@ -128,9 +123,8 @@ def update_procedure(command):
print("All attempts to update Nextcloud apps have failed.") print("All attempts to update Nextcloud apps have failed.")
raise # Re-raise the last exception after all attempts fail raise # Re-raise the last exception after all attempts fail
def start_docker(directory): def start_docker(directory):
if is_any_service_up(directory): if is_any_service_up():
print(f"Restarting containers in {directory}.") print(f"Restarting containers in {directory}.")
run_command("docker-compose up -d --force-recreate") run_command("docker-compose up -d --force-recreate")
else: else:
@ -146,9 +140,10 @@ if __name__ == "__main__":
if dir_entry.is_dir(): if dir_entry.is_dir():
dir_path = dir_entry.path dir_path = dir_entry.path
print(f"Checking for updates in: {dir_path}") print(f"Checking for updates in: {dir_path}")
os.chdir(dir_path)
if os.path.isdir(os.path.join(dir_path, ".git")): if os.path.isdir(os.path.join(dir_path, ".git")):
git_repository_was_pulled = git_pull(dir_path) git_repository_was_pulled = git_pull()
# Discourse is an exception and uses own update command instead of docker compose # Discourse is an exception and uses own update command instead of docker compose
if os.path.basename(dir_path) == "discourse": if os.path.basename(dir_path) == "discourse":
@ -156,8 +151,16 @@ if __name__ == "__main__":
update_discourse(dir_path) update_discourse(dir_path)
else: else:
print("Discourse update skipped. No changes in git repository.") print("Discourse update skipped. No changes in git repository.")
if os.path.basename(dir_path) == "matrix":
# No autoupdate for matrix is possible atm,
# due to the reason that the role has to be executed every time.
# The update has to be executed in the role
# @todo implement in future
pass
else: else:
# Pull and update docker images
update_docker(dir_path) update_docker(dir_path)
# Nextcloud needs additional update procedures # Nextcloud needs additional update procedures
if os.path.basename(dir_path) == "nextcloud": if os.path.basename(dir_path) == "nextcloud":
update_nextcloud() update_nextcloud()