Dovecot

(This was written before dovecot 2.x)

Now, many mailsystems somehow assume you have a local user for each mailbox. That is of course not what i wanted.

Dovecot still is influenced by this, but you can have many virtual users in one system user. So i decided i need exactly one system user for the mailboxes.

I named that user “vmail” and put him in /var/dovecot/home/vmail (uid 512, gid 65534, no shell – a “system” user).

No we need some PostgreSQL tables; i created a user dovecot for it, and used a database named “system”; admin is my admin user:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
CREATE SCHEMA dovecot;
ALTER SCHEMA dovecot OWNER TO dovecot;

CREATE TABLE users (
    userid character varying(128) NOT NULL,
    password character varying(128)
);
ALTER TABLE dovecot.users OWNER TO admin;

CREATE VIEW dovecot_users AS
    SELECT users.userid AS "user", users.password, (('/var/dovecot/home/vmail/'::text || (users.userid)::text) || '/'::text)
    AS userdb_home, 512 AS userdb_uid, 65534 AS userdb_gid FROM users;

CREATE TABLE transport (
    domain character varying(128) NOT NULL,
    transport character varying(128) NOT NULL
);


ALTER TABLE dovecot.transport OWNER TO admin;

CREATE VIEW postfix_mailboxes AS
    SELECT users.userid, (('/var/dovecot/home/vmail/'::text || (users.userid)::text) || '/Maildir/'::text) AS
    mailbox FROM users UNION ALL SELECT transport.domain AS userid, 'dummy' AS mailbox FROM transport;

CREATE TABLE virtual (
    address character varying(255) NOT NULL,
    userid character varying(255) NOT NULL
);


ALTER TABLE dovecot.virtual OWNER TO admin;

CREATE VIEW postfix_virtual AS
    SELECT users.userid, users.userid AS address FROM users UNION ALL SELECT virtual.userid, virtual.address FROM virtual;

ALTER TABLE ONLY transport
    ADD CONSTRAINT transport_pkey PRIMARY KEY (domain);
ALTER TABLE ONLY users
    ADD CONSTRAINT users_pkey PRIMARY KEY (userid);
ALTER TABLE ONLY virtual
    ADD CONSTRAINT virtual_pkey PRIMARY KEY (address);

REVOKE ALL ON TABLE users FROM PUBLIC;
GRANT SELECT ON TABLE users TO dovecot;

REVOKE ALL ON TABLE dovecot_users FROM PUBLIC;
GRANT SELECT ON TABLE dovecot_users TO dovecot;

REVOKE ALL ON TABLE transport FROM PUBLIC;
GRANT SELECT ON TABLE transport TO dovecot;

REVOKE ALL ON TABLE postfix_mailboxes FROM PUBLIC;
GRANT SELECT ON TABLE postfix_mailboxes TO dovecot;

REVOKE ALL ON TABLE virtual FROM PUBLIC;
GRANT SELECT ON TABLE virtual TO dovecot;

REVOKE ALL ON TABLE postfix_virtual FROM PUBLIC;
GRANT SELECT ON TABLE postfix_virtual TO dovecot;

As you perhaps see, i hardcoded the paths, uid and gid into the views. You can of course use real columns for that.

You can use different password schemes, just put {scheme} before them (dovecotpw does this for you); i use plaintext as default setting, but i use cram-md5 for now in my sql tables. (See Mechanisms and PasswordSchemes).

In the transport table you will tell postfix how to deliver emails; just insert (‘example.com’, ‘virtual:’) for every domain you want to use dovecot for.

The virtual table is used to determine where a mail is sent to; you can do forwards with it, too:

1
2
3
('@example.com', 'postmaster@example.com, postmaster@other.example.com')
('user1@example.com', 'mailbox1@example.com')
('forward@example.com', 'user@farfaraway.example.com')

In the users table you store your users; the userid is the mailbox name, i.e. ‘mailbox1@example.com’.

Now we need to tell dovecot where to find its data:
/etc/dovecot/dovecot-sql.conf:

1
2
3
4
driver = pgsql
connect = host=10.0.0.1 dbname=system user=dovecot password=yourpassword
default_pass_scheme = PLAIN
password_query = SELECT "user", "password", "userdb_home", "userdb_uid", "userdb_gid" FROM "dovecot_users" WHERE "user" = '%u'

And configure dovecot (for the ssl certs see [[SSL-Certs]]):
I think most parts are well documented, so just the important parts:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
disable_plaintext_auth = no
mail_location = maildir:~/Maildir

# I needed that for subfolders in kmail
namespace private {
   separator = /
   prefix = ""
   inbox = yes
}
auth default {
  # if you use plaintext passwords, you can use every mechanism
  # if you don't use plaintext passwords, then only plain, login and the matching mechanism (if existing)
  mechanisms = plain login cram-md5
  passdb sql {
    args = /etc/dovecot/dovecot-sql.conf
  }
  # take user data from password fetch, saves one query
  userdb prefetch {
  }
  user = nobody
  # so postfix can ask us for authentication
  socket listen {
    client {
      path = /var/spool/postfix/private/auth
      mode = 0660
      user = postfix
      group = postfix
    }
  }
}

See Postfix for the postfix part.

Generated using nanoc and bootstrap - Last content change: 2011-06-10 07:41