-
Notifications
You must be signed in to change notification settings - Fork 1.2k
Expand file tree
/
Copy pathWebSocketResourcePerformanceTests.cpp
More file actions
138 lines (113 loc) · 4.15 KB
/
Copy pathWebSocketResourcePerformanceTests.cpp
File metadata and controls
138 lines (113 loc) · 4.15 KB
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
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
#include <CppUnitTest.h>
#include <Networking/IWebSocketResource.h>
#include <Test/WebSocketServer.h>
#include <unicode.h>
// Windows API
#include <TlHelp32.h>
#include <Windows.h>
// Standard library includes
#include <math.h>
#include <atomic>
#include <future>
using namespace Microsoft::React;
using namespace Microsoft::VisualStudio::CppUnitTestFramework;
using Microsoft::Common::Unicode::Utf8ToUtf16;
using Networking::IWebSocketResource;
using std::shared_ptr;
using std::string;
using std::vector;
// None of these tests are runnable
TEST_CLASS (WebSocketResourcePerformanceTest) {
static uint16_t s_port;
TEST_METHOD_CLEANUP(MethodCleanup) {
// Bug in WebSocketServer does not correctly release TCP port between test methods.
// Using a different por per test for now.
s_port++;
}
// See http://msdn.microsoft.com/en-us/library/ms686701(v=VS.85).aspx
int32_t GetCurrentThreadCount() {
DWORD procId = GetCurrentProcessId();
HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPALL, 0 /*th32ProcessID*/);
PROCESSENTRY32 entry = {0};
entry.dwSize = sizeof(entry);
BOOL procFound = true;
procFound = Process32First(snapshot, &entry);
while (procFound && entry.th32ProcessID != procId)
procFound = Process32Next(snapshot, &entry);
CloseHandle(snapshot);
if (procFound)
return entry.cntThreads;
return -1;
}
///
/// Spawn a number of WebSocket resources, have it write and read a message
/// several times, then measure the amount of allocated threads. Important. This
/// test must be run in isolation (no other tests running concurrently).
///
BEGIN_TEST_METHOD_ATTRIBUTE(ProcessThreadsPerResource)
TEST_IGNORE()
END_TEST_METHOD_ATTRIBUTE()
TEST_METHOD(ProcessThreadsPerResource) {
// About 3 seconds total running time.
// 6, if we increase this value to 100.
const int resourceTotal = 50;
const int maxWriteCount = 10;
const int expectedThreadsPerResource = 3;
const int startThreadCount = GetCurrentThreadCount();
std::atomic_int32_t threadCount = 0;
bool errorFound = false;
string errorMessage;
// WebSocket resources scope.
{
vector<shared_ptr<IWebSocketResource>> resources;
for (int i = 0; i < resourceTotal; i++) {
auto ws = IWebSocketResource::Make();
ws->SetOnMessage([this, &threadCount, &errorFound](size_t size, const string &message, bool isBinary) {
if (errorFound)
return;
auto count = this->GetCurrentThreadCount();
if (count > threadCount.load())
threadCount.store(count);
});
ws->SetOnSend([this, &threadCount, &errorFound](size_t) {
if (errorFound)
return;
auto count = this->GetCurrentThreadCount();
if (count > threadCount.load())
threadCount.store(count);
});
ws->SetOnClose([this, &threadCount, &errorFound](IWebSocketResource::CloseCode, const string & /*reason*/) {
if (errorFound)
return;
auto count = this->GetCurrentThreadCount();
if (count > threadCount.load())
threadCount.store(count);
});
ws->SetOnError([this, &errorFound, &errorMessage](IWebSocketResource::Error &&error) {
if (errorFound)
return;
errorFound = true;
errorMessage = error.Message;
});
ws->Connect("ws://localhost:5555");
resources.push_back(std::move(ws));
} // Create and store WS resources.
// Send messages.
for (auto &ws : resources) {
ws->Send("some message");
}
// Close resources.
for (auto &ws : resources) {
ws->Close();
}
}
int32_t finalThreadCount = threadCount.load();
int64_t threadsPerResource = (finalThreadCount - startThreadCount) / resourceTotal;
Assert::IsFalse(errorFound, Utf8ToUtf16(errorMessage).c_str());
Assert::AreNotEqual(finalThreadCount, 0);
Assert::IsTrue(threadsPerResource <= expectedThreadsPerResource);
}
};
/*static*/ uint16_t WebSocketResourcePerformanceTest::s_port = 5550;