From 61d2961ee92c2aabb55404e9eb073dd62165c66c Mon Sep 17 00:00:00 2001 From: Alberto Bertogli Date: Sun, 25 Feb 2018 02:50:39 +0000 Subject: [PATCH] test: Add a new integration test with minor dialogs This patch adds a new integration test, which executes various small dialogs, to cover corner cases that are not well covered (according to our coverage report). For example, "EHLO" without domain, or invalid DATA. While we could do them via Go tests, this way is more realistic, and the tests are easier to write. --- test/t-12-minor_dialogs/auth_multi_dialog.cmy | 27 ++++++++++++++++ test/t-12-minor_dialogs/auth_not_tls.cmy | 8 +++++ .../auth_too_many_failures.cmy | 18 +++++++++++ test/t-12-minor_dialogs/bad_data.cmy | 32 +++++++++++++++++++ test/t-12-minor_dialogs/bad_mail_from.cmy | 20 ++++++++++++ test/t-12-minor_dialogs/bad_rcpt_to.cmy | 26 +++++++++++++++ test/t-12-minor_dialogs/config/chasquid.conf | 15 +++++++++ .../config/domains/testserver/aliases | 3 ++ test/t-12-minor_dialogs/empty_helo.cmy | 11 +++++++ test/t-12-minor_dialogs/helo.cmy | 9 ++++++ test/t-12-minor_dialogs/hosts | 1 + test/t-12-minor_dialogs/run.sh | 26 +++++++++++++++ test/t-12-minor_dialogs/sendmail.cmy | 23 +++++++++++++ test/t-12-minor_dialogs/unknown_command.cmy | 9 ++++++ test/util/chamuyero | 19 +++++++++++ 15 files changed, 247 insertions(+) create mode 100644 test/t-12-minor_dialogs/auth_multi_dialog.cmy create mode 100644 test/t-12-minor_dialogs/auth_not_tls.cmy create mode 100644 test/t-12-minor_dialogs/auth_too_many_failures.cmy create mode 100644 test/t-12-minor_dialogs/bad_data.cmy create mode 100644 test/t-12-minor_dialogs/bad_mail_from.cmy create mode 100644 test/t-12-minor_dialogs/bad_rcpt_to.cmy create mode 100644 test/t-12-minor_dialogs/config/chasquid.conf create mode 100644 test/t-12-minor_dialogs/config/domains/testserver/aliases create mode 100644 test/t-12-minor_dialogs/empty_helo.cmy create mode 100644 test/t-12-minor_dialogs/helo.cmy create mode 100644 test/t-12-minor_dialogs/hosts create mode 100755 test/t-12-minor_dialogs/run.sh create mode 100644 test/t-12-minor_dialogs/sendmail.cmy create mode 100644 test/t-12-minor_dialogs/unknown_command.cmy diff --git a/test/t-12-minor_dialogs/auth_multi_dialog.cmy b/test/t-12-minor_dialogs/auth_multi_dialog.cmy new file mode 100644 index 0000000..1e60f4a --- /dev/null +++ b/test/t-12-minor_dialogs/auth_multi_dialog.cmy @@ -0,0 +1,27 @@ + +c tls_connect localhost:1465 + +c <~ 220 +c -> EHLO localhost +c <... 250 HELP + +c -> AUTH SOMETHINGELSE +c <~ 534 + +c -> AUTH PLAIN +c <~ 334 +c -> dXNlckB0ZXN0c2VydmVyAHlalala== +c <~ 535 error decoding AUTH response + +c -> AUTH PLAIN +c <~ 334 +c -> dXNlckB0ZXN0c2VydmVyAHVzZXJAdGVzdHNlcnZlcgB3cm9uZ3Bhc3N3b3Jk +c <~ 535 Incorrect user or password + +c -> AUTH PLAIN +c <~ 334 +c -> dXNlckB0ZXN0c2VydmVyAHVzZXJAdGVzdHNlcnZlcgBzZWNyZXRwYXNzd29yZA== +c <~ 235 + +c -> AUTH PLAIN +c <~ 503 You are already wearing that! diff --git a/test/t-12-minor_dialogs/auth_not_tls.cmy b/test/t-12-minor_dialogs/auth_not_tls.cmy new file mode 100644 index 0000000..4a16c0d --- /dev/null +++ b/test/t-12-minor_dialogs/auth_not_tls.cmy @@ -0,0 +1,8 @@ + +c tcp_connect localhost:1025 + +c <~ 220 +c -> EHLO localhost +c <... 250 HELP +c -> AUTH PLAIN +c <- 503 You feel vulnerable diff --git a/test/t-12-minor_dialogs/auth_too_many_failures.cmy b/test/t-12-minor_dialogs/auth_too_many_failures.cmy new file mode 100644 index 0000000..8ea8195 --- /dev/null +++ b/test/t-12-minor_dialogs/auth_too_many_failures.cmy @@ -0,0 +1,18 @@ + +c tls_connect localhost:1465 + +c <~ 220 +c -> EHLO localhost +c <... 250 HELP + +c -> AUTH PLAIN something +c <~ 535 +c -> AUTH PLAIN something +c <~ 535 +c -> AUTH PLAIN something +c <~ 535 +c -> AUTH PLAIN something +c <~ 535 +c -> AUTH PLAIN something +c <~ 503 Too many attempts - go away + diff --git a/test/t-12-minor_dialogs/bad_data.cmy b/test/t-12-minor_dialogs/bad_data.cmy new file mode 100644 index 0000000..302bc0f --- /dev/null +++ b/test/t-12-minor_dialogs/bad_data.cmy @@ -0,0 +1,32 @@ + +c tcp_connect localhost:1025 + +c <~ 220 + +c -> DATA +c <- 503 Invisible customers are not welcome! + +c -> HELO localhost +c <~ 250 +c -> DATA +c <- 503 sender not yet given + +c -> MAIL FROM: +c <~ 250 +c -> RCPT TO: user@testserver +c <~ 250 +c -> DATA +c <~ 354 +c -> From: Mailer daemon +c -> Subject: I've come to haunt you +c -> Bad header +c -> +c -> Muahahahaha +c -> +c -> +c -> . +c <~ 554 error parsing message + +c -> QUIT +c <~ 221 + diff --git a/test/t-12-minor_dialogs/bad_mail_from.cmy b/test/t-12-minor_dialogs/bad_mail_from.cmy new file mode 100644 index 0000000..4853895 --- /dev/null +++ b/test/t-12-minor_dialogs/bad_mail_from.cmy @@ -0,0 +1,20 @@ + +c tcp_connect localhost:1025 + +c <~ 220 +c -> HELO localhost +c <~ 250 +c -> MAIL LALA: <> +c <- 500 unknown command + +c -> MAIL FROM: +c <~ 500 + +c -> MAIL FROM: +c <~ 501 + +c -> MAIL FROM: +c <- 501 malformed address (IDNA conversion failed) + +c -> MAIL FROM: +c <- 501 address too long diff --git a/test/t-12-minor_dialogs/bad_rcpt_to.cmy b/test/t-12-minor_dialogs/bad_rcpt_to.cmy new file mode 100644 index 0000000..0e9bd50 --- /dev/null +++ b/test/t-12-minor_dialogs/bad_rcpt_to.cmy @@ -0,0 +1,26 @@ + +c tcp_connect localhost:1025 + +c <~ 220 +c -> HELO localhost +c <~ 250 +c -> MAIL FROM: +c <~ 250 + +c -> RCPT LALA: <> +c <- 500 unknown command + +c -> RCPT TO: +c <~ 500 + +c -> RCPT TO: +c <~ 501 + +c -> RCPT TO: +c <- 501 malformed address (IDNA conversion failed) + +c -> RCPT TO: +c <- 550 recipient invalid, please check the address for typos + +c -> RCPT TO: +c <- 501 address too long diff --git a/test/t-12-minor_dialogs/config/chasquid.conf b/test/t-12-minor_dialogs/config/chasquid.conf new file mode 100644 index 0000000..9a35641 --- /dev/null +++ b/test/t-12-minor_dialogs/config/chasquid.conf @@ -0,0 +1,15 @@ +hostname: "testserver" + +smtp_address: ":1025" +submission_address: ":1587" +submission_over_tls_address: ":1465" +monitoring_address: ":1099" + +mail_delivery_agent_bin: "test-mda" +mail_delivery_agent_args: "%to%" + +data_dir: "../.data" +mail_log_path: "../.logs/mail_log" + +suffix_separators: "+-" +drop_characters: "._" diff --git a/test/t-12-minor_dialogs/config/domains/testserver/aliases b/test/t-12-minor_dialogs/config/domains/testserver/aliases new file mode 100644 index 0000000..0c85b2c --- /dev/null +++ b/test/t-12-minor_dialogs/config/domains/testserver/aliases @@ -0,0 +1,3 @@ + +fail: | false + diff --git a/test/t-12-minor_dialogs/empty_helo.cmy b/test/t-12-minor_dialogs/empty_helo.cmy new file mode 100644 index 0000000..e3acf81 --- /dev/null +++ b/test/t-12-minor_dialogs/empty_helo.cmy @@ -0,0 +1,11 @@ + +c tcp_connect localhost:1025 + +c <~ 220 +c -> HELO +c <~ 501 +c -> EHLO +c <~ 501 +c -> HELO localhost +c <~ 250 + diff --git a/test/t-12-minor_dialogs/helo.cmy b/test/t-12-minor_dialogs/helo.cmy new file mode 100644 index 0000000..af8ab1c --- /dev/null +++ b/test/t-12-minor_dialogs/helo.cmy @@ -0,0 +1,9 @@ + +c tcp_connect localhost:1025 + +c <~ 220 +c -> HELO localhost +c <~ 250 +c -> QUIT +c <~ 221 + diff --git a/test/t-12-minor_dialogs/hosts b/test/t-12-minor_dialogs/hosts new file mode 100644 index 0000000..2b9b623 --- /dev/null +++ b/test/t-12-minor_dialogs/hosts @@ -0,0 +1 @@ +testserver localhost diff --git a/test/t-12-minor_dialogs/run.sh b/test/t-12-minor_dialogs/run.sh new file mode 100755 index 0000000..3c3f570 --- /dev/null +++ b/test/t-12-minor_dialogs/run.sh @@ -0,0 +1,26 @@ +#!/bin/bash + +set -e +. $(dirname ${0})/../util/lib.sh + +init + +generate_certs_for testserver +add_user user@testserver secretpassword + +mkdir -p .logs +chasquid -v=2 --logfile=.logs/chasquid.log --config_dir=config & +wait_until_ready 1025 + +FAILED=0 +for i in *.cmy; do + if ! chamuyero $i > .logs/$i.log 2>&1 ; then + echo "test $i failed, see .logs/$i.log" + FAILED=1 + fi +done + +if [ $FAILED == 1 ]; then + fail +fi +success diff --git a/test/t-12-minor_dialogs/sendmail.cmy b/test/t-12-minor_dialogs/sendmail.cmy new file mode 100644 index 0000000..b413e8d --- /dev/null +++ b/test/t-12-minor_dialogs/sendmail.cmy @@ -0,0 +1,23 @@ + +c tcp_connect localhost:1025 + +c <~ 220 +c -> EHLO localhost +c <... 250 HELP +c -> MAIL FROM: <> +c <~ 250 +c -> RCPT TO: user@testserver +c <~ 250 +c -> DATA +c <~ 354 +c -> From: Mailer daemon +c -> Subject: I've come to haunt you +c -> +c -> Muahahahaha +c -> +c -> +c -> . +c <~ 250 +c -> QUIT +c <~ 221 + diff --git a/test/t-12-minor_dialogs/unknown_command.cmy b/test/t-12-minor_dialogs/unknown_command.cmy new file mode 100644 index 0000000..c8673cb --- /dev/null +++ b/test/t-12-minor_dialogs/unknown_command.cmy @@ -0,0 +1,9 @@ + +c tcp_connect localhost:1025 + +c <~ 220 +c -> EHLO localhost +c <... 250 HELP +c -> WHATISTHIS +c <- 500 unknown command + diff --git a/test/util/chamuyero b/test/util/chamuyero index 8ab7d57..4cdb042 100755 --- a/test/util/chamuyero +++ b/test/util/chamuyero @@ -12,6 +12,7 @@ interactive command-line tools. import argparse import os import re +import ssl import socket import subprocess import sys @@ -97,6 +98,19 @@ class TCPSock (Sock): self.has_conn.set() +class TLSSock (Sock): + def __init__(self, addr): + host, port = addr.rsplit(":", 1) + Sock.__init__(self, (host, int(port))) + plain_sock = socket.create_connection(self.addr) + self.sock = ssl.wrap_socket(plain_sock) + + def connect(self): + self.connr = self.sock.makefile(mode="r") + self.connw = self.sock.makefile(mode="w") + self.has_conn.set() + + class Interpreter (object): """Interpreter for chamuyero scripts.""" def __init__(self): @@ -175,6 +189,11 @@ class Interpreter (object): sock.connect() self.procs[proc] = sock + elif op == "tls_connect": + sock = TLSSock(params) + sock.connect() + self.procs[proc] = sock + # -> Send to a process stdin, with a \n at the end. # .> Send to a process stdin, no \n at the end. elif op == "->":