MailJDTourDownloadDocsQualityTestsCoverage

Which source lines and branches the tests execute. Lines 91.5 %, branches 75.0 % (minimum 85 % and 72 %). main @ 399ffe3d · 21 October 2026 · pipeline 7238.

GCC Code Coverage Report


Directory: src/
Coverage: low: ≥ 0% medium: ≥ 75.0% high: ≥ 90.0%
Coverage Exec / Excl / Total
Lines: 100.0% 3 / 0 / 3
Functions: 100.0% 3 / 0 / 3
Branches: 54.5% 6 / 0 / 11

service/ConnectionDiagnosis.h
Line Branch Exec Source
1 #pragma once
2 #include <QAbstractSocket>
3 #include <QCoreApplication>
4 #include <QList>
5 #include <QMetaType>
6 #include <QSslError>
7 #include <QString>
8 #include <QVariantMap>
9
10 // Sprint 100 S100.1.11 (§6.2.3, D-24, G17): what went wrong when MailJD
11 // connects to a mail, rule or DAV server, in words a user can act on.
12 // diagnose() is pure: probes collect the facts (socket error, TLS errors,
13 // server reply), this class decides the kind, the sentence (what happened,
14 // the likely reason, what to do), the one primary action and the field
15 // that gets the focus. Raw server text only goes to `detail`.
16 struct CertificateInfo {
17 QString subject, issuer, validFrom, validTo, sha256;
18
2/4
✓ Branch 3 → 4 taken 18 times.
✗ Branch 3 → 7 not taken.
✓ Branch 5 → 6 taken 18 times.
✗ Branch 5 → 7 not taken.
18 bool isEmpty() const { return subject.isEmpty() && sha256.isEmpty(); }
19 };
20
21 struct Diagnosis {
22 QString kind; // "ok" or an error kind of §6.2.3
23 QString service; // "imap", "smtp", "sieve", "dav"
24 QString message; // translated, ≤ two sentences
25 QString action; // retry, app-password-help, change-server, check-server-name,
26 // ask-admin, change-security, use-port
27 QString actionLabel; // translated label of the action
28 QString field; // password, host, port, security, ""
29 QString detail; // raw server/socket text for "Details" (copyable)
30 QString helpUrl; // provider page for app passwords
31 int suggestedPort = 0;
32 CertificateInfo certificate;
33 bool ok() const { return kind == QLatin1String("ok"); }
34 QVariantMap toMap() const;
35 };
36
4/7
✗ Branch 3 → 4 not taken.
✓ Branch 3 → 5 taken 1 time.
✓ Branch 8 → 9 taken 1 time.
✗ Branch 8 → 14 not taken.
✓ Branch 9 → 10 taken 1 time.
✓ Branch 10 → 11 taken 1 time.
✗ Branch 14 → 15 not taken.
1 Q_DECLARE_METATYPE(Diagnosis)
37
38 class ConnectionDiagnosis final {
39 85 Q_DECLARE_TR_FUNCTIONS(ConnectionDiagnosis)
40 public:
41 struct Input {
42 QString service; // imap, smtp, sieve, dav
43 QString host;
44 int port = 0;
45 QString account; // the address, for the sentence
46 bool offline = false; // the network is down (QNetworkInformation)
47 bool socketFailed = false;
48 QAbstractSocket::SocketError socketError = QAbstractSocket::UnknownSocketError;
49 QList<QSslError> sslErrors;
50 bool tlsUnavailable = false; // no implicit TLS and no STARTTLS offered
51 bool protocolMismatch = false; // the greeting is not the expected protocol
52 bool authRejected = false;
53 bool rateLimited = false;
54 QString serverText; // the server's reply or socket text
55 };
56 static Diagnosis diagnose(const Input &input);
57 static Diagnosis success(const QString &service);
58 // Providers that need app passwords without OAuth (T-036): "google",
59 // "microsoft", "apple" or "".
60 static QString appPasswordProvider(const QString &addressOrHost);
61 static QString appPasswordHelpUrl(const QString &provider);
62 static QString providerName(const QString &provider);
63 // The usual port of a service with implicit TLS / STARTTLS.
64 static int usualPort(const QString &service);
65 static CertificateInfo certificateInfo(const QSslCertificate &certificate);
66 // The service as a word for the sentence ("incoming server").
67 static QString serviceWord(const QString &service);
68 private:
69 static Diagnosis certificateProblem(const Input &input, const QSslError &error);
70 };
71