summaryrefslogtreecommitdiff
path: root/jstests/ocsp/ocsp_stapling.js
blob: e2735f758d99d184df874433e2d810bc5f2a9caf (plain)
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
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
// Check that OCSP stapling works
// @tags: [requires_http_client, requires_ocsp_stapling]

load("jstests/ocsp/lib/mock_ocsp.js");

(function() {
"use strict";

if (!supportsStapling()) {
    return;
}

function test(serverCert, caCert, responderCertPair) {
    const ocsp_options = {
        sslMode: "requireSSL",
        sslPEMKeyFile: serverCert,
        sslCAFile: caCert,
        sslAllowInvalidHostnames: "",
        setParameter: {
            "ocspStaplingRefreshPeriodSecs": 500,
            "ocspEnabled": "true",
        },
    };

    // This is to test what happens when the responder is down,
    // making sure that we soft fail.
    let conn = null;

    assert.doesNotThrow(() => {
        conn = MongoRunner.runMongod(ocsp_options);
    });

    MongoRunner.stopMongod(conn);

    let mock_ocsp = new MockOCSPServer("", 1000, responderCertPair);
    mock_ocsp.start();

    // In this scenario, the Mongod has the ocsp response stapled
    // which should allow the connection to proceed. Even when the
    // responder says that the certificate is revoked, the mongod
    // should still have the old response stashed and doesn't have
    // to refresh the response, so the shell should connect.
    assert.doesNotThrow(() => {
        conn = MongoRunner.runMongod(ocsp_options);
    });
    mock_ocsp.stop();

    mock_ocsp = new MockOCSPServer(FAULT_REVOKED, 1000, responderCertPair);
    mock_ocsp.start();
    assert.doesNotThrow(() => {
        new Mongo(conn.host);
    });

    MongoRunner.stopMongod(conn);

    // This is the same scenario as above, except that the mongod has
    // the status saying that the certificate is revoked. If we have a shell
    // waiting to connect, it will fail because the certificate status of
    // the mongod's cert is revoked.
    Object.extend(ocsp_options, {waitForConnect: false});
    conn = MongoRunner.runMongod(ocsp_options);

    waitForServer(conn);

    assert.throws(() => {
        new Mongo(conn.host);
    });
    mock_ocsp.stop();

    mock_ocsp = new MockOCSPServer("", 1000, responderCertPair);
    mock_ocsp.start();

    assert.throws(() => {
        new Mongo(conn.host);
    });

    MongoRunner.stopMongod(conn);

    // The mongoRunner spawns a new Mongo Object to validate the collections which races
    // with the shutdown logic of the mock_ocsp responder on some platforms. We need this
    // sleep to make sure that the threads don't interfere with each other.
    sleep(1000);
    mock_ocsp.stop();
}

test(OCSP_SERVER_CERT, OCSP_CA_PEM, OCSP_DELEGATE_RESPONDER);
test(OCSP_SERVER_CERT, OCSP_CA_PEM, OCSP_CA_RESPONDER);
test(OCSP_SERVER_SIGNED_BY_INTERMEDIATE_CA_PEM,
     OCSP_INTERMEDIATE_CA_WITH_ROOT_PEM,
     OCSP_INTERMEDIATE_RESPONDER);
test(OCSP_SERVER_AND_INTERMEDIATE_APPENDED_PEM, OCSP_CA_PEM, OCSP_INTERMEDIATE_RESPONDER);
}());