NobGit
public nobgit read

NobMail

Based on mailcow: dockerized

Languages

Repository composition by tracked source files.

PHP
PHP 49% JavaScript 35% HTML 9% CSS 4% Shell 2% Python 1% Lua 0% Perl 0% Ruby 0% SCSS 0%
Create file Wiki Documentation
Clone
https://nobgit.com/orgs/nobgit/nobmail.git
ssh://[email protected]:2222/orgs/nobgit/nobmail.git

Commit

add random masterpass for sogo admin login add required headers for sogo proxy auth with password add SOGoEncryptionKey add SOGoTrustProxyAuthentication only conditionally if feature is enabled

dd6d253a
Marcel Hofer <[email protected]> 7 years ago
data/Dockerfiles/dovecot/docker-entrypoint.sh      | 26 +++++++++++++---------
 data/Dockerfiles/sogo/bootstrap-sogo.sh            | 11 +++++++++
 .../nginx/templates/sogo.auth_request.template.sh  | 12 +++++-----
 data/conf/phpfpm/sogo-sso/.gitkeep                 |  0
 data/conf/sogo/sogo.conf                           |  2 --
 data/web/sogo-auth.php                             | 23 +++++++++++++------
 docker-compose.yml                                 |  2 ++
 7 files changed, 51 insertions(+), 25 deletions(-)
 create mode 100644 data/conf/phpfpm/sogo-sso/.gitkeep

Diff

diff --git a/data/Dockerfiles/dovecot/docker-entrypoint.sh b/data/Dockerfiles/dovecot/docker-entrypoint.sh
index 179ffb65..28b31420 100755
--- a/data/Dockerfiles/dovecot/docker-entrypoint.sh
+++ b/data/Dockerfiles/dovecot/docker-entrypoint.sh
@@ -118,17 +118,6 @@ default_pass_scheme = SSHA256
 password_query = SELECT password FROM mailbox WHERE active = '1' AND username = '%u' AND domain IN (SELECT domain FROM domain WHERE domain='%d' AND active='1') AND JSON_EXTRACT(attributes, '$.force_pw_update') NOT LIKE '%%1%%'
 EOF
 
-if [[ "${ALLOW_ADMIN_EMAIL_LOGIN}" =~ ^([yY][eE][sS]|[yY])+$ ]]; then
-    cat <<EOF > /usr/local/etc/dovecot/sogo-sso.conf
-passdb {
-  driver = static
-  args = password= allow_real_nets=${IPV4_NETWORK}.248/32
-}
-EOF
-else
-    rm -f /usr/local/etc/dovecot/sogo-sso.conf
-fi
-
 # Create global sieve_after script
 cat /usr/local/etc/dovecot/sieve_after > /var/vmail/sieve/global.sieve
 
@@ -146,6 +135,21 @@ echo ${RAND_USER}@mailcow.local:{SHA1}$(echo -n ${RAND_PASS} | sha1sum | awk '{p
 echo ${RAND_USER}@mailcow.local::5000:5000:::: > /usr/local/etc/dovecot/dovecot-master.userdb
 echo ${RAND_USER}@mailcow.local:${RAND_PASS} > /etc/sogo/sieve.creds
 
+if [[ "${ALLOW_ADMIN_EMAIL_LOGIN}" =~ ^([yY][eE][sS]|[yY])+$ ]]; then
+    # Create random master Password for SOGo 'login as user' via proxy auth
+    RAND_PASS=$(cat /dev/urandom | tr -dc 'a-z0-9' | fold -w 32 | head -n 1)
+    echo -n ${RAND_PASS} > /etc/phpfpm/sogo-sso.pass
+    cat <<EOF > /usr/local/etc/dovecot/sogo-sso.conf
+passdb {
+  driver = static
+  args = allow_real_nets=${IPV4_NETWORK}.248/32 password={plain}${RAND_PASS}
+}
+EOF
+else
+    rm -f /usr/local/etc/dovecot/sogo-sso.pass
+    rm -f /usr/local/etc/dovecot/sogo-sso.conf
+fi
+
 # 401 is user dovecot
 if [[ ! -s /mail_crypt/ecprivkey.pem || ! -s /mail_crypt/ecpubkey.pem ]]; then
 	openssl ecparam -name prime256v1 -genkey | openssl pkey -out /mail_crypt/ecprivkey.pem
diff --git a/data/Dockerfiles/sogo/bootstrap-sogo.sh b/data/Dockerfiles/sogo/bootstrap-sogo.sh
index 84176ebd..51e1eea3 100755
--- a/data/Dockerfiles/sogo/bootstrap-sogo.sh
+++ b/data/Dockerfiles/sogo/bootstrap-sogo.sh
@@ -88,6 +88,13 @@ mkdir -p /var/lib/sogo/GNUstep/Defaults/
 # Force-remove lines from sogo.conf
 sed -i '/SOGoIMAPServer/d' /etc/sogo/sogo.conf
 
+if [[ "${ALLOW_ADMIN_EMAIL_LOGIN}" =~ ^([yY][eE][sS]|[yY])+$ ]]; then
+  TRUST_PROXY="YES"
+else
+  TRUST_PROXY="NO"
+fi
+RAND_PASS=$(cat /dev/urandom | tr -dc 'a-z0-9' | fold -w 24 | head -n 1)
+
 # Generate plist header with timezone data
 cat <<EOF > /var/lib/sogo/GNUstep/Defaults/sogod.plist
 <?xml version="1.0" encoding="UTF-8"?>
@@ -98,6 +105,10 @@ cat <<EOF > /var/lib/sogo/GNUstep/Defaults/sogod.plist
     <string>mysql://${DBUSER}:${DBPASS}@%2Fvar%2Frun%2Fmysqld%2Fmysqld.sock/${DBNAME}/sogo_acl</string>
     <key>SOGoIMAPServer</key>
     <string>imap://${IPV4_NETWORK}.250:143/?tls=YES</string>
+    <key>SOGoTrustProxyAuthentication</key>
+    <string>${TRUST_PROXY}</string>
+    <key>SOGoEncryptionKey</key>
+    <string>${RAND_PASS}</string>
     <key>OCSCacheFolderURL</key>
     <string>mysql://${DBUSER}:${DBPASS}@%2Fvar%2Frun%2Fmysqld%2Fmysqld.sock/${DBNAME}/sogo_cache_folder</string>
     <key>OCSEMailAlarmsFolderURL</key>
diff --git a/data/conf/nginx/templates/sogo.auth_request.template.sh b/data/conf/nginx/templates/sogo.auth_request.template.sh
index d885d9f5..f6d2d98e 100644
--- a/data/conf/nginx/templates/sogo.auth_request.template.sh
+++ b/data/conf/nginx/templates/sogo.auth_request.template.sh
@@ -1,8 +1,10 @@
 if printf "%s\n" "${ALLOW_ADMIN_EMAIL_LOGIN}" | grep -E '^([yY][eE][sS]|[yY])+$' >/dev/null; then
     echo 'auth_request /sogo-auth-verify;
-auth_request_set $user $upstream_http_x_username;
-proxy_set_header x-webobjects-remote-user $user;
-if ($args ~* (.*)(account=(?!0))(.*)) {
-  return 401;
-}'
+auth_request_set $user $upstream_http_x_user;
+auth_request_set $auth $upstream_http_x_auth;
+auth_request_set $auth_type $upstream_http_x_auth_type;
+proxy_set_header x-webobjects-remote-user "$user";
+proxy_set_header Authorization "$auth";
+proxy_set_header x-webobjects-auth-type "$auth_type";
+'
 fi
diff --git a/data/conf/phpfpm/sogo-sso/.gitkeep b/data/conf/phpfpm/sogo-sso/.gitkeep
new file mode 100644
index 00000000..e69de29b
diff --git a/data/conf/sogo/sogo.conf b/data/conf/sogo/sogo.conf
index b115d75d..f9e9e077 100644
--- a/data/conf/sogo/sogo.conf
+++ b/data/conf/sogo/sogo.conf
@@ -82,6 +82,4 @@
   //SOGoUIxDebugEnabled = YES;
   //WODontZipResponse = YES;
     WOLogFile = "/dev/sogo_log";
-
-    SOGoTrustProxyAuthentication = YES;
 }
diff --git a/data/web/sogo-auth.php b/data/web/sogo-auth.php
index 77c73590..d9c10557 100644
--- a/data/web/sogo-auth.php
+++ b/data/web/sogo-auth.php
@@ -30,7 +30,8 @@ $ALLOW_ADMIN_EMAIL_LOGIN = (preg_match(
   $_ENV["ALLOW_ADMIN_EMAIL_LOGIN"]
 ));
 
-$session_variable = 'sogo-sso-user';
+$session_var_user = 'sogo-sso-user';
+$session_var_pass = 'sogo-sso-pass';
 
 if (!$ALLOW_ADMIN_EMAIL_LOGIN) {
   header("Location: /");
@@ -42,7 +43,9 @@ elseif (isset($_GET['login'])) {
     $login = html_entity_decode(rawurldecode($_GET["login"]));
     if (filter_var($login, FILTER_VALIDATE_EMAIL)) {
       if (!empty(mailbox('get', 'mailbox_details', $login))) {
-        $_SESSION[$session_variable] = $login;
+        $sogo_sso_pass = file_get_contents("/etc/sogo-sso/sogo-sso.pass");
+        $_SESSION[$session_var_user] = $login;
+        $_SESSION[$session_var_pass] = $sogo_sso_pass;
         header("Location: /SOGo/");
         exit;
       }
@@ -54,11 +57,17 @@ elseif (isset($_GET['login'])) {
 else {
   // this is an nginx auth_request call, we check for an existing sogo-sso-user session variable
   session_start();
-  $username = "";
-  if (isset($_SESSION[$session_variable]) && filter_var($_SESSION[$session_variable], FILTER_VALIDATE_EMAIL)) {
-      $username = $_SESSION[$session_variable];
+  if (isset($_SESSION[$session_var_user]) && filter_var($_SESSION[$session_var_user], FILTER_VALIDATE_EMAIL)) {
+      $username = $_SESSION[$session_var_user];
+      $password = $_SESSION[$session_var_pass];
+      header("X-User: $username");
+      header("X-Auth: Basic ".base64_encode("$username:$password"));
+      header("X-Auth-Type: Basic");
+  } else {
+      // if username is empty, SOGo will display the normal login form
+      header("X-User: ");
+      header("X-Auth: ");
+      header("X-Auth-Type: ");
   }
-  // if username is empty, SOGo will display the normal login form
-  header("X-Username: $username");
   exit;
 }
diff --git a/docker-compose.yml b/docker-compose.yml
index c2394909..4d4b9022 100644
--- a/docker-compose.yml
+++ b/docker-compose.yml
@@ -106,6 +106,7 @@ services:
         - mysql-socket-vol-1:/var/run/mysqld/
         - ./data/conf/sogo/:/etc/sogo/
         - ./data/conf/rspamd/meta_exporter:/meta_exporter:ro
+        - ./data/conf/phpfpm/sogo-sso/:/etc/sogo-sso/
         - ./data/conf/phpfpm/php-fpm.d/pools.conf:/usr/local/etc/php-fpm.d/z-pools.conf
         - ./data/conf/phpfpm/php-conf.d/opcache-recommended.ini:/usr/local/etc/php/conf.d/opcache-recommended.ini
         - ./data/conf/phpfpm/php-conf.d/upload.ini:/usr/local/etc/php/conf.d/upload.ini
@@ -175,6 +176,7 @@ services:
         - ./data/conf/dovecot:/usr/local/etc/dovecot
         - ./data/assets/ssl:/etc/ssl/mail/:ro
         - ./data/conf/sogo/:/etc/sogo/
+        - ./data/conf/phpfpm/sogo-sso/:/etc/phpfpm/
         - vmail-vol-1:/var/vmail
         - vmail-attachments-vol-1:/var/attachments
         - crypt-vol-1:/mail_crypt/