Compare commits

..

43 Commits

Author SHA1 Message Date
Niklas Meyer
490d553dfc Merge pull request #5264 from mailcow/staging
2023-05a
2023-05-30 16:23:26 +02:00
DerLinkman
70aab7568e Changed maintainers to tinc (Dockerfiles) 2023-05-30 16:20:35 +02:00
DerLinkman
f82aba3e26 [Dovecot] Update to 1.24 2023-05-30 16:18:14 +02:00
FreddleSpl0it
f80940efdc [Dovecot] remove pass return in Dovecot lua auth 2023-05-30 09:09:41 +02:00
renovate[bot]
38cd376228 Update dependency nextcloud/server to v26.0.2 (#5254)
Signed-off-by: milkmaker <milkmaker@mailcow.de>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2023-05-28 15:48:28 +02:00
Niklas Meyer
74bcec45f1 Merge pull request #5250 from mailcow/staging
2023-05
2023-05-25 16:30:16 +02:00
Niklas Meyer
9700b3251f Merge pull request #5214 from mailcow/feat/gh_actions_postscreen
Add GitHub action update_postscreen_access_list.yml
2023-05-25 15:40:20 +02:00
Niklas Meyer
88b8d50cd5 Merge pull request #4028 from Daniel15/patch-2
Enable maildir_very_dirty_syncs by default
2023-05-24 11:00:38 +02:00
DerLinkman
55b0191050 [PHP] Update to 1.84 2023-05-23 10:46:21 +02:00
Peter
33c97fb318 change domain for docs 2023-05-10 20:32:38 +02:00
Niklas Meyer
23d33ad5a8 Merge pull request #5231 from mailcow/renovate/alpine-3.x
Update alpine Docker tag to v3.18
2023-05-10 08:58:47 +02:00
renovate[bot]
bd6c98047a Update alpine Docker tag to v3.18
Signed-off-by: milkmaker <milkmaker@mailcow.de>
2023-05-10 01:50:21 +00:00
Patrick Schult
73d6a29ae1 Merge pull request #5205 from mailcow/clean_sasl_log
Clean up old entries from sasl_log
2023-05-09 09:49:40 +02:00
Patrick Schult
173e39c859 Merge pull request #5200 from mailcow/fix/delete-sender-acl
[Web] Fix deleting sender_acl when mbox is deleted
2023-05-08 16:35:42 +02:00
Patrick Schult
c0745c5cde Merge pull request #5197 from mailcow/fix/bcc-validation
[Web] Fix BCC validation
2023-05-08 16:32:12 +02:00
Patrick Schult
1a6f93327e Merge pull request #5203 from mailcow/feat/bad_asn
Add IP Connect Inc to bad_asn.map
2023-05-08 16:01:44 +02:00
Patrick Schult
3c68a53170 Merge pull request #5201 from mailcow/fix/sieve-print
[Dockerapi] Fix typo in dockerapi sieve print
2023-05-08 16:00:22 +02:00
Patrick Schult
e38c27ed67 Merge pull request #5211 from goodygh/5175-fix-mobileconfig-redirect
[web] Fix typo in mobileconfig redirect
2023-05-08 15:55:50 +02:00
Patrick Schult
8eaf8bbbde Merge pull request #5220 from mailcow/fix/bcc-selectpicker
[Web] fix bcc localdest selectpicker
2023-05-08 15:53:53 +02:00
Patrick Schult
e015c7dbca Merge pull request #5202 from mailcow/feat/user-acl-tabs
[Web] hide user tabs if acl is missing
2023-05-08 15:48:52 +02:00
Patrick Schult
58452abcdf Merge pull request #5204 from mailcow/fix/rspamd-table
[Web] fix rspamd table on sm devices
2023-05-08 15:43:58 +02:00
Patrick Schult
2cbf0da137 Merge pull request #5198 from mailcow/fix/sorting-tla
[Web] Fix temporary email aliases sorting
2023-05-08 15:29:32 +02:00
FreddleSpl0it
aabcd10539 [Web] fix bcc localdest selectpicker 2023-05-03 09:59:49 +02:00
milkmaker
ee607dc3cc Translations update from Weblate (#5218)
* [Web] Updated lang.en-gb.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.cs-cz.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.de-de.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.fr-fr.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.ro-ro.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.sk-sk.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.zh-cn.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.it-it.json

Co-authored-by: Peter <magic@kthx.at>

* [Web] Updated lang.zh-tw.json

Co-authored-by: Peter <magic@kthx.at>

---------

Co-authored-by: Peter <magic@kthx.at>
2023-05-02 18:29:38 +02:00
DerLinkman
1265302a8e [DockerAPI] Update to 2.04 2023-05-02 18:11:59 +02:00
DerLinkman
b5acf56e20 Added Platform Information on Status Page 2023-05-02 18:11:10 +02:00
FreddleSpl0it
fe4a418af4 [Web] fix rspamd table scan_time on sm devices 2023-04-27 10:45:11 +02:00
Peter
e5f03e8526 Update update_postscreen_whitelist.sh 2023-04-26 18:44:35 +02:00
Peter
fb60c4a150 Add update_postscreen_access_list.yml 2023-04-26 18:43:54 +02:00
goodygh
fd203abd47 Fix typo in mobileconfig redirect 2023-04-25 22:11:04 +02:00
milkmaker
6b65f0fc74 [Web] Updated lang.ru-ru.json (#5210)
Co-authored-by: Vakhtang <vakhtang.g.st@gmail.com>
2023-04-25 20:59:05 +02:00
Michael Kuron
856b3b62f2 Clean up old sasl_log entries 2023-04-22 14:16:42 +02:00
FreddleSpl0it
0372a2150d [Web] fix rspamd table on sm devices 2023-04-21 20:14:43 +02:00
Peter
f3322c0577 Add IP Connect Inc 2023-04-21 19:43:20 +02:00
FreddleSpl0it
c2bcc4e086 [Web] hide user tabs if acl is missing 2023-04-21 17:03:40 +02:00
FreddleSpl0it
6e79c48640 [Dockerapi] Fix typo in dockerapi sieve print 2023-04-21 16:15:16 +02:00
FreddleSpl0it
d7dfa95e1b [Web] Fix deleting sender_acl when mbox is deleted 2023-04-21 13:47:13 +02:00
FreddleSpl0it
cf1cc24e33 [Web] Fix temporary email aliases sorting 2023-04-21 12:26:50 +02:00
FreddleSpl0it
6824a5650f [Web] Fix BCC validation 2023-04-21 11:21:43 +02:00
Patrick Schult
8f28666916 Merge pull request #5195 from mailcow/staging
2023-04b
2023-04-20 16:49:17 +02:00
Daniel Lo Nigro
1606658cb1 Add missing spaces 2021-08-28 20:02:39 -07:00
Daniel Lo Nigro
54ba66733e Enable maildir_very_dirty_syncs rather than just adding comment 2021-05-02 16:39:26 -07:00
Daniel Lo Nigro
f6847e6f8c Add comment about maildir_very_dirty_syncs to dovecot.conf 2021-03-13 10:46:32 -08:00
52 changed files with 313 additions and 926 deletions

View File

@@ -0,0 +1,39 @@
name: Update postscreen_access.cidr
on:
schedule:
# Monthly
- cron: "0 0 1 * *"
workflow_dispatch: # Allow to run workflow manually
permissions:
contents: read # to fetch code (actions/checkout)
jobs:
Update-postscreen_access_cidr:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v3
- name: Generate postscreen_access.cidr
run: |
bash helper-scripts/update_postscreen_whitelist.sh
- name: Create Pull Request
uses: peter-evans/create-pull-request@v5
with:
token: ${{ secrets.mailcow_action_Update_postscreen_access_cidr_pat }}
commit-message: update postscreen_access.cidr
committer: milkmaker <milkmaker@mailcow.de>
author: milkmaker <milkmaker@mailcow.de>
signoff: false
branch: update/postscreen_access.cidr
base: staging
delete-branch: true
add-paths: |
data/conf/postfix/postscreen_access.cidr
title: '[Postfix] update postscreen_access.cidr'
body: |
This PR updates the postscreen_access.cidr using GitHub Actions and [helper-scripts/update_postscreen_whitelist.sh](https://github.com/mailcow/mailcow-dockerized/blob/master/helper-scripts/update_postscreen_whitelist.sh)

View File

@@ -1,6 +1,6 @@
FROM alpine:3.17 FROM alpine:3.17
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
RUN apk upgrade --no-cache \ RUN apk upgrade --no-cache \
&& apk add --update --no-cache \ && apk add --update --no-cache \

View File

@@ -1,6 +1,6 @@
FROM alpine:3.17 FROM alpine:3.17
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
WORKDIR /app WORKDIR /app

View File

@@ -9,6 +9,7 @@ import os
import json import json
import asyncio import asyncio
import redis import redis
import platform
from datetime import datetime from datetime import datetime
import logging import logging
from logging.config import dictConfig from logging.config import dictConfig
@@ -274,49 +275,6 @@ class DockerUtils:
res = { 'type': 'success', 'msg': 'Scheduled immediate delivery'} res = { 'type': 'success', 'msg': 'Scheduled immediate delivery'}
return Response(content=json.dumps(res, indent=4), media_type="application/json") return Response(content=json.dumps(res, indent=4), media_type="application/json")
# api call: container_post - post_action: exec - cmd: sogo - task: customize_enable
def container_post__exec__sogo__customize_enable(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "/customize.sh enable"]
sogo_return = container.exec_run(cmd)
return exec_run_handler('utf8_text_only', sogo_return)
# api call: container_post - post_action: exec - cmd: sogo - task: customize_disable
def container_post__exec__sogo__customize_disable(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "/customize.sh disable"]
sogo_return = container.exec_run(cmd)
return exec_run_handler('utf8_text_only', sogo_return)
# api call: container_post - post_action: exec - cmd: sogo - task: set_logo
def container_post__exec__sogo__set_logo(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "/customize.sh set_logo"]
sogo_return = container.exec_run(cmd)
return exec_run_handler('utf8_text_only', sogo_return)
# api call: container_post - post_action: exec - cmd: sogo - task: remove_logo
def container_post__exec__sogo__remove_logo(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "rm -f /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo-full.svg"]
sogo_return = container.exec_run(cmd)
return exec_run_handler('utf8_text_only', sogo_return)
# api call: container_post - post_action: exec - cmd: sogo - task: set_favicon
def container_post__exec__sogo__set_favicon(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "/customize.sh set_favicon"]
sogo_return = container.exec_run(cmd)
return exec_run_handler('utf8_text_only', sogo_return)
# api call: container_post - post_action: exec - cmd: sogo - task: remove_favicon
def container_post__exec__sogo__remove_favicon(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "cp /sogo.ico /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo.ico"]
sogo_return = container.exec_run(cmd)
return exec_run_handler('utf8_text_only', sogo_return)
# api call: container_post - post_action: exec - cmd: sogo - task: set_theme
def container_post__exec__sogo__set_theme(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "/customize.sh set_theme"]
sogo_return = container.exec_run(cmd)
return exec_run_handler('utf8_text_only', sogo_return)
# api call: container_post - post_action: exec - cmd: mailq - task: list # api call: container_post - post_action: exec - cmd: mailq - task: list
def container_post__exec__mailq__list(self, container_id, request_json): def container_post__exec__mailq__list(self, container_id, request_json):
for container in self.docker_client.containers.list(filters={"id": container_id}): for container in self.docker_client.containers.list(filters={"id": container_id}):
@@ -413,7 +371,7 @@ class DockerUtils:
return exec_run_handler('utf8_text_only', sieve_return) return exec_run_handler('utf8_text_only', sieve_return)
# api call: container_post - post_action: exec - cmd: sieve - task: print # api call: container_post - post_action: exec - cmd: sieve - task: print
def container_post__exec__sieve__print(self, container_id, request_json): def container_post__exec__sieve__print(self, container_id, request_json):
if 'username' in request.json and 'script_name' in request_json: if 'username' in request_json and 'script_name' in request_json:
for container in self.docker_client.containers.list(filters={"id": container_id}): for container in self.docker_client.containers.list(filters={"id": container_id}):
cmd = ["/bin/bash", "-c", "/usr/bin/doveadm sieve get -u '" + request_json['username'].replace("'", "'\\''") + "' '" + request_json['script_name'].replace("'", "'\\''") + "'"] cmd = ["/bin/bash", "-c", "/usr/bin/doveadm sieve get -u '" + request_json['username'].replace("'", "'\\''") + "' '" + request_json['script_name'].replace("'", "'\\''") + "'"]
sieve_return = container.exec_run(cmd) sieve_return = container.exec_run(cmd)
@@ -528,7 +486,8 @@ async def get_host_stats(wait=5):
"swap": psutil.swap_memory() "swap": psutil.swap_memory()
}, },
"uptime": time.time() - psutil.boot_time(), "uptime": time.time() - psutil.boot_time(),
"system_time": system_time.strftime("%d.%m.%Y %H:%M:%S") "system_time": system_time.strftime("%d.%m.%Y %H:%M:%S"),
"architecture": platform.machine()
} }
redis_client.set('host_stats', json.dumps(host_stats), ex=10) redis_client.set('host_stats', json.dumps(host_stats), ex=10)

View File

@@ -1,5 +1,5 @@
FROM debian:bullseye-slim FROM debian:bullseye-slim
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
ARG DEBIAN_FRONTEND=noninteractive ARG DEBIAN_FRONTEND=noninteractive
# renovate: datasource=github-tags depName=dovecot/core versioning=semver-coerced # renovate: datasource=github-tags depName=dovecot/core versioning=semver-coerced

View File

@@ -159,7 +159,7 @@ function auth_password_verify(req, pass)
VALUES ("%s", 0, "%s", "%s")]], con:escape(req.service), con:escape(req.user), con:escape(req.real_rip))) VALUES ("%s", 0, "%s", "%s")]], con:escape(req.service), con:escape(req.user), con:escape(req.real_rip)))
cur:close() cur:close()
con:close() con:close()
return dovecot.auth.PASSDB_RESULT_OK, "password=" .. pass return dovecot.auth.PASSDB_RESULT_OK, "password=pass"
end end
row = cur:fetch (row, "a") row = cur:fetch (row, "a")
end end
@@ -180,13 +180,13 @@ function auth_password_verify(req, pass)
if tostring(req.real_rip) == "__IPV4_SOGO__" then if tostring(req.real_rip) == "__IPV4_SOGO__" then
cur:close() cur:close()
con:close() con:close()
return dovecot.auth.PASSDB_RESULT_OK, "password=" .. pass return dovecot.auth.PASSDB_RESULT_OK, "password=pass"
elseif row.has_prot_access == "1" then elseif row.has_prot_access == "1" then
con:execute(string.format([[REPLACE INTO sasl_log (service, app_password, username, real_rip) con:execute(string.format([[REPLACE INTO sasl_log (service, app_password, username, real_rip)
VALUES ("%s", %d, "%s", "%s")]], con:escape(req.service), row.id, con:escape(req.user), con:escape(req.real_rip))) VALUES ("%s", %d, "%s", "%s")]], con:escape(req.service), row.id, con:escape(req.user), con:escape(req.real_rip)))
cur:close() cur:close()
con:close() con:close()
return dovecot.auth.PASSDB_RESULT_OK, "password=" .. pass return dovecot.auth.PASSDB_RESULT_OK, "password=pass"
end end
end end
row = cur:fetch (row, "a") row = cur:fetch (row, "a")

View File

@@ -1,5 +1,5 @@
FROM alpine:3.17 FROM alpine:3.17
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
ENV XTABLES_LIBDIR /usr/lib/xtables ENV XTABLES_LIBDIR /usr/lib/xtables
ENV PYTHON_IPTABLES_XTABLES_VERSION 12 ENV PYTHON_IPTABLES_XTABLES_VERSION 12

View File

@@ -1,5 +1,5 @@
FROM alpine:3.17 FROM alpine:3.17
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
WORKDIR /app WORKDIR /app

View File

@@ -1,5 +1,5 @@
FROM php:8.2-fpm-alpine3.17 FROM php:8.2-fpm-alpine3.17
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
# renovate: datasource=github-tags depName=krakjoe/apcu versioning=semver-coerced # renovate: datasource=github-tags depName=krakjoe/apcu versioning=semver-coerced
ARG APCU_PECL_VERSION=5.1.22 ARG APCU_PECL_VERSION=5.1.22

View File

@@ -172,6 +172,24 @@ BEGIN
END; END;
// //
DELIMITER ; DELIMITER ;
DROP EVENT IF EXISTS clean_sasl_log;
DELIMITER //
CREATE EVENT clean_sasl_log
ON SCHEDULE EVERY 1 DAY DO
BEGIN
DELETE sasl_log.* FROM sasl_log
LEFT JOIN (
SELECT username, service, MAX(datetime) AS lastdate
FROM sasl_log
GROUP BY username, service
) AS last ON sasl_log.username = last.username AND sasl_log.service = last.service
WHERE datetime < DATE_SUB(NOW(), INTERVAL 31 DAY) AND datetime < lastdate;
DELETE FROM sasl_log
WHERE username NOT IN (SELECT username FROM mailbox) AND
datetime < DATE_SUB(NOW(), INTERVAL 31 DAY);
END;
//
DELIMITER ;
EOF EOF
fi fi

View File

@@ -1,5 +1,5 @@
FROM debian:bullseye-slim FROM debian:bullseye-slim
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
ARG DEBIAN_FRONTEND=noninteractive ARG DEBIAN_FRONTEND=noninteractive
ENV LC_ALL C ENV LC_ALL C

View File

@@ -1,5 +1,5 @@
FROM debian:bullseye-slim FROM debian:bullseye-slim
LABEL maintainer "Andre Peters <andre.peters@tinc.gmbh>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
ARG DEBIAN_FRONTEND=noninteractive ARG DEBIAN_FRONTEND=noninteractive
ARG CODENAME=bullseye ARG CODENAME=bullseye

View File

@@ -1,5 +1,5 @@
FROM debian:bullseye-slim FROM debian:bullseye-slim
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
ARG DEBIAN_FRONTEND=noninteractive ARG DEBIAN_FRONTEND=noninteractive
ARG SOGO_DEBIAN_REPOSITORY=http://packages.sogo.nu/nightly/5/debian/ ARG SOGO_DEBIAN_REPOSITORY=http://packages.sogo.nu/nightly/5/debian/
@@ -25,7 +25,6 @@ RUN echo "Building from repository $SOGO_DEBIAN_REPOSITORY" \
psmisc \ psmisc \
wget \ wget \
patch \ patch \
redis-tools \
&& dpkgArch="$(dpkg --print-architecture | awk -F- '{ print $NF }')" \ && dpkgArch="$(dpkg --print-architecture | awk -F- '{ print $NF }')" \
&& wget -O /usr/local/bin/gosu "https://github.com/tianon/gosu/releases/download/$GOSU_VERSION/gosu-$dpkgArch" \ && wget -O /usr/local/bin/gosu "https://github.com/tianon/gosu/releases/download/$GOSU_VERSION/gosu-$dpkgArch" \
&& chmod +x /usr/local/bin/gosu \ && chmod +x /usr/local/bin/gosu \
@@ -47,14 +46,10 @@ COPY syslog-ng-redis_slave.conf /etc/syslog-ng/syslog-ng-redis_slave.conf
COPY supervisord.conf /etc/supervisor/supervisord.conf COPY supervisord.conf /etc/supervisor/supervisord.conf
COPY acl.diff /acl.diff COPY acl.diff /acl.diff
COPY stop-supervisor.sh /usr/local/sbin/stop-supervisor.sh COPY stop-supervisor.sh /usr/local/sbin/stop-supervisor.sh
COPY customize.sh /
COPY docker-entrypoint.sh / COPY docker-entrypoint.sh /
RUN rm -rf /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo-full.svg
RUN mv /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo.ico /sogo.ico
RUN chmod +x /bootstrap-sogo.sh \ RUN chmod +x /bootstrap-sogo.sh \
/usr/local/sbin/stop-supervisor.sh \ /usr/local/sbin/stop-supervisor.sh
/customize.sh
ENTRYPOINT ["/docker-entrypoint.sh"] ENTRYPOINT ["/docker-entrypoint.sh"]

View File

@@ -240,8 +240,6 @@ chmod 600 /var/lib/sogo/GNUstep/Defaults/sogod.plist
# Copy logo, if any # Copy logo, if any
[[ -f /etc/sogo/sogo-full.svg ]] && cp /etc/sogo/sogo-full.svg /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo-full.svg [[ -f /etc/sogo/sogo-full.svg ]] && cp /etc/sogo/sogo-full.svg /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo-full.svg
# Use the mailcow logo if no sogo-full.svg file does exist
! [[ -f /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo-full.svg ]] && cp /etc/sogo/cow_mailcow.svg /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo-full.svg
# Rsync web content # Rsync web content
echo "Syncing web content with named volume" echo "Syncing web content with named volume"

View File

@@ -1,112 +0,0 @@
#!/bin/bash
if [[ "$1" == "enable" ]]; then
# enable debug mode
if grep -q "SOGoUIxDebugEnabled = YES;" "/etc/sogo/sogo.conf"; then
sed -i "s|//SOGoUIxDebugEnabled = YES;|SOGoUIxDebugEnabled = YES;|" "/etc/sogo/sogo.conf"
else
echo "SOGoUIxDebugEnabled = YES;" >> "/etc/sogo/sogo.conf"
fi
echo "Success: SOGoUIxDebugEnabled has been enabled"
elif [[ "$1" == "disable" ]]; then
# disable debug mode
if grep -q "SOGoUIxDebugEnabled = YES;" "/etc/sogo/sogo.conf"; then
if ! grep -q "//SOGoUIxDebugEnabled = YES;" "/etc/sogo/sogo.conf"; then
sed -i "s|SOGoUIxDebugEnabled = YES;|//SOGoUIxDebugEnabled = YES;|" "/etc/sogo/sogo.conf"
fi
fi
echo "Success: SOGoUIxDebugEnabled has been disabled"
elif [[ "$1" == "set_theme" ]]; then
# Get the sogo palettes from Redis
PRIMARY=$(redis-cli -h redis HGET SOGO_THEME primary)
if [ $? -ne 0 ]; then
PRIMARY="green"
fi
ACCENT=$(redis-cli -h redis HGET SOGO_THEME accent)
if [ $? -ne 0 ]; then
ACCENT="green"
fi
BACKGROUND=$(redis-cli -h redis HGET SOGO_THEME background)
if [ $? -ne 0 ]; then
BACKGROUND="grey"
fi
# Read custom palettes
if [ -f /etc/sogo/custom-palettes.js ]; then
COLORS=$(cat /etc/sogo/custom-palettes.js)
else
COLORS=""
fi
# Write theme to /usr/lib/GNUstep/SOGo/WebServerResources/js/theme.js
cat > /usr/lib/GNUstep/SOGo/WebServerResources/js/theme.js <<EOL
(function() {
'use strict';
angular.module('SOGo.Common')
.config(configure)
configure.\$inject = ['\$mdThemingProvider'];
function configure(\$mdThemingProvider) {
$COLORS
var primary = \$mdThemingProvider.extendPalette('$PRIMARY', {});
var accent = \$mdThemingProvider.extendPalette('$ACCENT', {
'A100': 'ffffff'
});
var background = \$mdThemingProvider.extendPalette('$BACKGROUND', {});
\$mdThemingProvider.definePalette('primary-cow', primary);
\$mdThemingProvider.definePalette('accent-cow', accent);
\$mdThemingProvider.definePalette('background-cow', background);
\$mdThemingProvider.theme('default')
.primaryPalette('primary-cow', primarySettings)
.accentPalette('accent-cow', accentSettings)
.backgroundPalette('background-cow', backgroundSettings);
\$mdThemingProvider.generateThemesOnDemand(false);
}
})();
EOL
echo "Success: Theme configuration written"
elif [[ "$1" == "set_logo" ]]; then
# Get the image data from Redis and save it to a tmp file
redis-cli -h redis GET MAIN_LOGO > /tmp/logo_base64.txt
# Check if mime type is svg+xml
mime_type=$(awk -F'[:;]' '{print $2}' /tmp/logo_base64.txt | sed 's/.*\///')
if [ "$mime_type" != "svg+xml" ]; then
echo "Error: Image format must be of type svg"
exit 1
fi
# Decode base64 and save to file
payload=$(cat /tmp/logo_base64.txt | sed 's/^data:[^;]*;//' | awk '{ sub(/^base64,/, ""); print $0 }')
echo $payload | base64 -d | tee /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo-full.svg > /dev/null
# Remove temp file
rm /tmp/logo_base64.txt
echo "Success: Image has been set"
elif [[ "$1" == "set_favicon" ]]; then
# Get the image data from Redis and save it to a tmp file
redis-cli -h redis GET FAVICON > /tmp/favicon_base64.txt
# Check if mime type is png or ico
mime_type=$(awk -F'[:;]' '{print $2}' /tmp/favicon_base64.txt | sed 's/.*\///')
if [[ "$mime_type" != "png" && "$mime_type" != "ico" ]]; then
echo "Error: Image format must be of type png or ico"
exit 1
fi
# Decode base64 and save to file
payload=$(cat /tmp/favicon_base64.txt | sed 's/^data:[^;]*;//' | awk '{ sub(/^base64,/, ""); print $0 }')
echo $payload | base64 -d | tee /usr/lib/GNUstep/SOGo/WebServerResources/img/sogo.ico > /dev/null
# Remove temp file
rm /tmp/favicon_base64.txt
echo "Success: Image has been set"
fi

View File

@@ -1,6 +1,6 @@
FROM alpine:3.17 FROM alpine:3.17
LABEL maintainer "Andre Peters <andre.peters@servercow.de>" LABEL maintainer "The Infrastructure Company GmbH <info@servercow.de>"
RUN apk add --update --no-cache \ RUN apk add --update --no-cache \
curl \ curl \

View File

@@ -24,6 +24,11 @@ mail_plugins = </etc/dovecot/mail_plugins
mail_attachment_fs = crypt:set_prefix=mail_crypt_global:posix: mail_attachment_fs = crypt:set_prefix=mail_crypt_global:posix:
mail_attachment_dir = /var/attachments mail_attachment_dir = /var/attachments
mail_attachment_min_size = 128k mail_attachment_min_size = 128k
# Significantly speeds up very large mailboxes, but is only safe to enable if
# you do not manually modify the files in the `cur` directories in
# mailcowdockerized_vmail-vol-1.
# https://docs.mailcow.email/manual-guides/Dovecot/u_e-dovecot-performance/
maildir_very_dirty_syncs = yes
# Dovecot 2.2 # Dovecot 2.2
#ssl_protocols = !SSLv3 #ssl_protocols = !SSLv3

View File

@@ -28,3 +28,4 @@
#197695 2 #Domain names registrar REG.RU Ltd, Russia #197695 2 #Domain names registrar REG.RU Ltd, Russia
#198068 2 #P.A.G.M. OU, Estonia #198068 2 #P.A.G.M. OU, Estonia
#201942 5 #Soltia Consulting SL, Spain #201942 5 #Soltia Consulting SL, Spain
#213373 4 #IP Connect Inc

View File

@@ -1,182 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Generator: Adobe Illustrator 16.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.1"
id="layer1"
x="0px"
y="0px"
width="434.82101"
height="376.871"
viewBox="0 0 434.82101 376.871"
enable-background="new 0 0 374.82 356.871"
xml:space="preserve"
inkscape:version="0.91 r13725"
sodipodi:docname="cow_mailcow.svg"><metadata
id="metadata77"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title><cc:license
rdf:resource="" /></cc:Work></rdf:RDF></metadata><defs
id="defs75" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1721"
inkscape:window-height="1177"
id="namedview73"
showgrid="false"
inkscape:zoom="1.4142136"
inkscape:cx="219.01206"
inkscape:cy="236.74714"
inkscape:window-x="-8"
inkscape:window-y="-8"
inkscape:window-maximized="1"
inkscape:current-layer="layer1"
fit-margin-top="10"
fit-margin-left="50"
fit-margin-bottom="10"
fit-margin-right="10"
showguides="true" /><g
id="g3"
transform="translate(50,10)"><g
id="grey_5_"><path
d="m 55.948,213.25 c 0.07331,-20.26146 -0.716379,-17.26061 -3.655806,-39.26743 2.227824,-22.4392 -7.627923,-38.85857 -7.669233,-58.34044 0,-4.715 -5.805961,-6.78013 -4.760961,-11.13713 -6.292,13.037 -9.833,27.707 -9.833,43.222 0,25.946 9.89,49.533 26.027,67.059 -0.048,-0.511 -0.082,-1.023 -0.108,-1.536 z"
id="path6"
inkscape:connector-curvature="0"
style="fill:#3d5263"
sodipodi:nodetypes="ccccscc" /></g><g
id="yellow"><path
d="m 254.808,180.412 -0.567,0.455 c -10.49,39.88 -40.951,71.658 -80.048,83.996 l 10.952,9.206 53.296,44.799 31.601,26.563 c 0.783,-2.011 1.229,-4.19 1.231,-6.478 0,-0.007 10e-4,-0.013 10e-4,-0.02 l 0,-16.836 0,-10e-4 0,-28.141 0,-126.736 -16.466,13.193 z"
id="path9"
inkscape:connector-curvature="0"
style="fill:#f9e82d" /><path
d="m 23.027,185.52 -6.574,-5.225 -16.452,-13.076 0,90.407 0,81.307 c 0,2.295 0.447,4.481 1.233,6.499 l 58.39,-48.683 26.964,-22.481 12.38,-10.321 C 62.73,251.524 34.307,222.274 23.027,185.52 Z"
id="path11"
inkscape:connector-curvature="0"
style="fill:#f9e82d" /><path
d="m 238.441,318.868 -53.296,-44.799 -10.952,-9.206 c -11.431,3.607 -23.597,5.558 -36.22,5.558 -13.653,0 -26.772,-2.28 -39.004,-6.474 l -12.38,10.321 -26.965,22.482 -58.39,48.683 c 2.605,6.69 9.094,11.438 16.706,11.438 l 235.394,0 c 7.613,0 14.103,-4.749 16.707,-11.44 l -31.6,-26.563 z"
id="path13"
inkscape:connector-curvature="0"
style="fill:#edd514;fill-opacity:0.89499996" /></g><g
id="grey_4_"><path
enable-background="new "
d="M 238.441,318.868 C 196.984,322.876 123.368,324.434 59.625,296.75 38.082,287.394 17.666,274.7 0.002,257.627 l 0,81.307 c 0,2.295 0.447,4.481 1.233,6.499 2.605,6.69 9.094,11.438 16.706,11.438 l 235.394,0 c 7.613,0 14.103,-4.749 16.707,-11.44 0.783,-2.011 1.229,-4.19 1.231,-6.478 l 0,-24.584 c 0,0 -12.58,2.541 -32.832,4.499 z"
id="path16"
inkscape:connector-curvature="0"
style="opacity:0.1;fill:#3d5263" /><path
enable-background="new "
d="m 86.588,274.268 c 14.979,6.703 31.579,10.435 49.051,10.435 17.648,0 34.408,-3.803 49.505,-10.634 37.082,-16.777 64.125,-51.824 69.664,-93.657 l -0.567,0.455 c -10.49,39.88 -40.951,71.658 -80.048,83.996 -11.431,3.607 -23.597,5.558 -36.22,5.558 -13.653,0 -26.772,-2.28 -39.004,-6.474 C 62.731,251.524 34.308,222.274 23.028,185.52 l -6.574,-5.225 c 5.525,42.054 32.786,77.261 70.134,93.973 z"
id="path18"
inkscape:connector-curvature="0"
style="opacity:0.1;fill:#3d5263" /></g><g
id="white_1_"><path
d="m 54.293,63.875 c -1.799,1.745 -3.541,3.548 -5.229,5.402 -0.042,0.046 -0.085,0.092 -0.127,0.139 -0.234,0.258 -0.473,0.51 -0.705,0.77 0.055,-0.055 0.111,-0.108 0.166,-0.163 21.76,-21.782 51.828,-35.259 85.046,-35.259 66.396,0 120.222,53.826 120.222,120.223 0,30.718 -11.526,58.74 -30.482,79.991 21.633,-21.737 35.006,-51.7 35.01,-84.791 0,-0.004 0,-0.009 0,-0.013 0,-21.143 -5.465,-41.007 -15.049,-58.269 -1.449,-2.608 -2.991,-5.157 -4.624,-7.643 -5.377,-8.187 -11.727,-15.676 -18.885,-22.307 -5.903,-5.467 -12.351,-10.354 -19.26,-14.558 -4.278,-2.604 -8.734,-4.944 -13.341,-7.006 -10.627,-4.756 -22.07,-8.016 -34.062,-9.509 -4.915,-0.612 -9.921,-0.931 -15.001,-0.931 -5.747,0 -11.398,0.409 -16.93,1.189 -12.291,1.733 -23.981,5.329 -34.784,10.487 -4.742,2.264 -9.313,4.83 -13.688,7.672 -6.561,4.266 -12.682,9.149 -18.277,14.576 z"
id="path21"
inkscape:connector-curvature="0"
style="fill:#ffffff" /><path
d="m 95.828,118.535 c 2.559,0 4.63,-2.071 4.63,-4.629 0,-2.553 -2.071,-4.626 -4.63,-4.626 -2.558,0 -4.634,2.074 -4.634,4.626 10e-4,2.557 2.076,4.629 4.634,4.629 z"
id="path23"
inkscape:connector-curvature="0"
style="fill:#ffffff" /><path
d="m 186.85,118.535 c 2.556,0 4.629,-2.071 4.629,-4.629 0,-2.553 -2.074,-4.626 -4.629,-4.626 -2.559,0 -4.631,2.074 -4.631,4.626 0,2.557 2.073,4.629 4.631,4.629 z"
id="path25"
inkscape:connector-curvature="0"
style="fill:#ffffff" /></g><g
id="grey_3_"><g
id="g28"><path
d="m 223.701,234.394 c 18.648,-21.18 29.965,-48.971 29.965,-79.408 0,-66.396 -53.825,-120.223 -120.222,-120.223 -33.218,0 -63.286,13.477 -85.046,35.259 -4.591,5.125 -8.746,10.647 -12.413,16.507 -1.524,2.437 -2.963,4.931 -4.314,7.48 -7.067,13.341 -11.704,28.167 -13.301,43.893 -0.411,4.043 -0.622,8.146 -0.622,12.298 0,3.849 0.188,7.653 0.542,11.409 0.776,8.241 2.38,16.24 4.735,23.912 11.281,36.754 39.703,66.004 75.941,78.427 12.231,4.193 25.351,6.474 39.004,6.474 12.623,0 24.79,-1.95 36.22,-5.558 18.139,-5.725 34.412,-15.64 47.7,-28.603 0.536,-0.522 1.811,-1.867 1.811,-1.867 z m -5.788,-58.356 c -2.132,7.217 -5.052,14.085 -8.668,20.495 -16.571,29.372 -47.64,49.146 -83.233,49.146 -27.584,0 -52.447,-11.88 -69.956,-30.895 C 39.919,197.26 30.03,173.673 30.03,147.726 c 0,-15.515 3.54,-30.185 9.833,-43.222 15.648,-32.42 48.344,-54.73 86.15,-54.73 3.967,0 7.876,0.25 11.717,0.728 47.479,5.898 84.262,47.175 84.262,97.224 -0.002,9.846 -1.431,19.348 -4.079,28.312 z"
id="path30"
inkscape:connector-curvature="0"
style="fill:#f1f2f2" /></g><path
d="m 49.064,69.277 c -0.042,0.046 -0.085,0.092 -0.127,0.139 0.042,-0.047 0.085,-0.093 0.127,-0.139 z"
id="path32"
inkscape:connector-curvature="0"
style="fill:#f1f2f2" /></g><g
id="darkbrown_1_"><path
d="m 257.626,161.89 c -0.488,5.062 -1.29,10.032 -2.387,14.89 -0.31,1.371 -0.643,2.733 -0.999,4.086 l 0.567,-0.455 16.466,-13.193 0,-0.023 -13.647,-5.305 z"
id="path35"
inkscape:connector-curvature="0"
style="fill:#5a3620" /><path
d="m 0.001,167.219 16.451,13.076 6.574,5.225 c -2.354,-7.672 -3.959,-15.671 -4.735,-23.912 l -2.85,0.871 L 0,167.196"
id="path37"
inkscape:connector-curvature="0"
style="fill:#5a3620" /><path
d="m 87.491,192.337 c -6.21,0 -11.254,5.034 -11.254,11.257 0,6.216 5.043,11.257 11.254,11.257 6.221,0 11.261,-5.041 11.261,-11.257 0,-6.223 -5.041,-11.257 -11.261,-11.257 z"
id="path39"
inkscape:connector-curvature="0"
style="fill:#5a3620" /><path
d="m 181.307,192.337 c -6.218,0 -11.259,5.034 -11.259,11.257 0,6.216 5.041,11.257 11.259,11.257 6.22,0 11.257,-5.041 11.257,-11.257 0,-6.223 -5.037,-11.257 -11.257,-11.257 z"
id="path41"
inkscape:connector-curvature="0"
style="fill:#5a3620" /><path
d="m 182.997,102.25057 c -6.963,0 -15.44243,7.76632 -15.44243,14.73532 0,6.965 8.12588,17.2072 15.08888,17.2072 6.968,0 15.79898,-9.53609 15.79898,-16.50009 0.001,-6.97 -8.47743,-15.44243 -15.44543,-15.44243 z m 3.853,16.28443 c -2.558,0 -4.631,-2.072 -4.631,-4.629 0,-2.552 2.072,-4.626 4.631,-4.626 2.555,0 4.629,2.073 4.629,4.626 0,2.558 -2.073,4.629 -4.629,4.629 z"
id="path43"
inkscape:connector-curvature="0"
style="fill:#5a3620"
sodipodi:nodetypes="ssscssssss" /><path
d="m 89.709786,102.60413 c -6.971,0 -14.379767,8.11987 -14.379767,15.08887 0,6.965 8.824981,16.14653 15.793981,16.14653 6.963,0 15.79298,-9.18253 15.79298,-16.14653 0.001,-6.97 -10.243194,-15.08887 -17.207194,-15.08887 z M 95.828,118.535 c -2.559,0 -4.634,-2.072 -4.634,-4.629 0,-2.552 2.076,-4.626 4.634,-4.626 2.559,0 4.63,2.073 4.63,4.626 0,2.558 -2.071,4.629 -4.63,4.629 z"
id="path45"
inkscape:connector-curvature="0"
style="fill:#5a3620"
sodipodi:nodetypes="ssscssssss" /></g><g
id="cream"><path
d="m 336.302,256.425 c 3.59,-9.155 7.701,-11 9.346,-11.346 -40.757,3.757 -36.661,27.769 -34.026,35.96 0.55,1.712 1.037,2.733 1.037,2.733 0,0 2.031,4.787 7.536,8.748 4.149,2.986 10.27,5.503 18.995,5.144 27.063,0.461 35.631,-50.166 35.631,-50.166 -6.654,11.655 -26.404,9.876 -38.519,8.927 z"
id="path48"
inkscape:connector-curvature="0"
style="fill:#fef3df" /><path
d="m 48.937,69.415 c 0.042,-0.046 0.085,-0.092 0.127,-0.139 1.688,-1.854 3.43,-3.657 5.229,-5.402 -8.915,-6.977 -24.344,-15.826 -41.744,-11.633 0,0 2.814,20.458 23.437,34.287 3.667,-5.86 7.822,-11.381 12.413,-16.507 -0.055,0.055 -0.111,0.108 -0.166,0.163 0.231,-0.258 0.47,-0.511 0.704,-0.769 z"
id="path50"
inkscape:connector-curvature="0"
style="fill:#fef3df" /><path
d="m 258.812,52.242 c -15.831,-3.815 -30.029,3.169 -39.176,9.714 7.158,6.63 13.508,14.12 18.885,22.307 17.763,-13.689 20.291,-32.021 20.291,-32.021 z"
id="path52"
inkscape:connector-curvature="0"
style="fill:#fef3df" /><path
d="m 134.269,160.225 c -43.299,0 -78.388,22.964 -78.388,51.289 0,0.582 0.038,1.157 0.067,1.735 0.026,0.514 0.06,1.025 0.108,1.535 17.508,19.015 42.371,30.895 69.956,30.895 35.594,0 66.662,-19.774 83.233,-49.146 -9.796,-21.016 -39.651,-36.308 -74.976,-36.308 z M 87.491,214.85 c -6.211,0 -11.254,-5.041 -11.254,-11.257 0,-6.223 5.044,-11.257 11.254,-11.257 6.22,0 11.261,5.034 11.261,11.257 0,6.216 -5.04,11.257 -11.261,11.257 z m 93.816,0 c -6.218,0 -11.259,-5.041 -11.259,-11.257 0,-6.223 5.041,-11.257 11.259,-11.257 6.22,0 11.257,5.034 11.257,11.257 0,6.216 -5.037,11.257 -11.257,11.257 z"
id="path54"
inkscape:connector-curvature="0"
style="fill:#fef3df" /><path
d="M 86.265,0 C 68.102,16.373 86.113,41.427 86.258,41.628 97.061,36.47 108.751,32.874 121.042,31.141 97.629,27.686 86.265,0 86.265,0 Z"
id="path56"
inkscape:connector-curvature="0"
style="fill:#fef3df" /><path
d="m 186.204,0 c 0,0 -10.863,26.476 -33.231,30.883 11.992,1.493 23.435,4.752 34.062,9.509 C 190.383,35.136 202.036,14.271 186.204,0 Z"
id="path58"
inkscape:connector-curvature="0"
style="fill:#fef3df" /></g><g
id="g60"><path
d="m 217.913,176.038 c 2.647,-8.964 6.55187,-25.89162 6.55187,-35.73662 C 224.46487,90.252379 185.208,56.4 137.728,50.502 c -2.157,28.03 3.629,87.043 80.185,125.536 z m -47.53,-58.345 c 0,-6.97 5.651,-12.614 12.614,-12.614 6.968,0 12.617,5.645 12.617,12.614 0,6.964 -5.649,12.611 -12.617,12.611 -6.963,0 -12.614,-5.646 -12.614,-12.611 z"
id="path62"
inkscape:connector-curvature="0"
style="fill:#87654a"
sodipodi:nodetypes="csccsssss" /></g><g
id="brown"><path
d="m 312.658,283.772 c 0,0 -0.487,-1.021 -1.037,-2.733 -3.758,3.317 -13.036,10.236 -27.03,12.416 l 0,-10e-4 c -0.009,0.002 -0.019,0.003 -0.027,0.005 -4.044,0.628 -8.479,0.863 -13.29,0.497 l 0,28.141 c 2.059,-0.801 4.607,-1.834 7.477,-3.083 5.462,-2.377 12.093,-5.542 18.771,-9.395 0.027,-0.016 0.054,-0.031 0.081,-0.047 8.158,-4.713 16.37,-10.452 22.593,-17.052 -5.506,-3.961 -7.538,-8.748 -7.538,-8.748 z"
id="path65"
inkscape:connector-curvature="0"
style="fill:#b58765" /><path
d="m 12.549,52.242 c 17.4,-4.193 32.83,4.656 41.744,11.633 C 59.888,58.449 66.009,53.565 72.57,49.301 48.272,18.498 2.169,37.201 2.169,37.201 -1.114,67.502 15.288,84.594 31.672,94.01 33.023,91.461 34.462,88.966 35.986,86.53 15.363,72.699 12.549,52.242 12.549,52.242 Z"
id="path67"
inkscape:connector-curvature="0"
style="fill:#b58765" /><path
d="m 200.376,47.398 c 6.909,4.205 13.356,9.091 19.26,14.558 9.146,-6.545 23.345,-13.529 39.176,-9.714 0,0 -2.527,18.332 -20.291,32.021 1.633,2.485 3.175,5.034 4.624,7.643 15.141,-9.784 29.097,-26.539 26.046,-54.704 0,-10e-4 -44.152,-17.909 -68.815,10.196 z"
id="path69"
inkscape:connector-curvature="0"
style="fill:#b58765" /><path
d="m 138.854,50.502 c -3.841,-0.478 -8.875,-0.728 -12.842,-0.728 -37.806,0 -70.502,22.31 -86.15,54.73 -1.045,4.357 -1.603,8.897 -1.603,13.612 0,1.454 0.085,2.787 0.121,4.175 0.127,3.935 0.448,7.585 0.855,11.135 4.291755,24.95762 7.959057,42.49186 13.464,66.758 0.056,0.407 0.164,0.804 0.224,1.211 0.617,4.028 1.642,7.992 3.025,11.854 -0.029,-0.578 -0.067,-1.153 -0.067,-1.735 0,-28.325 35.089,-51.289 78.388,-51.289 35.325,0 65.181,15.292 74.977,36.308 3.616,-6.409 6.536,-13.277 8.668,-20.495 C 179.98905,152.54886 163.9995,134.88987 153.25313,111.82124 142.50675,88.752624 137.775,64.517 138.854,50.502 Z m -47.73,79.802 c -6.97,0 -12.612,-5.646 -12.612,-12.611 0,-6.97 5.642,-12.614 12.612,-12.614 6.964,0 12.611,5.645 12.611,12.614 0.001,6.964 -5.648,12.611 -12.611,12.611 z"
id="path71"
inkscape:connector-curvature="0"
style="fill:#b58765"
sodipodi:nodetypes="cscscccccssccscssscs" /></g></g></svg>

Before

Width:  |  Height:  |  Size: 14 KiB

View File

@@ -1,7 +0,0 @@
$mdThemingProvider.definePalette("sogo-green",{50:"eaf5e9",100:"cbe5c8",200:"aad6a5",300:"88c781",400:"66b86a",500:"56b04c",600:"4da143",700:"388e3c",800:"367d2e",900:"225e1b",A100:"ffffff",A200:"69f0ae",A400:"00e676",A700:"00c853",contrastDefaultColor:"dark",contrastLightColors:["300","400","500","600","700","800","900"]})
$mdThemingProvider.definePalette("sogo-blue",{50:"f0faf9",100:"e1f5f3",200:"ceebe8",300:"bfe0dd",400:"b2d6d3",500:"a1ccc8",600:"8ebfbb",700:"7db3b0",800:"639997",900:"4d8080",A100:"d4f7fa",A200:"c3f5fa",A400:"53e3f0",A700:"00b0c0",contrastDefaultColor:"light",contrastDarkColors:["50","100","200"]})
$mdThemingProvider.definePalette("sogo-grey",$mdThemingProvider.extendPalette("grey",{1e3:"baa870"}))
var primarySettings = {default:"900","hue-1":"400","hue-2":"800","hue-3":"A700"}
var accentSettings = {default:"500","hue-1":"A100","hue-2":"300","hue-3":"A700"}
var backgroundSettings = {}

View File

@@ -1,34 +1,36 @@
/* EXAMPLE - EXAMPLE - EXAMPLE - EXAMPLE - EXAMPLE - EXAMPLE - EXAMPLE
(function() { (function() {
'use strict'; 'use strict';
angular.module('SOGo.Common') angular.module('SOGo.Common')
.config(configure) .config(configure)
configure.$inject = ['$mdThemingProvider']; configure.$inject = ['$mdThemingProvider'];
function configure($mdThemingProvider) { function configure($mdThemingProvider) {
var greyMap = $mdThemingProvider.extendPalette('grey', {
$mdThemingProvider.definePalette("sogo-green",{50:"eaf5e9",100:"cbe5c8",200:"aad6a5",300:"88c781",400:"66b86a",500:"56b04c",600:"4da143",700:"388e3c",800:"367d2e",900:"225e1b",A100:"ffffff",A200:"69f0ae",A400:"00e676",A700:"00c853",contrastDefaultColor:"dark",contrastLightColors:["300","400","500","600","700","800","900"]}) '200': 'F5F5F5',
$mdThemingProvider.definePalette("sogo-blue",{50:"f0faf9",100:"e1f5f3",200:"ceebe8",300:"bfe0dd",400:"b2d6d3",500:"a1ccc8",600:"8ebfbb",700:"7db3b0",800:"639997",900:"4d8080",A100:"d4f7fa",A200:"c3f5fa",A400:"53e3f0",A700:"00b0c0",contrastDefaultColor:"light",contrastDarkColors:["50","100","200"]}) '300': 'E5E5E5',
$mdThemingProvider.definePalette("sogo-grey",$mdThemingProvider.extendPalette("grey",{1e3:"baa870"})) '1000': '4C566A'
var primarySettings = {default:"900","hue-1":"400","hue-2":"800","hue-3":"A700"}
var accentSettings = {default:"500","hue-1":"A100","hue-2":"300","hue-3":"A700"}
var backgroundSettings = {}
var primary = $mdThemingProvider.extendPalette('sogo-blue', {});
var accent = $mdThemingProvider.extendPalette('sogo-green', {
'A100': 'ffffff'
}); });
var background = $mdThemingProvider.extendPalette('sogo-grey', {}); var greenCow = $mdThemingProvider.extendPalette('green', {
'600': 'E5E5E5'
$mdThemingProvider.definePalette('primary-cow', primary); });
$mdThemingProvider.definePalette('accent-cow', accent); $mdThemingProvider.definePalette('frost-grey', greyMap);
$mdThemingProvider.definePalette('background-cow', background); $mdThemingProvider.definePalette('green-cow', greenCow);
$mdThemingProvider.theme('default') $mdThemingProvider.theme('default')
.primaryPalette('primary-cow', primarySettings) .primaryPalette('green-cow', {
.accentPalette('accent-cow', accentSettings) 'default': '400',
.backgroundPalette('background-cow', backgroundSettings); 'hue-1': '400',
'hue-2': '600',
'hue-3': 'A700'
})
.accentPalette('green', {
'default': '600',
'hue-1': '300',
'hue-2': '300',
'hue-3': 'A700'
})
.backgroundPalette('frost-grey');
$mdThemingProvider.generateThemesOnDemand(false); $mdThemingProvider.generateThemesOnDemand(false);
} }
})(); })();
*/

View File

@@ -103,12 +103,9 @@ $template_data = [
'rsettings' => $rsettings, 'rsettings' => $rsettings,
'rspamd_regex_maps' => $rspamd_regex_maps, 'rspamd_regex_maps' => $rspamd_regex_maps,
'logo_specs' => customize('get', 'main_logo_specs'), 'logo_specs' => customize('get', 'main_logo_specs'),
'favicon_specs' => customize('get', 'favicon_specs'),
'ip_check' => customize('get', 'ip_check'), 'ip_check' => customize('get', 'ip_check'),
'password_complexity' => password_complexity('get'), 'password_complexity' => password_complexity('get'),
'show_rspamd_global_filters' => @$_SESSION['show_rspamd_global_filters'], 'show_rspamd_global_filters' => @$_SESSION['show_rspamd_global_filters'],
'sogo_palettes' => $GLOBALS['SOGO_PALETTES'],
'sogo_theme' => customize('get', 'sogo_theme'),
'lang_admin' => json_encode($lang['admin']), 'lang_admin' => json_encode($lang['admin']),
'lang_datatables' => json_encode($lang['datatables']) 'lang_datatables' => json_encode($lang['datatables'])
]; ];

View File

@@ -5602,109 +5602,6 @@ paths:
description: You can list all mailboxes existing in system for a specific domain. description: You can list all mailboxes existing in system for a specific domain.
operationId: Get mailboxes of a domain operationId: Get mailboxes of a domain
summary: Get mailboxes of a domain summary: Get mailboxes of a domain
/api/v1/edit/sogo_theme/:
post:
responses:
"401":
$ref: "#/components/responses/Unauthorized"
"200":
content:
application/json:
examples:
response:
value:
- type: success
log:
- customize
- edit
- sogo_theme
- primary: "brown"
accent: "brown"
background: "amber"
msg:
- sogo_theme_modified
schema:
properties:
log:
description: contains request object
items: {}
type: array
msg:
items: {}
type: array
type:
enum:
- success
- danger
- error
type: string
type: object
description: OK
headers: {}
tags:
- Customize
description: >-
Using this endpoint you can edit the sogo theme. SOGo has to be restarted after each change.
operationId: Edit SOGo theme
requestBody:
content:
application/json:
schema:
example:
primary: "brown"
accent: "brown"
background: "amber"
summary: Edit SOGo theme
/api/v1/delete/sogo_theme/:
post:
responses:
"401":
$ref: "#/components/responses/Unauthorized"
"200":
content:
application/json:
examples:
response:
value:
- type: success
log:
- customize
- delete
- sogo_theme
- items:
- sogo-theme
msg: "sogo_theme_removed"
schema:
properties:
log:
description: contains request object
items: {}
type: array
msg:
items: {}
type: array
type:
enum:
- success
- danger
- error
type: string
type: object
description: OK
headers: {}
tags:
- Customize
description: >-
Using this endpoint you can reset the sogo theme. SOGo has to be restarted after each change.
operationId: Reset SOGo theme
requestBody:
content:
application/json:
schema:
example:
- items:
- "sogo-theme"
summary: Reset SOGo theme
tags: tags:
- name: Domains - name: Domains
@@ -5749,5 +5646,3 @@ tags:
description: Get the status of your cow description: Get the status of your cow
- name: Ratelimits - name: Ratelimits
description: Edit domain ratelimits description: Edit domain ratelimits
- name: Customize
description: You can customize mailcow's appearance

View File

@@ -49,7 +49,9 @@ function bcc($_action, $_data = null, $_attr = null) {
} }
elseif (filter_var($local_dest, FILTER_VALIDATE_EMAIL)) { elseif (filter_var($local_dest, FILTER_VALIDATE_EMAIL)) {
$mailbox = mailbox('get', 'mailbox_details', $local_dest); $mailbox = mailbox('get', 'mailbox_details', $local_dest);
if ($mailbox === false && array_key_exists($local_dest, array_merge($direct_aliases, $shared_aliases)) === false) { $shared_aliases = mailbox('get', 'shared_aliases');
$direct_aliases = mailbox('get', 'direct_aliases');
if ($mailbox === false && in_array($local_dest, array_merge($direct_aliases, $shared_aliases)) === false) {
$_SESSION['return'][] = array( $_SESSION['return'][] = array(
'type' => 'danger', 'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_data, $_attr), 'log' => array(__FUNCTION__, $_action, $_data, $_attr),

View File

@@ -73,81 +73,6 @@ function customize($_action, $_item, $_data = null) {
); );
return false; return false;
} }
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'set_logo'));
$_SESSION['return'][] = array(
'type' => 'success',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'upload_success'
);
break;
case 'favicon':
if (in_array($_data['favicon']['type'], array('image/png', 'image/x-icon'))) {
try {
if (file_exists($_data['favicon']['tmp_name']) !== true) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'img_tmp_missing'
);
return false;
}
$image = new Imagick($_data['favicon']['tmp_name']);
if ($image->valid() !== true) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'img_invalid'
);
return false;
}
$available_sizes = array(32, 128, 180, 192, 256);
if ($image->getImageWidth() != $image->getImageHeight()) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'img_invalid'
);
return false;
}
if (!in_array($image->getImageWidth(), $available_sizes)) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'img_invalid'
);
return false;
}
$image->destroy();
}
catch (ImagickException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'img_invalid'
);
return false;
}
}
else {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'invalid_mime_type'
);
return false;
}
try {
$redis->Set('FAVICON', 'data:' . $_data['favicon']['type'] . ';base64,' . base64_encode(file_get_contents($_data['favicon']['tmp_name'])));
}
catch (RedisException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => array('redis_error', $e)
);
return false;
}
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'set_favicon'));
$_SESSION['return'][] = array( $_SESSION['return'][] = array(
'type' => 'success', 'type' => 'success',
'log' => array(__FUNCTION__, $_action, $_item, $_data), 'log' => array(__FUNCTION__, $_action, $_item, $_data),
@@ -254,34 +179,6 @@ function customize($_action, $_item, $_data = null) {
'msg' => 'ip_check_opt_in_modified' 'msg' => 'ip_check_opt_in_modified'
); );
break; break;
case 'sogo_theme':
$_data['primary'] = (isset($_data['primary']) && in_array($_data['primary'], $GLOBALS['SOGO_PALETTES'])) ? $_data['primary'] : 'green';
$_data['accent'] = (isset($_data['accent']) && in_array($_data['accent'], $GLOBALS['SOGO_PALETTES'])) ? $_data['accent'] : 'green';
$_data['background'] = (isset($_data['background']) && in_array($_data['background'], $GLOBALS['SOGO_PALETTES'])) ? $_data['background'] : 'grey';
try {
$redis->hSet('SOGO_THEME', 'primary', $_data['primary']);
$redis->hSet('SOGO_THEME', 'accent', $_data['accent']);
$redis->hSet('SOGO_THEME', 'background', $_data['background']);
}
catch (RedisException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => array('redis_error', $e)
);
return false;
}
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'customize_enable'));
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'set_theme'));
$_SESSION['return'][] = array(
'type' => 'success',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'sogo_theme_modified'
);
return true;
break;
} }
break; break;
case 'delete': case 'delete':
@@ -306,7 +203,6 @@ function customize($_action, $_item, $_data = null) {
case 'main_logo': case 'main_logo':
try { try {
if ($redis->del('MAIN_LOGO')) { if ($redis->del('MAIN_LOGO')) {
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'remove_logo'));
$_SESSION['return'][] = array( $_SESSION['return'][] = array(
'type' => 'success', 'type' => 'success',
'log' => array(__FUNCTION__, $_action, $_item, $_data), 'log' => array(__FUNCTION__, $_action, $_item, $_data),
@@ -324,51 +220,6 @@ function customize($_action, $_item, $_data = null) {
return false; return false;
} }
break; break;
case 'favicon':
try {
if ($redis->del('FAVICON')) {
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'remove_favicon'));
$_SESSION['return'][] = array(
'type' => 'success',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'reset_favicon'
);
return true;
}
}
catch (RedisException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => array('redis_error', $e)
);
return false;
}
break;
case 'sogo_theme':
try {
$redis->hSet('SOGO_THEME', 'primary', 'sogo-blue');
$redis->hSet('SOGO_THEME', 'accent', 'sogo-green');
$redis->hSet('SOGO_THEME', 'background', 'sogo-grey');
}
catch (RedisException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => array('redis_error', $e)
);
return false;
}
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'set_theme'));
$docker_return = docker('post', 'sogo-mailcow', 'exec', array('cmd' => 'sogo', 'task' => 'customize_disable'));
$_SESSION['return'][] = array(
'type' => 'success',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'sogo_theme_removed'
);
return true;
break;
} }
break; break;
case 'get': case 'get':
@@ -400,19 +251,6 @@ function customize($_action, $_item, $_data = null) {
return false; return false;
} }
break; break;
case 'favicon':
try {
return $redis->get('FAVICON');
}
catch (RedisException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => array('redis_error', $e)
);
return false;
}
break;
case 'ui_texts': case 'ui_texts':
try { try {
$data['title_name'] = ($title_name = $redis->get('TITLE_NAME')) ? $title_name : 'mailcow UI'; $data['title_name'] = ($title_name = $redis->get('TITLE_NAME')) ? $title_name : 'mailcow UI';
@@ -457,25 +295,6 @@ function customize($_action, $_item, $_data = null) {
return false; return false;
} }
break; break;
case 'favicon_specs':
try {
$image = new Imagick();
$img_data = explode('base64,', customize('get', 'favicon'));
if ($img_data[1]) {
$image->readImageBlob(base64_decode($img_data[1]));
return $image->identifyImage();
}
return false;
}
catch (ImagickException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => 'imagick_exception'
);
return false;
}
break;
case 'ip_check': case 'ip_check':
try { try {
$ip_check = ($ip_check = $redis->get('IP_CHECK')) ? $ip_check : 0; $ip_check = ($ip_check = $redis->get('IP_CHECK')) ? $ip_check : 0;
@@ -490,28 +309,6 @@ function customize($_action, $_item, $_data = null) {
return false; return false;
} }
break; break;
case 'sogo_theme':
$data = array();
try {
$data['primary'] = $redis->hGet('SOGO_THEME', 'primary');
$data['accent'] = $redis->hGet('SOGO_THEME', 'accent');
$data['background'] = $redis->hGet('SOGO_THEME', 'background');
}
catch (RedisException $e) {
$_SESSION['return'][] = array(
'type' => 'danger',
'log' => array(__FUNCTION__, $_action, $_item, $_data),
'msg' => array('redis_error', $e)
);
return false;
}
$data['primary'] = empty($data['primary']) ? 'sogo-blue' : $data['primary'];
$data['accent'] = empty($data['accent']) ? 'sogo-green' : $data['accent'];
$data['background'] = empty($data['background']) ? 'sogo-grey' : $data['background'];
return $data;
break;
} }
break; break;
} }

View File

@@ -3965,6 +3965,39 @@ function mailbox($_action, $_type, $_data = null, $_extra = null) {
} }
return $aliasdomaindata; return $aliasdomaindata;
break; break;
case 'shared_aliases':
$shared_aliases = array();
$stmt = $pdo->query("SELECT `address` FROM `alias`
WHERE `goto` REGEXP ','
AND `address` NOT LIKE '@%'
AND `goto` != `address`");
$rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
while($row = array_shift($rows)) {
$domain = explode("@", $row['address'])[1];
if (hasDomainAccess($_SESSION['mailcow_cc_username'], $_SESSION['mailcow_cc_role'], $domain)) {
$shared_aliases[] = $row['address'];
}
}
return $shared_aliases;
break;
case 'direct_aliases':
$direct_aliases = array();
$stmt = $pdo->query("SELECT `address` FROM `alias`
WHERE `goto` NOT LIKE '%,%'
AND `address` NOT LIKE '@%'
AND `goto` != `address`");
$rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
while($row = array_shift($rows)) {
$domain = explode("@", $row['address'])[1];
if (hasDomainAccess($_SESSION['mailcow_cc_username'], $_SESSION['mailcow_cc_role'], $domain)) {
$direct_aliases[] = $row['address'];
}
}
return $direct_aliases;
break;
case 'domains': case 'domains':
$domains = array(); $domains = array();
if ($_SESSION['mailcow_cc_role'] != "admin" && $_SESSION['mailcow_cc_role'] != "domainadmin") { if ($_SESSION['mailcow_cc_role'] != "admin" && $_SESSION['mailcow_cc_role'] != "domainadmin") {
@@ -4956,9 +4989,10 @@ function mailbox($_action, $_type, $_data = null, $_extra = null) {
$stmt->execute(array( $stmt->execute(array(
':username' => $username ':username' => $username
)); ));
$stmt = $pdo->prepare("DELETE FROM `sender_acl` WHERE `logged_in_as` = :username"); $stmt = $pdo->prepare("DELETE FROM `sender_acl` WHERE `logged_in_as` = :logged_in_as OR `send_as` = :send_as");
$stmt->execute(array( $stmt->execute(array(
':username' => $username ':logged_in_as' => $username,
':send_as' => $username
)); ));
// fk, better safe than sorry // fk, better safe than sorry
$stmt = $pdo->prepare("DELETE FROM `user_acl` WHERE `username` = :username"); $stmt = $pdo->prepare("DELETE FROM `user_acl` WHERE `username` = :username");

View File

@@ -40,7 +40,6 @@ $globalVariables = [
'ui_texts' => $UI_TEXTS, 'ui_texts' => $UI_TEXTS,
'css_path' => '/cache/'.basename($CSSPath), 'css_path' => '/cache/'.basename($CSSPath),
'logo' => customize('get', 'main_logo'), 'logo' => customize('get', 'main_logo'),
'favicon' => customize('get', 'favicon'),
'available_languages' => $AVAILABLE_LANGUAGES, 'available_languages' => $AVAILABLE_LANGUAGES,
'lang' => $lang, 'lang' => $lang,
'skip_sogo' => (getenv('SKIP_SOGO') == 'y'), 'skip_sogo' => (getenv('SKIP_SOGO') == 'y'),

View File

@@ -63,7 +63,7 @@ if (isset($_POST["login_user"]) && isset($_POST["pass_user"])) {
unset($_SESSION['index_query_string']); unset($_SESSION['index_query_string']);
if (in_array('mobileconfig', $http_parameters)) { if (in_array('mobileconfig', $http_parameters)) {
if (in_array('only_email', $http_parameters)) { if (in_array('only_email', $http_parameters)) {
header("Location: /mobileconfig.php?email_only"); header("Location: /mobileconfig.php?only_email");
die(); die();
} }
header("Location: /mobileconfig.php"); header("Location: /mobileconfig.php");
@@ -125,14 +125,6 @@ if (isset($_SESSION['mailcow_cc_role']) && $_SESSION['mailcow_cc_role'] == "admi
if (isset($_POST["reset_main_logo"])) { if (isset($_POST["reset_main_logo"])) {
customize('delete', 'main_logo'); customize('delete', 'main_logo');
} }
if (isset($_POST["submit_favicon"])) {
if ($_FILES['favicon']['error'] == 0) {
customize('add', 'favicon', $_FILES);
}
}
if (isset($_POST["reset_favicon"])) {
customize('delete', 'favicon');
}
// Some actions will not be available via API // Some actions will not be available via API
if (isset($_POST["license_validate_now"])) { if (isset($_POST["license_validate_now"])) {
license('verify'); license('verify');

View File

@@ -210,30 +210,6 @@ $FIDO2_USER_PRESENT_FLAG = true;
$FIDO2_FORMATS = array('apple', 'android-key', 'android-safetynet', 'fido-u2f', 'none', 'packed', 'tpm'); $FIDO2_FORMATS = array('apple', 'android-key', 'android-safetynet', 'fido-u2f', 'none', 'packed', 'tpm');
$SOGO_PALETTES = array(
'sogo-green',
'sogo-blue',
'sogo-grey',
'red',
'pink',
'purple',
'deep-purple',
'indigo',
'blue',
'light-blue',
'cyan',
'teal',
'green',
'light-green',
'lime',
'yellow',
'amber',
'orange',
'deep-orange',
'brown',
'grey',
'blue-grey'
);
// Set visible Rspamd maps in mailcow UI, do not change unless you know what you are doing // Set visible Rspamd maps in mailcow UI, do not change unless you know what you are doing
$RSPAMD_MAPS = array( $RSPAMD_MAPS = array(

View File

@@ -1,3 +1,13 @@
const LOCALE = undefined;
const DATETIME_FORMAT = {
year: "numeric",
month: "2-digit",
day: "2-digit",
hour: "2-digit",
minute: "2-digit",
second: "2-digit"
};
$(document).ready(function() { $(document).ready(function() {
// mailcow alert box generator // mailcow alert box generator
window.mailcow_alert_box = function(message, type) { window.mailcow_alert_box = function(message, type) {

View File

@@ -1,13 +1,3 @@
const LOCALE = undefined;
const DATETIME_FORMAT = {
year: "numeric",
month: "2-digit",
day: "2-digit",
hour: "2-digit",
minute: "2-digit",
second: "2-digit"
};
$(document).ready(function() { $(document).ready(function() {
// Parse seconds ago to date // Parse seconds ago to date
// Get "now" timestamp // Get "now" timestamp
@@ -43,7 +33,7 @@ $(document).ready(function() {
if (mailcow_info.branch === "master"){ if (mailcow_info.branch === "master"){
check_update(mailcow_info.version_tag, mailcow_info.project_url); check_update(mailcow_info.version_tag, mailcow_info.project_url);
} }
$("#maiclow_version").click(function(){ $("#mailcow_version").click(function(){
if (mailcow_cc_role !== "admin" && mailcow_cc_role !== "domainadmin" || mailcow_info.branch !== "master") if (mailcow_cc_role !== "admin" && mailcow_cc_role !== "domainadmin" || mailcow_info.branch !== "master")
return; return;
@@ -829,13 +819,10 @@ jQuery(function($){
url: '/api/v1/get/rspamd/actions', url: '/api/v1/get/rspamd/actions',
async: true, async: true,
success: function(data){ success: function(data){
console.log(data);
var total = 0; var total = 0;
$(data).map(function(){total += this[1];}); $(data).map(function(){total += this[1];});
var labels = $.makeArray($(data).map(function(){return this[0] + ' ' + Math.round(this[1]/total * 100) + '%';})); var labels = $.makeArray($(data).map(function(){return this[0] + ' ' + Math.round(this[1]/total * 100) + '%';}));
var values = $.makeArray($(data).map(function(){return this[1];})); var values = $.makeArray($(data).map(function(){return this[1];}));
console.log(values);
var graphdata = { var graphdata = {
labels: labels, labels: labels,
@@ -951,12 +938,15 @@ jQuery(function($){
title: 'Score', title: 'Score',
data: 'score', data: 'score',
defaultContent: '', defaultContent: '',
class: 'text-nowrap',
createdCell: function(td, cellData) { createdCell: function(td, cellData) {
$(td).attr({ $(td).attr({
"data-order": cellData.sortBy, "data-order": cellData.sortBy,
"data-sort": cellData.sortBy "data-sort": cellData.sortBy
}); });
$(td).html(cellData.value); },
render: function (data) {
return data.value;
} }
}, },
{ {
@@ -979,7 +969,9 @@ jQuery(function($){
"data-order": cellData.sortBy, "data-order": cellData.sortBy,
"data-sort": cellData.sortBy "data-sort": cellData.sortBy
}); });
$(td).html(cellData.value); },
render: function (data) {
return data.value;
} }
}, },
{ {
@@ -1302,6 +1294,12 @@ function update_stats(timeout=5){
$("#host_cpu_usage").text(parseInt(data.cpu.usage).toString() + "%"); $("#host_cpu_usage").text(parseInt(data.cpu.usage).toString() + "%");
$("#host_memory_total").text((data.memory.total / (1024 ** 3)).toFixed(2).toString() + "GB"); $("#host_memory_total").text((data.memory.total / (1024 ** 3)).toFixed(2).toString() + "GB");
$("#host_memory_usage").text(parseInt(data.memory.usage).toString() + "%"); $("#host_memory_usage").text(parseInt(data.memory.usage).toString() + "%");
if (data.architecture == "aarch64"){
$("#host_architecture").html('<span data-bs-toggle="tooltip" data-bs-placement="top" title="' + lang_debug.wip +'">' + data.architecture + ' ⚠️</span>');
}
else {
$("#host_architecture").html(data.architecture);
}
// update cpu and mem chart // update cpu and mem chart
var cpu_chart = Chart.getChart("host_cpu_chart"); var cpu_chart = Chart.getChart("host_cpu_chart");

View File

@@ -1458,30 +1458,37 @@ jQuery(function($){
} }
function draw_bcc_table() { function draw_bcc_table() {
$.get("/api/v1/get/bcc-destination-options", function(data){ $.get("/api/v1/get/bcc-destination-options", function(data){
var optgroup = "";
// Domains // Domains
var optgroup = "<optgroup label='" + lang.domains + "'>"; if (data.domains && data.domains.length > 0) {
$.each(data.domains, function(index, domain){ optgroup = "<optgroup label='" + lang.domains + "'>";
optgroup += "<option value='" + domain + "'>" + domain + "</option>"; $.each(data.domains, function(index, domain){
}); optgroup += "<option value='" + domain + "'>" + domain + "</option>";
optgroup += "</optgroup>";
$('#bcc-local-dest').append(optgroup);
// Alias domains
var optgroup = "<optgroup label='" + lang.domain_aliases + "'>";
$.each(data.alias_domains, function(index, alias_domain){
optgroup += "<option value='" + alias_domain + "'>" + alias_domain + "</option>";
});
optgroup += "</optgroup>"
$('#bcc-local-dest').append(optgroup);
// Mailboxes and aliases
$.each(data.mailboxes, function(mailbox, aliases){
var optgroup = "<optgroup label='" + mailbox + "'>";
$.each(aliases, function(index, alias){
optgroup += "<option value='" + alias + "'>" + alias + "</option>";
}); });
optgroup += "</optgroup>"; optgroup += "</optgroup>";
$('#bcc-local-dest').append(optgroup); $('#bcc-local-dest').append(optgroup);
}); }
// Finish // Alias domains
if (data.alias_domains && data.alias_domains.length > 0) {
optgroup = "<optgroup label='" + lang.domain_aliases + "'>";
$.each(data.alias_domains, function(index, alias_domain){
optgroup += "<option value='" + alias_domain + "'>" + alias_domain + "</option>";
});
optgroup += "</optgroup>"
$('#bcc-local-dest').append(optgroup);
}
// Mailboxes and aliases
if (data.mailboxes && Object.keys(data.mailboxes).length > 0) {
$.each(data.mailboxes, function(mailbox, aliases){
optgroup = "<optgroup label='" + mailbox + "'>";
$.each(aliases, function(index, alias){
optgroup += "<option value='" + alias + "'>" + alias + "</option>";
});
optgroup += "</optgroup>";
$('#bcc-local-dest').append(optgroup);
});
}
// Recreate picker
$('#bcc-local-dest').selectpicker('refresh'); $('#bcc-local-dest').selectpicker('refresh');
}); });
@@ -2326,16 +2333,19 @@ jQuery(function($){
// detect element visibility changes // detect element visibility changes
function onVisible(element, callback) { function onVisible(element, callback) {
$(document).ready(function() { $(document).ready(function() {
element_object = document.querySelector(element); let element_object = document.querySelector(element);
if (element_object === null) return; if (element_object === null) return;
new IntersectionObserver((entries, observer) => { let observer = new IntersectionObserver((entries, observer) => {
entries.forEach(entry => { entries.forEach(entry => {
if(entry.intersectionRatio > 0) { if(entry.intersectionRatio > 0) {
callback(element_object); callback(element_object);
observer.unobserve(element_object);
} }
}); });
}).observe(element_object); })
observer.observe(element_object);
}); });
} }

View File

@@ -127,6 +127,20 @@ jQuery(function($){
} }
} }
function createSortableDate(td, cellData, date_string = false) {
if (date_string)
var date = new Date(cellData);
else
var date = new Date(cellData ? cellData * 1000 : 0);
var timestamp = date.getTime();
$(td).attr({
"data-order": timestamp,
"data-sort": timestamp
});
$(td).html(date.toLocaleDateString(LOCALE, DATETIME_FORMAT));
}
function draw_tla_table() { function draw_tla_table() {
// just recalc width if instance already exists // just recalc width if instance already exists
if ($.fn.DataTable.isDataTable('#tla_table') ) { if ($.fn.DataTable.isDataTable('#tla_table') ) {
@@ -144,6 +158,7 @@ jQuery(function($){
"tr" + "tr" +
"<'row'<'col-sm-12 col-md-5'i><'col-sm-12 col-md-7'p>>", "<'row'<'col-sm-12 col-md-5'i><'col-sm-12 col-md-7'p>>",
language: lang_datatables, language: lang_datatables,
order: [[4, 'desc']],
ajax: { ajax: {
type: "GET", type: "GET",
url: "/api/v1/get/time_limited_aliases", url: "/api/v1/get/time_limited_aliases",
@@ -191,18 +206,16 @@ jQuery(function($){
title: lang.alias_valid_until, title: lang.alias_valid_until,
data: 'validity', data: 'validity',
defaultContent: '', defaultContent: '',
render: function (data, type) { createdCell: function(td, cellData) {
var date = new Date(data ? data * 1000 : 0); createSortableDate(td, cellData)
return date.toLocaleDateString(undefined, {year: "numeric", month: "2-digit", day: "2-digit", hour: "2-digit", minute: "2-digit", second: "2-digit"});
} }
}, },
{ {
title: lang.created_on, title: lang.created_on,
data: 'created', data: 'created',
defaultContent: '', defaultContent: '',
render: function (data, type) { createdCell: function(td, cellData) {
var date = new Date(data.replace(/-/g, "/")); createSortableDate(td, cellData, true)
return date.toLocaleDateString(undefined, {year: "numeric", month: "2-digit", day: "2-digit", hour: "2-digit", minute: "2-digit", second: "2-digit"});
} }
}, },
{ {

View File

@@ -1744,9 +1744,6 @@ if (isset($_GET['query'])) {
case "rlhash": case "rlhash":
echo ratelimit('delete', null, implode($items)); echo ratelimit('delete', null, implode($items));
break; break;
case "sogo_theme":
process_delete_return(customize('delete', 'sogo_theme', $items));
break;
// return no route found if no case is matched // return no route found if no case is matched
default: default:
http_response_code(404); http_response_code(404);
@@ -1941,9 +1938,6 @@ if (isset($_GET['query'])) {
case "ip_check": case "ip_check":
process_edit_return(customize('edit', 'ip_check', $attr)); process_edit_return(customize('edit', 'ip_check', $attr));
break; break;
case "sogo_theme":
process_edit_return(customize('edit', 'sogo_theme', $attr));
break;
case "self": case "self":
if ($_SESSION['mailcow_cc_role'] == "domainadmin") { if ($_SESSION['mailcow_cc_role'] == "domainadmin") {
process_edit_return(domain_admin('edit', $attr)); process_edit_return(domain_admin('edit', $attr));

View File

@@ -541,7 +541,7 @@
"inactive": "Neaktivní", "inactive": "Neaktivní",
"kind": "Druh", "kind": "Druh",
"last_modified": "Naposledy změněn", "last_modified": "Naposledy změněn",
"lookup_mx": "Cíl je regulární výraz který se shoduje s MX záznamem (<code>.*google\\.com</code> směřuje veškerou poštu na MX které jsou cílem pro google.com přes tento skok)", "lookup_mx": "Cíl je regulární výraz který se shoduje s MX záznamem (<code>.*\\.google\\.com</code> směřuje veškerou poštu na MX které jsou cílem pro google.com přes tento skok)",
"mailbox": "Úprava mailové schránky", "mailbox": "Úprava mailové schránky",
"mailbox_quota_def": "Výchozí kvóta schránky", "mailbox_quota_def": "Výchozí kvóta schránky",
"mailbox_relayhost_info": "Aplikované jen na uživatelskou schránku a přímé aliasy, přepisuje předávající server domény.", "mailbox_relayhost_info": "Aplikované jen na uživatelskou schránku a přímé aliasy, přepisuje předávající server domény.",

View File

@@ -145,7 +145,6 @@
"ays": "Soll der Vorgang wirklich ausgeführt werden?", "ays": "Soll der Vorgang wirklich ausgeführt werden?",
"ban_list_info": "Übersicht ausgesperrter Netzwerke: <b>Netzwerk (verbleibende Bannzeit) - [Aktionen]</b>.<br />IPs, die zum Entsperren eingereiht werden, verlassen die Liste aktiver Banns nach wenigen Sekunden.<br />Rote Labels sind Indikatoren für aktive Blacklist-Einträge.", "ban_list_info": "Übersicht ausgesperrter Netzwerke: <b>Netzwerk (verbleibende Bannzeit) - [Aktionen]</b>.<br />IPs, die zum Entsperren eingereiht werden, verlassen die Liste aktiver Banns nach wenigen Sekunden.<br />Rote Labels sind Indikatoren für aktive Blacklist-Einträge.",
"change_logo": "Logo ändern", "change_logo": "Logo ändern",
"change_favicon": "Favicon ändern",
"configuration": "Konfiguration", "configuration": "Konfiguration",
"convert_html_to_text": "Konvertiere HTML zu reinem Text", "convert_html_to_text": "Konvertiere HTML zu reinem Text",
"credentials_transport_warning": "<b>Warnung</b>: Das Hinzufügen einer neuen Regel bewirkt die Aktualisierung der Authentifizierungsdaten aller vorhandenen Einträge mit identischem Next Hop.", "credentials_transport_warning": "<b>Warnung</b>: Das Hinzufügen einer neuen Regel bewirkt die Aktualisierung der Authentifizierungsdaten aller vorhandenen Einträge mit identischem Next Hop.",
@@ -217,8 +216,7 @@
"loading": "Bitte warten...", "loading": "Bitte warten...",
"login_time": "Zeit", "login_time": "Zeit",
"logo_info": "Die hochgeladene Grafik wird für die Navigationsleiste auf eine Höhe von 40px skaliert. Für die Darstellung auf der Login-Maske beträgt die skalierte Breite maximal 250px. Eine frei skalierbare Grafik (etwa SVG) wird empfohlen.", "logo_info": "Die hochgeladene Grafik wird für die Navigationsleiste auf eine Höhe von 40px skaliert. Für die Darstellung auf der Login-Maske beträgt die skalierte Breite maximal 250px. Eine frei skalierbare Grafik (etwa SVG) wird empfohlen.",
"favicon_info": "Das Bild muss eine PNG- oder ICO-Datei mit den Abmessungen <code>32 x 32</code>, <code>128 x 128</code>, <code>180 x 180</code>, <code>192 x 192</code> oder <code>256 x 256</code> sein. SOGo muss nachdem ändern neugestartet werden.", "lookup_mx": "Ziel mit MX vergleichen (Regex, etwa <code>.*\\.google\\.com</code>, um alle Ziele mit MX *google.com zu routen)",
"lookup_mx": "Ziel mit MX vergleichen (Regex, etwa <code>.*google\\.com</code>, um alle Ziele mit MX *google.com zu routen)",
"main_name": "\"mailcow UI\" Name", "main_name": "\"mailcow UI\" Name",
"merged_vars_hint": "Ausgegraute Reihen wurden aus der Datei <code>vars.(local.)inc.php</code> gelesen und können hier nicht verändert werden.", "merged_vars_hint": "Ausgegraute Reihen wurden aus der Datei <code>vars.(local.)inc.php</code> gelesen und können hier nicht verändert werden.",
"message": "Nachricht", "message": "Nachricht",
@@ -308,8 +306,6 @@
"sender": "Sender", "sender": "Sender",
"service": "Dienst", "service": "Dienst",
"service_id": "Service", "service_id": "Service",
"sogo_theme": "SOGo Theme",
"sogo_theme_info": "SOGo muss nachdem ändern neugestartet werden.",
"source": "Quelle", "source": "Quelle",
"spamfilter": "Spamfilter", "spamfilter": "Spamfilter",
"subject": "Betreff", "subject": "Betreff",
@@ -502,6 +498,7 @@
} }
}, },
"debug": { "debug": {
"architecture": "Architektur",
"chart_this_server": "Chart (dieser Server)", "chart_this_server": "Chart (dieser Server)",
"containers_info": "Container-Information", "containers_info": "Container-Information",
"container_running": "Läuft", "container_running": "Läuft",
@@ -538,7 +535,8 @@
"update_available": "Es ist ein Update verfügbar", "update_available": "Es ist ein Update verfügbar",
"no_update_available": "Das System ist auf aktuellem Stand", "no_update_available": "Das System ist auf aktuellem Stand",
"update_failed": "Es konnte nicht nach einem Update gesucht werden", "update_failed": "Es konnte nicht nach einem Update gesucht werden",
"username": "Benutzername" "username": "Benutzername",
"wip": "Aktuell noch in Arbeit"
}, },
"diagnostics": { "diagnostics": {
"cname_from_a": "Wert abgeleitet von A/AAAA-Eintrag. Wird unterstützt, sofern der Eintrag auf die korrekte Ressource zeigt.", "cname_from_a": "Wert abgeleitet von A/AAAA-Eintrag. Wird unterstützt, sofern der Eintrag auf die korrekte Ressource zeigt.",
@@ -597,7 +595,7 @@
"inactive": "Inaktiv", "inactive": "Inaktiv",
"kind": "Art", "kind": "Art",
"last_modified": "Zuletzt geändert", "last_modified": "Zuletzt geändert",
"lookup_mx": "Ziel mit MX vergleichen (Regex, etwa <code>.*google\\.com</code>, um alle Ziele mit MX *google.com zu routen)", "lookup_mx": "Ziel mit MX vergleichen (Regex, etwa <code>.*\\.google\\.com</code>, um alle Ziele mit MX *google.com zu routen)",
"mailbox": "Mailbox bearbeiten", "mailbox": "Mailbox bearbeiten",
"mailbox_quota_def": "Standard-Quota einer Mailbox", "mailbox_quota_def": "Standard-Quota einer Mailbox",
"mailbox_relayhost_info": "Wird auf eine Mailbox und direkte Alias-Adressen angewendet. Überschreibt die Einstellung einer Domain.", "mailbox_relayhost_info": "Wird auf eine Mailbox und direkte Alias-Adressen angewendet. Überschreibt die Einstellung einer Domain.",
@@ -1044,7 +1042,6 @@
"relayhost_added": "Map-Eintrag %s wurde hinzugefügt", "relayhost_added": "Map-Eintrag %s wurde hinzugefügt",
"relayhost_removed": "Map-Eintrag %s wurde entfernt", "relayhost_removed": "Map-Eintrag %s wurde entfernt",
"reset_main_logo": "Standardgrafik wurde wiederhergestellt", "reset_main_logo": "Standardgrafik wurde wiederhergestellt",
"reset_favicon": "Standard favicon wurde wiederhergestellt",
"resource_added": "Ressource %s wurde angelegt", "resource_added": "Ressource %s wurde angelegt",
"resource_modified": "Änderungen an Ressource %s wurden gespeichert", "resource_modified": "Änderungen an Ressource %s wurden gespeichert",
"resource_removed": "Ressource %s wurde entfernt", "resource_removed": "Ressource %s wurde entfernt",
@@ -1057,8 +1054,6 @@
"template_modified": "Änderungen am Template %s wurden gespeichert", "template_modified": "Änderungen am Template %s wurden gespeichert",
"template_removed": "Template ID %s wurde gelöscht", "template_removed": "Template ID %s wurde gelöscht",
"sogo_profile_reset": "ActiveSync-Gerät des Benutzers %s wurde zurückgesetzt", "sogo_profile_reset": "ActiveSync-Gerät des Benutzers %s wurde zurückgesetzt",
"sogo_theme_modified": "SOGo Theme wurde gespeichert",
"sogo_theme_removed": "SOGo Theme wurde entfernt",
"tls_policy_map_entry_deleted": "TLS-Richtlinie mit der ID %s wurde gelöscht", "tls_policy_map_entry_deleted": "TLS-Richtlinie mit der ID %s wurde gelöscht",
"tls_policy_map_entry_saved": "TLS-Richtlinieneintrag \"%s\" wurde gespeichert", "tls_policy_map_entry_saved": "TLS-Richtlinieneintrag \"%s\" wurde gespeichert",
"ui_texts": "Änderungen an UI-Texten", "ui_texts": "Änderungen an UI-Texten",

View File

@@ -147,7 +147,6 @@
"ays": "Are you sure you want to proceed?", "ays": "Are you sure you want to proceed?",
"ban_list_info": "See a list of banned IPs below: <b>network (remaining ban time) - [actions]</b>.<br />IPs queued to be unbanned will be removed from the active ban list within a few seconds.<br />Red labels indicate active permanent bans by blacklisting.", "ban_list_info": "See a list of banned IPs below: <b>network (remaining ban time) - [actions]</b>.<br />IPs queued to be unbanned will be removed from the active ban list within a few seconds.<br />Red labels indicate active permanent bans by blacklisting.",
"change_logo": "Change logo", "change_logo": "Change logo",
"change_favicon": "Change favicon",
"configuration": "Configuration", "configuration": "Configuration",
"convert_html_to_text": "Convert HTML to plain text", "convert_html_to_text": "Convert HTML to plain text",
"credentials_transport_warning": "<b>Warning</b>: Adding a new transport map entry will update the credentials for all entries with a matching next hop column.", "credentials_transport_warning": "<b>Warning</b>: Adding a new transport map entry will update the credentials for all entries with a matching next hop column.",
@@ -219,8 +218,7 @@
"loading": "Please wait...", "loading": "Please wait...",
"login_time": "Login time", "login_time": "Login time",
"logo_info": "Your image will be scaled to a height of 40px for the top navigation bar and a max. width of 250px for the start page. A scalable graphic is highly recommended.", "logo_info": "Your image will be scaled to a height of 40px for the top navigation bar and a max. width of 250px for the start page. A scalable graphic is highly recommended.",
"favicon_info": "The image has to be a PNG or ICO file in the dimensions <code>32 x 32</code>, <code>128 x 128</code>, <code>180 x 180</code>, <code>192 x 192</code>, or <code>256 x 256</code>. Restart SOGo after changing the favicon", "lookup_mx": "Destination is a regular expression to match against MX name (<code>.*\\.google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)",
"lookup_mx": "Destination is a regular expression to match against MX name (<code>.*google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)",
"main_name": "\"mailcow UI\" name", "main_name": "\"mailcow UI\" name",
"merged_vars_hint": "Greyed out rows were merged from <code>vars.(local.)inc.php</code> and cannot be modified.", "merged_vars_hint": "Greyed out rows were merged from <code>vars.(local.)inc.php</code> and cannot be modified.",
"message": "Message", "message": "Message",
@@ -313,11 +311,6 @@
"sender": "Sender", "sender": "Sender",
"service": "Service", "service": "Service",
"service_id": "Service ID", "service_id": "Service ID",
"sogo_theme": "SOGo Theme",
"sogo_theme_info": "Restart SOGo after changing the theme.",
"sogo_theme_primary": "Primary Color:",
"sogo_theme_accent": "Accent Color:",
"sogo_theme_background": "Background Color:",
"source": "Source", "source": "Source",
"spamfilter": "Spam filter", "spamfilter": "Spam filter",
"subject": "Subject", "subject": "Subject",
@@ -505,6 +498,7 @@
} }
}, },
"debug": { "debug": {
"architecture": "Architecture",
"chart_this_server": "Chart (this server)", "chart_this_server": "Chart (this server)",
"containers_info": "Container information", "containers_info": "Container information",
"container_running": "Running", "container_running": "Running",
@@ -541,7 +535,8 @@
"update_available": "There is an update available", "update_available": "There is an update available",
"no_update_available": "The System is on the latest version", "no_update_available": "The System is on the latest version",
"update_failed": "Could not check for an Update", "update_failed": "Could not check for an Update",
"username": "Username" "username": "Username",
"wip": "Currently Work in Progress"
}, },
"diagnostics": { "diagnostics": {
"cname_from_a": "Value derived from A/AAAA record. This is supported as long as the record points to the correct resource.", "cname_from_a": "Value derived from A/AAAA record. This is supported as long as the record points to the correct resource.",
@@ -600,7 +595,7 @@
"inactive": "Inactive", "inactive": "Inactive",
"kind": "Kind", "kind": "Kind",
"last_modified": "Last modified", "last_modified": "Last modified",
"lookup_mx": "Destination is a regular expression to match against MX name (<code>.*google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)", "lookup_mx": "Destination is a regular expression to match against MX name (<code>.*\\.google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)",
"mailbox": "Edit mailbox", "mailbox": "Edit mailbox",
"mailbox_quota_def": "Default mailbox quota", "mailbox_quota_def": "Default mailbox quota",
"mailbox_relayhost_info": "Applied to the mailbox and direct aliases only, does override a domain relayhost.", "mailbox_relayhost_info": "Applied to the mailbox and direct aliases only, does override a domain relayhost.",
@@ -1054,7 +1049,6 @@
"relayhost_added": "Map entry %s has been added", "relayhost_added": "Map entry %s has been added",
"relayhost_removed": "Map entry %s has been removed", "relayhost_removed": "Map entry %s has been removed",
"reset_main_logo": "Reset to default logo", "reset_main_logo": "Reset to default logo",
"reset_favicon": "Reset to default favicon",
"resource_added": "Resource %s has been added", "resource_added": "Resource %s has been added",
"resource_modified": "Changes to mailbox %s have been saved", "resource_modified": "Changes to mailbox %s have been saved",
"resource_removed": "Resource %s has been removed", "resource_removed": "Resource %s has been removed",
@@ -1064,8 +1058,6 @@
"settings_map_added": "Added settings map entry", "settings_map_added": "Added settings map entry",
"settings_map_removed": "Removed settings map ID %s", "settings_map_removed": "Removed settings map ID %s",
"sogo_profile_reset": "SOGo profile for user %s was reset", "sogo_profile_reset": "SOGo profile for user %s was reset",
"sogo_theme_modified": "SOGo Theme has been modified",
"sogo_theme_removed": "SOGo Theme has been removed",
"template_added": "Added template %s", "template_added": "Added template %s",
"template_modified": "Changes to template %s have been saved", "template_modified": "Changes to template %s have been saved",
"template_removed": "Template ID %s has been deleted", "template_removed": "Template ID %s has been deleted",

View File

@@ -588,7 +588,7 @@
"unchanged_if_empty": "Si non modifié, laisser en blanc", "unchanged_if_empty": "Si non modifié, laisser en blanc",
"username": "Nom d'utilisateur", "username": "Nom d'utilisateur",
"validate_save": "Valider et sauver", "validate_save": "Valider et sauver",
"lookup_mx": "La destination est une expression régulière qui doit correspondre avec le nom du MX (<code>.*google\\.com</code> pour acheminer tout le courrier destiné à un MX se terminant par google.com via ce saut)", "lookup_mx": "La destination est une expression régulière qui doit correspondre avec le nom du MX (<code>.*\\.google\\.com</code> pour acheminer tout le courrier destiné à un MX se terminant par google.com via ce saut)",
"mailbox_relayhost_info": "S'applique uniquement à la boîte aux lettres et aux alias directs, remplace le relayhost du domaine." "mailbox_relayhost_info": "S'applique uniquement à la boîte aux lettres et aux alias directs, remplace le relayhost du domaine."
}, },
"footer": { "footer": {

View File

@@ -213,7 +213,7 @@
"loading": "Caricamento in corso...", "loading": "Caricamento in corso...",
"login_time": "Ora di accesso", "login_time": "Ora di accesso",
"logo_info": "La tua immagine verrà ridimensionata a 40px di altezza, quando verrà usata nella barra di navigazione in alto, ed ad una larghezza massima di 250px nella schermata iniziale. È altamente consigliato l'utilizzo di un'immagine modulabile.", "logo_info": "La tua immagine verrà ridimensionata a 40px di altezza, quando verrà usata nella barra di navigazione in alto, ed ad una larghezza massima di 250px nella schermata iniziale. È altamente consigliato l'utilizzo di un'immagine modulabile.",
"lookup_mx": "Destination is a regular expression to match against MX name (<code>.*google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)", "lookup_mx": "Destination is a regular expression to match against MX name (<code>.*\\.google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)",
"main_name": "Nome \"mailcow UI\"", "main_name": "Nome \"mailcow UI\"",
"merged_vars_hint": "Greyed out rows were merged from <code>vars.(local.)inc.php</code> and cannot be modified.", "merged_vars_hint": "Greyed out rows were merged from <code>vars.(local.)inc.php</code> and cannot be modified.",
"message": "Messaggio", "message": "Messaggio",
@@ -554,7 +554,7 @@
"hostname": "Hostname", "hostname": "Hostname",
"inactive": "Inattivo", "inactive": "Inattivo",
"kind": "Genere", "kind": "Genere",
"lookup_mx": "Destination is a regular expression to match against MX name (<code>.*google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)", "lookup_mx": "Destination is a regular expression to match against MX name (<code>.*\\.google\\.com</code> to route all mail targeted to a MX ending in google.com over this hop)",
"mailbox": "Modifica casella di posta", "mailbox": "Modifica casella di posta",
"mailbox_quota_def": "Default mailbox quota", "mailbox_quota_def": "Default mailbox quota",
"mailbox_relayhost_info": "Applied to the mailbox and direct aliases only, does override a domain relayhost.", "mailbox_relayhost_info": "Applied to the mailbox and direct aliases only, does override a domain relayhost.",

View File

@@ -539,7 +539,7 @@
"inactive": "Inactiv", "inactive": "Inactiv",
"kind": "Fel", "kind": "Fel",
"last_modified": "Ultima modificare", "last_modified": "Ultima modificare",
"lookup_mx": "Destinația este o expresie regulată care potrivită cu numele MX (<code>.*google\\.com</code> pentru a direcționa toate e-mailurile vizate către un MX care se termină în google.com peste acest hop)", "lookup_mx": "Destinația este o expresie regulată care potrivită cu numele MX (<code>.*\\.google\\.com</code> pentru a direcționa toate e-mailurile vizate către un MX care se termină în google.com peste acest hop)",
"mailbox": "Editează căsuța poștală", "mailbox": "Editează căsuța poștală",
"mailbox_quota_def": "Cota implicită a căsuței poștale", "mailbox_quota_def": "Cota implicită a căsuței poștale",
"mailbox_relayhost_info": "Aplicat numai căsuței poștale și aliasurilor directe, suprascrie un transport dependent de domeniu.", "mailbox_relayhost_info": "Aplicat numai căsuței poștale și aliasurilor directe, suprascrie un transport dependent de domeniu.",

View File

@@ -336,7 +336,9 @@
"validate_license_now": "Получить лицензию на основе GUID с сервера лицензий", "validate_license_now": "Получить лицензию на основе GUID с сервера лицензий",
"verify": "Проверить", "verify": "Проверить",
"yes": "&#10003;", "yes": "&#10003;",
"queue_unban": "разблокировать" "queue_unban": "разблокировать",
"f2b_ban_time_increment": "Время бана увеличивается с каждым баном",
"f2b_max_ban_time": "Максимальное время блокировки"
}, },
"danger": { "danger": {
"access_denied": "Доступ запрещён, или указаны неверные данные", "access_denied": "Доступ запрещён, или указаны неверные данные",

View File

@@ -213,7 +213,7 @@
"loading": "Čakajte prosím ...", "loading": "Čakajte prosím ...",
"login_time": "Čas prihlásenia", "login_time": "Čas prihlásenia",
"logo_info": "Váš obrázok bude upravený na výšku 40px pre vrchný navigačný riadok a na maximálnu šírku 250px pre úvodnú stránku. Odporúča sa škálovateľná grafika.", "logo_info": "Váš obrázok bude upravený na výšku 40px pre vrchný navigačný riadok a na maximálnu šírku 250px pre úvodnú stránku. Odporúča sa škálovateľná grafika.",
"lookup_mx": "Cieľ je regulárny výraz ktorý sa porovnáva s MX záznamom (<code>.*google\\.com</code> smeruje všetku poštu určenú pre MX ktoré sú cieľom pre google.com cez tento skok)", "lookup_mx": "Cieľ je regulárny výraz ktorý sa porovnáva s MX záznamom (<code>.*\\.google\\.com</code> smeruje všetku poštu určenú pre MX ktoré sú cieľom pre google.com cez tento skok)",
"main_name": "\"mailcow UI\" názov", "main_name": "\"mailcow UI\" názov",
"merged_vars_hint": "Sivé riadky boli načítané z <code>vars.(local.)inc.php</code> a nemôžu byť modifikované cez UI.", "merged_vars_hint": "Sivé riadky boli načítané z <code>vars.(local.)inc.php</code> a nemôžu byť modifikované cez UI.",
"message": "Správa", "message": "Správa",
@@ -539,7 +539,7 @@
"inactive": "Neaktívny", "inactive": "Neaktívny",
"kind": "Druh", "kind": "Druh",
"last_modified": "Naposledy upravené", "last_modified": "Naposledy upravené",
"lookup_mx": "Cieľ je regulárny výraz ktorý sa zhoduje s MX záznamom (<code>.*google\\.com</code> smeruje všetku poštu na MX ktoré sú cieľom pre google.com cez tento skok)", "lookup_mx": "Cieľ je regulárny výraz ktorý sa zhoduje s MX záznamom (<code>.*\\.google\\.com</code> smeruje všetku poštu na MX ktoré sú cieľom pre google.com cez tento skok)",
"mailbox": "Upraviť mailovú schránku", "mailbox": "Upraviť mailovú schránku",
"mailbox_quota_def": "Predvolená veľkosť mailovej schránky", "mailbox_quota_def": "Predvolená veľkosť mailovej schránky",
"mailbox_relayhost_info": "Aplikované len na používateľské schránky a priame aliasy, prepisuje doménového preposielateľa.", "mailbox_relayhost_info": "Aplikované len na používateľské schránky a priame aliasy, prepisuje doménového preposielateľa.",

View File

@@ -213,7 +213,7 @@
"loading": "请等待...", "loading": "请等待...",
"login_time": "登录时间", "login_time": "登录时间",
"logo_info": "你的图片将会在顶部导航栏被缩放为 40px 高,在起始页被缩放为最大 250px 高。强烈推荐使用能较好适应缩放的图片。", "logo_info": "你的图片将会在顶部导航栏被缩放为 40px 高,在起始页被缩放为最大 250px 高。强烈推荐使用能较好适应缩放的图片。",
"lookup_mx": "应当为一个正则表达式,用于匹配 MX 记录 (例如 <code>.*google\\.com</code> 将转发所有拥有以 google.com 结尾的 MX 记录的邮件)", "lookup_mx": "应当为一个正则表达式,用于匹配 MX 记录 (例如 <code>.*\\.google\\.com</code> 将转发所有拥有以 google.com 结尾的 MX 记录的邮件)",
"main_name": "Mailcow UI 的名称", "main_name": "Mailcow UI 的名称",
"merged_vars_hint": "灰色行来自 <code>vars.(local.)inc.php</code> 文件并且无法修改。", "merged_vars_hint": "灰色行来自 <code>vars.(local.)inc.php</code> 文件并且无法修改。",
"message": "消息", "message": "消息",
@@ -544,7 +544,7 @@
"hostname": "主机名", "hostname": "主机名",
"inactive": "禁用", "inactive": "禁用",
"kind": "类型", "kind": "类型",
"lookup_mx": "应当为一个正则表达式,用于匹配 MX 记录 (例如 <code>.*google\\.com</code> 将转发所有拥有以 google.com 结尾的 MX 记录的邮件)", "lookup_mx": "应当为一个正则表达式,用于匹配 MX 记录 (例如 <code>.*\\.google\\.com</code> 将转发所有拥有以 google.com 结尾的 MX 记录的邮件)",
"mailbox": "编辑邮箱", "mailbox": "编辑邮箱",
"mailbox_quota_def": "邮箱默认配额", "mailbox_quota_def": "邮箱默认配额",
"mailbox_relayhost_info": "只适用于邮箱和邮箱别名,不会覆盖域名的中继主机。", "mailbox_relayhost_info": "只适用于邮箱和邮箱别名,不会覆盖域名的中继主机。",

View File

@@ -213,7 +213,7 @@
"loading": "請稍等...", "loading": "請稍等...",
"login_time": "登入時間", "login_time": "登入時間",
"logo_info": "你的起始頁面圖片會在頂部導覽列的限制下被縮放為 40px 高,以及最大 250px 高度。強烈推薦使用能較好縮放的圖片。", "logo_info": "你的起始頁面圖片會在頂部導覽列的限制下被縮放為 40px 高,以及最大 250px 高度。強烈推薦使用能較好縮放的圖片。",
"lookup_mx": "目的地是可以用來匹配 MX 紀錄的正規表達式 (<code>.*google\\.com</code> 會將所有 MX 結尾於 google.com 的郵件轉發到此主機。)", "lookup_mx": "目的地是可以用來匹配 MX 紀錄的正規表達式 (<code>.*\\.google\\.com</code> 會將所有 MX 結尾於 google.com 的郵件轉發到此主機。)",
"main_name": "\"mailcow UI\" 名稱", "main_name": "\"mailcow UI\" 名稱",
"merged_vars_hint": "灰色列來自 <code>vars.(local.)inc.php</code> 並且不能修改。", "merged_vars_hint": "灰色列來自 <code>vars.(local.)inc.php</code> 並且不能修改。",
"message": "訊息", "message": "訊息",
@@ -540,7 +540,7 @@
"inactive": "停用", "inactive": "停用",
"kind": "種類", "kind": "種類",
"last_modified": "上次修改時間", "last_modified": "上次修改時間",
"lookup_mx": "目的地是可以用來匹配 MX 紀錄的正規表達式 (<code>.*google\\.com</code> 會將所有 MX 結尾於 google.com 的郵件轉發到此主機。)", "lookup_mx": "目的地是可以用來匹配 MX 紀錄的正規表達式 (<code>.*\\.google\\.com</code> 會將所有 MX 結尾於 google.com 的郵件轉發到此主機。)",
"mailbox": "編輯信箱", "mailbox": "編輯信箱",
"mailbox_quota_def": "預設信箱容量配額", "mailbox_quota_def": "預設信箱容量配額",
"mailbox_relayhost_info": "只會套用於信箱和直接別名,不會覆寫域名中繼主機。", "mailbox_relayhost_info": "只會套用於信箱和直接別名,不會覆寫域名中繼主機。",

View File

@@ -7,89 +7,31 @@
<span class="d-none d-md-block">{{ lang.admin.customize }}</span> <span class="d-none d-md-block">{{ lang.admin.customize }}</span>
</div> </div>
<div id="collapse-tab-config-customize" class="card-body collapse" data-bs-parent="#admin-content"> <div id="collapse-tab-config-customize" class="card-body collapse" data-bs-parent="#admin-content">
<div class="row"> <legend><i class="bi bi-file-image"></i> {{ lang.admin.change_logo }}</legend><hr />
<div class="col-12 col-lg-6 d-flex flex-column"> <p class="text-muted">{{ lang.admin.logo_info }}</p>
<legend><i class="bi bi-file-image"></i> {{ lang.admin.change_logo }}</legend><hr /> <form class="form-inline" role="form" method="post" enctype="multipart/form-data">
<p class="text-muted">{{ lang.admin.logo_info }}</p> <p>
<form class="form-inline" role="form" method="post" enctype="multipart/form-data"> <input class="mb-4" type="file" name="main_logo" accept="image/gif, image/jpeg, image/pjpeg, image/x-png, image/png, image/svg+xml"><br>
<p> <button name="submit_main_logo" type="submit" class="btn btn-sm d-block d-sm-inline btn-secondary"><i class="bi bi-upload"></i> {{ lang.admin.upload }}</button>
<input class="mb-4" type="file" name="main_logo" accept="image/gif, image/jpeg, image/pjpeg, image/x-png, image/png, image/svg+xml"><br> </p>
<button name="submit_main_logo" type="submit" class="btn btn-sm d-block d-sm-inline btn-secondary"><i class="bi bi-upload"></i> {{ lang.admin.upload }}</button> </form>
</p> {% if logo %}
</form> <div class="row">
{% if logo %} <div class="col-sm-4">
<div class="thumbnail mt-auto"> <div class="thumbnail">
<img class="img-thumbnail" src="{{ logo }}" alt="mailcow logo"> <img class="img-thumbnail" src="{{ logo }}" alt="mailcow logo">
<div class="caption d-flex flex-wrap mt-2 mb-4"> <div class="caption">
<span class="badge fs-5 bg-info">{{ logo_specs.geometry.width }}x{{ logo_specs.geometry.height }} px</span> <span class="badge fs-5 bg-info">{{ logo_specs.geometry.width }}x{{ logo_specs.geometry.height }} px</span>
<span class="badge fs-5 bg-info mx-2">{{ logo_specs.mimetype }}</span> <span class="badge fs-5 bg-info">{{ logo_specs.mimetype }}</span>
<span class="badge fs-5 bg-info">{{ logo_specs.fileSize }}</span> <span class="badge fs-5 bg-info">{{ logo_specs.fileSize }}</span>
</div> </div>
</div> </div>
<hr>
<form class="form-inline" role="form" method="post"> <form class="form-inline" role="form" method="post">
<p><button name="reset_main_logo" type="submit" class="btn btn-sm d-block d-sm-inline btn-secondary">{{ lang.admin.reset_default }}</button></p> <p><button name="reset_main_logo" type="submit" class="btn btn-sm d-block d-sm-inline btn-secondary">{{ lang.admin.reset_default }}</button></p>
</form> </form>
{% endif %}
</div>
<div class="col-12 col-lg-6 d-flex flex-column">
<legend><i class="bi bi-file-image"></i> {{ lang.admin.change_favicon }}</legend><hr />
<p class="text-muted">{{ lang.admin.favicon_info|raw }}</p>
<form class="form-inline" role="form" method="post" enctype="multipart/form-data">
<p>
<input class="mb-4" type="file" name="favicon" accept="image/x-icon, image/png"><br>
<button name="submit_favicon" type="submit" class="btn btn-sm d-block d-sm-inline btn-secondary"><i class="bi bi-upload"></i> {{ lang.admin.upload }}</button>
</p>
</form>
{% if favicon %}
<div class="thumbnail mt-auto">
<img class="img-thumbnail" src="{{ favicon }}" alt="mailcow favicon">
<div class="caption d-flex flex-wrap mt-2 mb-4">
<span class="badge fs-5 bg-info">{{ favicon_specs.geometry.width }}x{{ favicon_specs.geometry.height }} px</span>
<span class="badge fs-5 bg-info mx-2">{{ favicon_specs.mimetype }}</span>
<span class="badge fs-5 bg-info">{{ favicon_specs.fileSize }}</span>
</div>
</div>
<form class="form-inline" role="form" method="post">
<p><button name="reset_favicon" type="submit" class="btn btn-sm d-block d-sm-inline btn-secondary">{{ lang.admin.reset_default }}</button></p>
</form>
{% endif %}
</div>
</div>
{% if not skip_sogo %}
<legend style="padding-top:20px" unselectable="on">{{ lang.admin.sogo_theme }}</legend><hr />
<form class="form" data-id="sogo_theme" role="form" method="post">
<div class="mb-4 row">
<div class="col-12 col-md-4 mb-2">
<label class="d-block" for="sogo_primary">{{ lang.admin.sogo_theme_primary }}</label>
<select multiple data-width="100%" id="sogo_primary" name="primary" class="selectpicker show-tick" data-max-options="1" data-id="sogo_theme">
{% for sogo_palette in sogo_palettes %}
<option {% if sogo_palette == sogo_theme.primary %}selected{% endif %} value="{{ sogo_palette }}">{{ sogo_palette }}</option>
{% endfor %}
</select>
</div>
<div class="col-12 col-md-4 mb-2">
<label class="d-block" for="sogo_accent">{{ lang.admin.sogo_theme_accent }}</label>
<select multiple data-width="100%" id="sogo_accent" name="accent" class="selectpicker show-tick" data-max-options="1" data-id="sogo_theme">
{% for sogo_palette in sogo_palettes %}
<option {% if sogo_palette == sogo_theme.accent %}selected{% endif %} value="{{ sogo_palette }}">{{ sogo_palette }}</option>
{% endfor %}
</select>
</div>
<div class="col-12 col-md-4 mb-2">
<label class="d-block" for="sogo_background">{{ lang.admin.sogo_theme_background }}</label>
<select multiple data-width="100%" id="sogo_background" name="background" class="selectpicker show-tick" data-max-options="1" data-id="sogo_theme">
{% for sogo_palette in sogo_palettes %}
<option {% if sogo_palette == sogo_theme.background %}selected{% endif %} value="{{ sogo_palette }}">{{ sogo_palette }}</option>
{% endfor %}
</select>
</div> </div>
</div> </div>
<p class="text-muted">{{ lang.admin.sogo_theme_info }}</p>
<p><div class="btn-group">
<button class="btn btn-sm btn-xs-half d-block d-sm-inline btn-success" type="button" data-action="edit_selected" data-item="sogo-theme" data-id="sogo_theme" data-reload="no" data-api-url='edit/sogo_theme' data-api-attr='{}'><i class="bi bi-check-lg"></i> {{ lang.admin.save }}</button>
<button class="btn btn-sm btn-xs-half d-block d-sm-inline btn-danger" type="button" data-action="delete_selected" data-item="sogo-theme" data-id="sogo_theme" data-api-url="delete/sogo_theme"><i class="bi bi-trash"></i> {{ lang.admin.remove }}</button>
</div></p>
</form>
{% endif %} {% endif %}
<legend style="padding-top:20px" unselectable="on">{{ lang.admin.ip_check }}</legend><hr /> <legend style="padding-top:20px" unselectable="on">{{ lang.admin.ip_check }}</legend><hr />
<div id="ip_check"> <div id="ip_check">

View File

@@ -23,8 +23,8 @@
} }
</script> </script>
<link rel="shortcut icon" href="{{ favicon|default('/favicon.png') }}" type="image/png"> <link rel="shortcut icon" href="/favicon.png" type="image/png">
<link rel="icon" href="{{ favicon|default('/favicon.png') }}" type="image/png"> <link rel="icon" href="/favicon.png" type="image/png">
</head> </head>
<body> <body>
<div class="overlay"></div> <div class="overlay"></div>

View File

@@ -49,6 +49,12 @@
<p><b>{{ hostname }}</b></p> <p><b>{{ hostname }}</b></p>
</div></td> </div></td>
</tr> </tr>
<tr>
<td>{{ lang.debug.architecture }}</td>
<td class="text-break"><div>
<p id="host_architecture">-</p>
</div></td>
</tr>
<tr> <tr>
<td>IPs</td> <td>IPs</td>
<td class="text-break"> <td class="text-break">
@@ -70,7 +76,7 @@
<td>Version</td> <td>Version</td>
<td class="text-break"> <td class="text-break">
<div class="fw-bolder"> <div class="fw-bolder">
<p ><a href="#" id="maiclow_version">{{ mailcow_info.version_tag }}</a></p> <p ><a href="#" id="mailcow_version">{{ mailcow_info.version_tag }}</a></p>
<p id="mailcow_update"></p> <p id="mailcow_update"></p>
</div> </div>
</td> </td>

View File

@@ -12,11 +12,21 @@
<li><button class="dropdown-item" role="tab" aria-selected="false" aria-controls="tab-config-f2b" data-bs-toggle="tab" data-bs-target="#tab-user-settings">{{ lang.user.mailbox_settings }}</button></li> <li><button class="dropdown-item" role="tab" aria-selected="false" aria-controls="tab-config-f2b" data-bs-toggle="tab" data-bs-target="#tab-user-settings">{{ lang.user.mailbox_settings }}</button></li>
</ul> </ul>
</li> </li>
{% if acl.spam_alias == 1 %}
<li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="SpamAliases" role="tab" data-bs-toggle="tab" data-bs-target="#SpamAliases">{{ lang.user.spam_aliases }}</button></li> <li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="SpamAliases" role="tab" data-bs-toggle="tab" data-bs-target="#SpamAliases">{{ lang.user.spam_aliases }}</button></li>
{% endif %}
{% if acl.spam_score == 1 %}
<li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="Spamfilter" role="tab" data-bs-toggle="tab" data-bs-target="#Spamfilter">{{ lang.user.spamfilter }}</button></li> <li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="Spamfilter" role="tab" data-bs-toggle="tab" data-bs-target="#Spamfilter">{{ lang.user.spamfilter }}</button></li>
{% endif %}
{% if acl.syncjobs == 1 %}
<li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="Syncjobs" role="tab" data-bs-toggle="tab" data-bs-target="#Syncjobs">{{ lang.user.sync_jobs }}</button></li> <li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="Syncjobs" role="tab" data-bs-toggle="tab" data-bs-target="#Syncjobs">{{ lang.user.sync_jobs }}</button></li>
{% endif %}
{% if acl.app_passwds == 1 %}
<li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="AppPasswds" role="tab" data-bs-toggle="tab" data-bs-target="#AppPasswds">{{ lang.user.app_passwds }}</button></li> <li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="AppPasswds" role="tab" data-bs-toggle="tab" data-bs-target="#AppPasswds">{{ lang.user.app_passwds }}</button></li>
{% endif %}
{% if acl.pushover == 1 %}
<li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="Pushover" role="tab" data-bs-toggle="tab" data-bs-target="#Pushover">Pushover API</button></li> <li class="nav-item" role="presentation"><button class="nav-link" role="tab" aria-selected="false" aria-controls="Pushover" role="tab" data-bs-toggle="tab" data-bs-target="#Pushover">Pushover API</button></li>
{% endif %}
</ul> </ul>
<div class="row"> <div class="row">
@@ -25,11 +35,11 @@
{% include 'user/tab-user-auth.twig' %} {% include 'user/tab-user-auth.twig' %}
{% include 'user/tab-user-details.twig' %} {% include 'user/tab-user-details.twig' %}
{% include 'user/tab-user-settings.twig' %} {% include 'user/tab-user-settings.twig' %}
{% include 'user/SpamAliases.twig' %} {% if acl.spam_alias == 1 %}{% include 'user/SpamAliases.twig' %}{% endif %}
{% include 'user/Spamfilter.twig' %} {% if acl.spam_score == 1 %}{% include 'user/Spamfilter.twig' %}{% endif %}
{% include 'user/Syncjobs.twig' %} {% if acl.syncjobs == 1 %}{% include 'user/Syncjobs.twig' %}{% endif %}
{% include 'user/AppPasswds.twig' %} {% if acl.app_passwds == 1 %}{% include 'user/AppPasswds.twig' %}{% endif %}
{% include 'user/Pushover.twig' %} {% if acl.pushover == 1 %}{% include 'user/Pushover.twig' %}{% endif %}
</div> </div>
</div> </div>
</div> </div>

View File

@@ -106,7 +106,7 @@ services:
- rspamd - rspamd
php-fpm-mailcow: php-fpm-mailcow:
image: mailcow/phpfpm:1.83 image: mailcow/phpfpm:1.84
command: "php-fpm -d date.timezone=${TZ} -d expose_php=0" command: "php-fpm -d date.timezone=${TZ} -d expose_php=0"
depends_on: depends_on:
- redis-mailcow - redis-mailcow
@@ -169,7 +169,7 @@ services:
- phpfpm - phpfpm
sogo-mailcow: sogo-mailcow:
image: mailcow/sogo:1.118 image: mailcow/sogo:1.117
environment: environment:
- DBNAME=${DBNAME} - DBNAME=${DBNAME}
- DBUSER=${DBUSER} - DBUSER=${DBUSER}
@@ -216,7 +216,7 @@ services:
- sogo - sogo
dovecot-mailcow: dovecot-mailcow:
image: mailcow/dovecot:1.23 image: mailcow/dovecot:1.24
depends_on: depends_on:
- mysql-mailcow - mysql-mailcow
dns: dns:

View File

@@ -26,6 +26,6 @@ services:
- /var/run/mysqld/mysqld.sock:/var/run/mysqld/mysqld.sock - /var/run/mysqld/mysqld.sock:/var/run/mysqld/mysqld.sock
mysql-mailcow: mysql-mailcow:
image: alpine:3.17 image: alpine:3.18
command: /bin/true command: /bin/true
restart: "no" restart: "no"

View File

@@ -1,6 +1,6 @@
#!/usr/bin/env bash #!/usr/bin/env bash
# renovate: datasource=github-releases depName=nextcloud/server versioning=semver extractVersion=^v(?<version>.*)$ # renovate: datasource=github-releases depName=nextcloud/server versioning=semver extractVersion=^v(?<version>.*)$
NEXTCLOUD_VERSION=26.0.1 NEXTCLOUD_VERSION=26.0.2
echo -ne "Checking prerequisites..." echo -ne "Checking prerequisites..."
sleep 1 sleep 1

View File

@@ -6,7 +6,7 @@ SPFTOOLS_DIR=${WORKING_DIR}/spf-tools
POSTWHITE_DIR=${WORKING_DIR}/postwhite POSTWHITE_DIR=${WORKING_DIR}/postwhite
POSTWHITE_CONF=${POSTWHITE_DIR}/postwhite.conf POSTWHITE_CONF=${POSTWHITE_DIR}/postwhite.conf
COSTOM_HOSTS="web.de gmx.net mail.de freenet.de arcor.de unity-mail.de" CUSTOM_HOSTS='"web.de gmx.net mail.de freenet.de arcor.de unity-mail.de"'
STATIC_HOSTS=( STATIC_HOSTS=(
"194.25.134.0/24 permit # t-online.de" "194.25.134.0/24 permit # t-online.de"
) )
@@ -19,13 +19,20 @@ function set_config() {
sudo sed -i "s@^\($1\s*=\s*\).*\$@\1$2@" ${POSTWHITE_CONF} sudo sed -i "s@^\($1\s*=\s*\).*\$@\1$2@" ${POSTWHITE_CONF}
} }
set_config custom_hosts ${COSTOM_HOSTS} set_config custom_hosts "${CUSTOM_HOSTS}"
set_config reload_postfix no set_config reload_postfix no
set_config postfixpath /. set_config postfixpath /.
set_config spftoolspath ${WORKING_DIR}/spf-tools set_config spftoolspath ${WORKING_DIR}/spf-tools
set_config whitelist .${SCRIPT_DIR}/../data/conf/postfix/postscreen_access.cidr set_config whitelist .${SCRIPT_DIR}/../data/conf/postfix/postscreen_access.cidr
set_config yahoo_static_hosts ${POSTWHITE_DIR}/yahoo_static_hosts.txt set_config yahoo_static_hosts ${POSTWHITE_DIR}/yahoo_static_hosts.txt
#Fix URL for Yahoo!: https://github.com/stevejenkins/postwhite/issues/59
sudo sed -i \
-e 's#yahoo_url="https://help.yahoo.com/kb/SLN23997.html"#yahoo_url="https://senders.yahooinc.com/outbound-mail-servers/"#' \
-e 's#echo "ipv6:$line";#echo "ipv6:$line" | grep -v "ipv6:::";#' \
-e 's#`command -v wget`#`command -v skip-wget`#' \
${POSTWHITE_DIR}/scrape_yahoo
cd ${POSTWHITE_DIR} cd ${POSTWHITE_DIR}
./postwhite ${POSTWHITE_CONF} ./postwhite ${POSTWHITE_CONF}