File indexing completed on 2024-05-19 05:22:51

0001 /*
0002     autotests/keyserverconfigtest.cpp
0003 
0004     This file is part of libkleopatra's test suite.
0005     SPDX-FileCopyrightText: 2021 g10 Code GmbH
0006     SPDX-FileContributor: Ingo Klöcker <dev@ingo-kloecker.de>
0007 
0008     SPDX-License-Identifier: GPL-2.0-or-later
0009 */
0010 
0011 #include <Libkleo/KeyserverConfig>
0012 
0013 #include <QString>
0014 #include <QTest>
0015 #include <QUrl>
0016 
0017 using namespace Kleo;
0018 
0019 namespace QTest
0020 {
0021 template<>
0022 inline char *toString(const KeyserverAuthentication &t)
0023 {
0024     switch (t) {
0025     case KeyserverAuthentication::Anonymous:
0026         return qstrdup("Anonymous");
0027     case KeyserverAuthentication::ActiveDirectory:
0028         return qstrdup("ActiveDirectory");
0029     case KeyserverAuthentication::Password:
0030         return qstrdup("Password");
0031     default:
0032         return qstrdup((std::string("invalid value (") + std::to_string(static_cast<int>(t)) + ")").c_str());
0033     }
0034 }
0035 
0036 template<>
0037 inline char *toString(const KeyserverConnection &t)
0038 {
0039     switch (t) {
0040     case KeyserverConnection::Default:
0041         return qstrdup("Default");
0042     case KeyserverConnection::Plain:
0043         return qstrdup("Plain");
0044     case KeyserverConnection::UseSTARTTLS:
0045         return qstrdup("UseSTARTTLS");
0046     case KeyserverConnection::TunnelThroughTLS:
0047         return qstrdup("TunnelThroughTLS");
0048     default:
0049         return qstrdup((std::string("invalid value (") + std::to_string(static_cast<int>(t)) + ")").c_str());
0050     }
0051 }
0052 }
0053 
0054 class KeyserverConfigTest : public QObject
0055 {
0056     Q_OBJECT
0057 private Q_SLOTS:
0058     void test_ldap_keyserver_on_active_directory()
0059     {
0060         const QUrl url{QStringLiteral("ldap://#ntds")};
0061         auto config = KeyserverConfig::fromUrl(url);
0062         QVERIFY(config.host().isEmpty());
0063         QCOMPARE(config.port(), -1);
0064         QVERIFY(config.user().isEmpty());
0065         QVERIFY(config.password().isEmpty());
0066         QCOMPARE(config.authentication(), KeyserverAuthentication::ActiveDirectory);
0067         QCOMPARE(config.connection(), KeyserverConnection::Default);
0068         QVERIFY(config.ldapBaseDn().isEmpty());
0069 
0070         const auto createdUrl = config.toUrl();
0071         QCOMPARE(createdUrl, url);
0072         QVERIFY(!createdUrl.hasQuery());
0073         QVERIFY(createdUrl.hasFragment());
0074     }
0075 
0076     void test_ldap_keyserver_with_authentication_via_active_directory()
0077     {
0078         const QUrl url{QStringLiteral("ldap://ldap.example.net#ntds")};
0079         auto config = KeyserverConfig::fromUrl(url);
0080         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0081         QCOMPARE(config.port(), -1);
0082         QVERIFY(config.user().isEmpty());
0083         QVERIFY(config.password().isEmpty());
0084         QCOMPARE(config.authentication(), KeyserverAuthentication::ActiveDirectory);
0085         QCOMPARE(config.connection(), KeyserverConnection::Default);
0086         QVERIFY(config.ldapBaseDn().isEmpty());
0087 
0088         const auto createdUrl = config.toUrl();
0089         QCOMPARE(createdUrl, url);
0090         QVERIFY(!createdUrl.hasQuery());
0091         QVERIFY(createdUrl.hasFragment());
0092     }
0093 
0094     void test_anonymous_ldap_keyserver()
0095     {
0096         const QUrl url{QStringLiteral("ldap://ldap.example.net")};
0097         auto config = KeyserverConfig::fromUrl(url);
0098         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0099         QCOMPARE(config.port(), -1);
0100         QVERIFY(config.user().isEmpty());
0101         QVERIFY(config.password().isEmpty());
0102         QCOMPARE(config.authentication(), KeyserverAuthentication::Anonymous);
0103         QCOMPARE(config.connection(), KeyserverConnection::Default);
0104         QVERIFY(config.ldapBaseDn().isEmpty());
0105 
0106         const auto createdUrl = config.toUrl();
0107         QCOMPARE(createdUrl, url);
0108         QVERIFY(!createdUrl.hasQuery());
0109         QVERIFY(!createdUrl.hasFragment());
0110     }
0111 
0112     void test_ldap_keyserver_with_password_authentication()
0113     {
0114         const QUrl url{QStringLiteral("ldap://user:password@ldap.example.net")};
0115         auto config = KeyserverConfig::fromUrl(url);
0116         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0117         QCOMPARE(config.port(), -1);
0118         QCOMPARE(config.user(), QLatin1StringView("user"));
0119         QCOMPARE(config.password(), QLatin1StringView("password"));
0120         QCOMPARE(config.authentication(), KeyserverAuthentication::Password);
0121         QCOMPARE(config.connection(), KeyserverConnection::Default);
0122         QVERIFY(config.ldapBaseDn().isEmpty());
0123 
0124         const auto createdUrl = config.toUrl();
0125         QCOMPARE(createdUrl, url);
0126         QVERIFY(!createdUrl.hasQuery());
0127         QVERIFY(!createdUrl.hasFragment());
0128     }
0129 
0130     void test_ldap_keyserver_with_starttls()
0131     {
0132         const QUrl url{QStringLiteral("ldap://user:password@ldap.example.net#starttls")};
0133         auto config = KeyserverConfig::fromUrl(url);
0134         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0135         QCOMPARE(config.port(), -1);
0136         QCOMPARE(config.user(), QLatin1StringView("user"));
0137         QCOMPARE(config.password(), QLatin1StringView("password"));
0138         QCOMPARE(config.authentication(), KeyserverAuthentication::Password);
0139         QCOMPARE(config.connection(), KeyserverConnection::UseSTARTTLS);
0140         QVERIFY(config.ldapBaseDn().isEmpty());
0141 
0142         const auto createdUrl = config.toUrl();
0143         QCOMPARE(createdUrl, url);
0144         QVERIFY(!createdUrl.hasQuery());
0145         QVERIFY(createdUrl.hasFragment());
0146     }
0147 
0148     void test_ldap_keyserver_with_tls_secured_tunnel()
0149     {
0150         const QUrl url{QStringLiteral("ldap://user:password@ldap.example.net#ldaptls")};
0151         auto config = KeyserverConfig::fromUrl(url);
0152         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0153         QCOMPARE(config.port(), -1);
0154         QCOMPARE(config.user(), QLatin1StringView("user"));
0155         QCOMPARE(config.password(), QLatin1StringView("password"));
0156         QCOMPARE(config.authentication(), KeyserverAuthentication::Password);
0157         QCOMPARE(config.connection(), KeyserverConnection::TunnelThroughTLS);
0158         QVERIFY(config.ldapBaseDn().isEmpty());
0159 
0160         const auto createdUrl = config.toUrl();
0161         QCOMPARE(createdUrl, url);
0162         QVERIFY(!createdUrl.hasQuery());
0163         QVERIFY(createdUrl.hasFragment());
0164     }
0165 
0166     void test_ldap_keyserver_with_explicit_plain_connection()
0167     {
0168         const QUrl url{QStringLiteral("ldap://user:password@ldap.example.net#plain")};
0169         auto config = KeyserverConfig::fromUrl(url);
0170         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0171         QCOMPARE(config.port(), -1);
0172         QCOMPARE(config.user(), QLatin1StringView("user"));
0173         QCOMPARE(config.password(), QLatin1StringView("password"));
0174         QCOMPARE(config.authentication(), KeyserverAuthentication::Password);
0175         QCOMPARE(config.connection(), KeyserverConnection::Plain);
0176         QVERIFY(config.ldapBaseDn().isEmpty());
0177 
0178         const auto createdUrl = config.toUrl();
0179         QCOMPARE(createdUrl, url);
0180         QVERIFY(!createdUrl.hasQuery());
0181         QVERIFY(createdUrl.hasFragment());
0182     }
0183 
0184     void test_ldap_keyserver_with_multiple_connection_flags()
0185     {
0186         // the last flag wins (as in dirmngr/ldapserver.c)
0187         const QUrl url{QStringLiteral("ldap://user:password@ldap.example.net#starttls,plain")};
0188         auto config = KeyserverConfig::fromUrl(url);
0189         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0190         QCOMPARE(config.port(), -1);
0191         QCOMPARE(config.user(), QLatin1StringView("user"));
0192         QCOMPARE(config.password(), QLatin1StringView("password"));
0193         QCOMPARE(config.authentication(), KeyserverAuthentication::Password);
0194         QCOMPARE(config.connection(), KeyserverConnection::Plain);
0195         QVERIFY(config.ldapBaseDn().isEmpty());
0196 
0197         const auto createdUrl = config.toUrl();
0198         // only one connection flag is added
0199         const auto expectedUrl = QUrl{QStringLiteral("ldap://user:password@ldap.example.net#plain")};
0200         QCOMPARE(createdUrl, expectedUrl);
0201         QVERIFY(!createdUrl.hasQuery());
0202         QVERIFY(createdUrl.hasFragment());
0203     }
0204 
0205     void test_ldap_keyserver_with_not_normalized_flags()
0206     {
0207         const QUrl url{QStringLiteral("ldap://ldap.example.net#startTLS, NTDS")};
0208         auto config = KeyserverConfig::fromUrl(url);
0209         QCOMPARE(config.authentication(), KeyserverAuthentication::ActiveDirectory);
0210         QCOMPARE(config.connection(), KeyserverConnection::UseSTARTTLS);
0211 
0212         const auto createdUrl = config.toUrl();
0213         const auto expectedUrl = QUrl{QStringLiteral("ldap://ldap.example.net#starttls,ntds")};
0214         QCOMPARE(createdUrl, expectedUrl);
0215         QVERIFY(!createdUrl.hasQuery());
0216         QVERIFY(createdUrl.hasFragment());
0217     }
0218 
0219     void test_ldap_keyserver_with_explicit_port()
0220     {
0221         const QUrl url{QStringLiteral("ldap://user:password@ldap.example.net:4242")};
0222         auto config = KeyserverConfig::fromUrl(url);
0223         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0224         QCOMPARE(config.port(), 4242);
0225         QCOMPARE(config.user(), QLatin1StringView("user"));
0226         QCOMPARE(config.password(), QLatin1StringView("password"));
0227         QCOMPARE(config.authentication(), KeyserverAuthentication::Password);
0228         QCOMPARE(config.connection(), KeyserverConnection::Default);
0229         QVERIFY(config.ldapBaseDn().isEmpty());
0230 
0231         const auto createdUrl = config.toUrl();
0232         QCOMPARE(createdUrl, url);
0233         QVERIFY(!createdUrl.hasQuery());
0234         QVERIFY(!createdUrl.hasFragment());
0235     }
0236 
0237     void test_ldap_keyserver_with_base_dn()
0238     {
0239         const QUrl url{QStringLiteral("ldap://user:password@ldap.example.net?base_dn")};
0240         auto config = KeyserverConfig::fromUrl(url);
0241         QCOMPARE(config.host(), QLatin1StringView("ldap.example.net"));
0242         QCOMPARE(config.port(), -1);
0243         QCOMPARE(config.user(), QLatin1StringView("user"));
0244         QCOMPARE(config.password(), QLatin1StringView("password"));
0245         QCOMPARE(config.authentication(), KeyserverAuthentication::Password);
0246         QCOMPARE(config.connection(), KeyserverConnection::Default);
0247         QCOMPARE(config.ldapBaseDn(), QLatin1StringView("base_dn"));
0248 
0249         const auto createdUrl = config.toUrl();
0250         QCOMPARE(createdUrl, url);
0251         QVERIFY(createdUrl.hasQuery());
0252         QVERIFY(!createdUrl.hasFragment());
0253     }
0254 
0255     void test_url_with_empty_string_as_user_and_password()
0256     {
0257         KeyserverConfig config;
0258         config.setHost(QStringLiteral("anonymous.example.net"));
0259         config.setUser(QStringLiteral(""));
0260         config.setPassword(QStringLiteral(""));
0261 
0262         const auto createdUrl = config.toUrl();
0263         QCOMPARE(createdUrl, QUrl{QStringLiteral("ldap://anonymous.example.net")});
0264         QVERIFY(!createdUrl.hasQuery());
0265         QVERIFY(!createdUrl.hasFragment());
0266     }
0267 
0268     void test_ldap_keyserver_with_additional_flags()
0269     {
0270         const QUrl url{QStringLiteral("ldap://ldap.example.net#flag1,StartTLS, Flag2 ,NTDS,flag 3")};
0271         auto config = KeyserverConfig::fromUrl(url);
0272         QCOMPARE(config.authentication(), KeyserverAuthentication::ActiveDirectory);
0273         QCOMPARE(config.connection(), KeyserverConnection::UseSTARTTLS);
0274         const QStringList expectedFlags{"flag1", "flag2", "flag 3"};
0275         QCOMPARE(config.additionalFlags(), expectedFlags);
0276 
0277         const auto createdUrl = config.toUrl();
0278         const auto expectedUrl = QUrl{QStringLiteral("ldap://ldap.example.net#starttls,ntds,flag1,flag2,flag 3")};
0279         QCOMPARE(createdUrl, expectedUrl);
0280         QVERIFY(!createdUrl.hasQuery());
0281         QVERIFY(createdUrl.hasFragment());
0282     }
0283 };
0284 
0285 QTEST_MAIN(KeyserverConfigTest)
0286 #include "keyserverconfigtest.moc"