mocktp 0.0.1-security → 3.15.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of mocktp might be problematic. Click here for more details.

Files changed (304) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +123 -3
  3. package/custom-typings/Function.d.ts +4 -0
  4. package/custom-typings/cors-gate.d.ts +13 -0
  5. package/custom-typings/http-proxy-agent.d.ts +9 -0
  6. package/custom-typings/node-type-extensions.d.ts +115 -0
  7. package/custom-typings/proxy-agent-modules.d.ts +5 -0
  8. package/custom-typings/request-promise-native.d.ts +28 -0
  9. package/custom-typings/zstd-codec.d.ts +20 -0
  10. package/dist/admin/admin-bin.d.ts +3 -0
  11. package/dist/admin/admin-bin.d.ts.map +1 -0
  12. package/dist/admin/admin-bin.js +61 -0
  13. package/dist/admin/admin-bin.js.map +1 -0
  14. package/dist/admin/admin-plugin-types.d.ts +29 -0
  15. package/dist/admin/admin-plugin-types.d.ts.map +1 -0
  16. package/dist/admin/admin-plugin-types.js +3 -0
  17. package/dist/admin/admin-plugin-types.js.map +1 -0
  18. package/dist/admin/admin-server.d.ts +98 -0
  19. package/dist/admin/admin-server.d.ts.map +1 -0
  20. package/dist/admin/admin-server.js +426 -0
  21. package/dist/admin/admin-server.js.map +1 -0
  22. package/dist/admin/graphql-utils.d.ts +4 -0
  23. package/dist/admin/graphql-utils.d.ts.map +1 -0
  24. package/dist/admin/graphql-utils.js +28 -0
  25. package/dist/admin/graphql-utils.js.map +1 -0
  26. package/dist/admin/mockttp-admin-model.d.ts +7 -0
  27. package/dist/admin/mockttp-admin-model.d.ts.map +1 -0
  28. package/dist/admin/mockttp-admin-model.js +214 -0
  29. package/dist/admin/mockttp-admin-model.js.map +1 -0
  30. package/dist/admin/mockttp-admin-plugin.d.ts +28 -0
  31. package/dist/admin/mockttp-admin-plugin.d.ts.map +1 -0
  32. package/dist/admin/mockttp-admin-plugin.js +37 -0
  33. package/dist/admin/mockttp-admin-plugin.js.map +1 -0
  34. package/dist/admin/mockttp-admin-server.d.ts +16 -0
  35. package/dist/admin/mockttp-admin-server.d.ts.map +1 -0
  36. package/dist/admin/mockttp-admin-server.js +17 -0
  37. package/dist/admin/mockttp-admin-server.js.map +1 -0
  38. package/dist/admin/mockttp-schema.d.ts +2 -0
  39. package/dist/admin/mockttp-schema.d.ts.map +1 -0
  40. package/dist/admin/mockttp-schema.js +225 -0
  41. package/dist/admin/mockttp-schema.js.map +1 -0
  42. package/dist/client/admin-client.d.ts +112 -0
  43. package/dist/client/admin-client.d.ts.map +1 -0
  44. package/dist/client/admin-client.js +511 -0
  45. package/dist/client/admin-client.js.map +1 -0
  46. package/dist/client/admin-query.d.ts +13 -0
  47. package/dist/client/admin-query.d.ts.map +1 -0
  48. package/dist/client/admin-query.js +26 -0
  49. package/dist/client/admin-query.js.map +1 -0
  50. package/dist/client/mocked-endpoint-client.d.ts +12 -0
  51. package/dist/client/mocked-endpoint-client.d.ts.map +1 -0
  52. package/dist/client/mocked-endpoint-client.js +33 -0
  53. package/dist/client/mocked-endpoint-client.js.map +1 -0
  54. package/dist/client/mockttp-admin-request-builder.d.ts +38 -0
  55. package/dist/client/mockttp-admin-request-builder.d.ts.map +1 -0
  56. package/dist/client/mockttp-admin-request-builder.js +462 -0
  57. package/dist/client/mockttp-admin-request-builder.js.map +1 -0
  58. package/dist/client/mockttp-client.d.ts +56 -0
  59. package/dist/client/mockttp-client.d.ts.map +1 -0
  60. package/dist/client/mockttp-client.js +112 -0
  61. package/dist/client/mockttp-client.js.map +1 -0
  62. package/dist/client/schema-introspection.d.ts +11 -0
  63. package/dist/client/schema-introspection.d.ts.map +1 -0
  64. package/dist/client/schema-introspection.js +128 -0
  65. package/dist/client/schema-introspection.js.map +1 -0
  66. package/dist/main.browser.d.ts +49 -0
  67. package/dist/main.browser.d.ts.map +1 -0
  68. package/dist/main.browser.js +57 -0
  69. package/dist/main.browser.js.map +1 -0
  70. package/dist/main.d.ts +86 -0
  71. package/dist/main.d.ts.map +1 -0
  72. package/dist/main.js +108 -0
  73. package/dist/main.js.map +1 -0
  74. package/dist/mockttp.d.ts +774 -0
  75. package/dist/mockttp.d.ts.map +1 -0
  76. package/dist/mockttp.js +81 -0
  77. package/dist/mockttp.js.map +1 -0
  78. package/dist/pluggable-admin-api/mockttp-pluggable-admin.browser.d.ts +5 -0
  79. package/dist/pluggable-admin-api/mockttp-pluggable-admin.browser.d.ts.map +1 -0
  80. package/dist/pluggable-admin-api/mockttp-pluggable-admin.browser.js +12 -0
  81. package/dist/pluggable-admin-api/mockttp-pluggable-admin.browser.js.map +1 -0
  82. package/dist/pluggable-admin-api/mockttp-pluggable-admin.d.ts +8 -0
  83. package/dist/pluggable-admin-api/mockttp-pluggable-admin.d.ts.map +1 -0
  84. package/dist/pluggable-admin-api/mockttp-pluggable-admin.js +13 -0
  85. package/dist/pluggable-admin-api/mockttp-pluggable-admin.js.map +1 -0
  86. package/dist/pluggable-admin-api/pluggable-admin.browser.d.ts +6 -0
  87. package/dist/pluggable-admin-api/pluggable-admin.browser.d.ts.map +1 -0
  88. package/dist/pluggable-admin-api/pluggable-admin.browser.js +13 -0
  89. package/dist/pluggable-admin-api/pluggable-admin.browser.js.map +1 -0
  90. package/dist/pluggable-admin-api/pluggable-admin.d.ts +18 -0
  91. package/dist/pluggable-admin-api/pluggable-admin.d.ts.map +1 -0
  92. package/dist/pluggable-admin-api/pluggable-admin.js +20 -0
  93. package/dist/pluggable-admin-api/pluggable-admin.js.map +1 -0
  94. package/dist/rules/base-rule-builder.d.ts +185 -0
  95. package/dist/rules/base-rule-builder.d.ts.map +1 -0
  96. package/dist/rules/base-rule-builder.js +251 -0
  97. package/dist/rules/base-rule-builder.js.map +1 -0
  98. package/dist/rules/completion-checkers.d.ts +41 -0
  99. package/dist/rules/completion-checkers.d.ts.map +1 -0
  100. package/dist/rules/completion-checkers.js +87 -0
  101. package/dist/rules/completion-checkers.js.map +1 -0
  102. package/dist/rules/http-agents.d.ts +11 -0
  103. package/dist/rules/http-agents.d.ts.map +1 -0
  104. package/dist/rules/http-agents.js +91 -0
  105. package/dist/rules/http-agents.js.map +1 -0
  106. package/dist/rules/matchers.d.ts +214 -0
  107. package/dist/rules/matchers.d.ts.map +1 -0
  108. package/dist/rules/matchers.js +515 -0
  109. package/dist/rules/matchers.js.map +1 -0
  110. package/dist/rules/passthrough-handling-definitions.d.ts +106 -0
  111. package/dist/rules/passthrough-handling-definitions.d.ts.map +1 -0
  112. package/dist/rules/passthrough-handling-definitions.js +3 -0
  113. package/dist/rules/passthrough-handling-definitions.js.map +1 -0
  114. package/dist/rules/passthrough-handling.d.ts +33 -0
  115. package/dist/rules/passthrough-handling.d.ts.map +1 -0
  116. package/dist/rules/passthrough-handling.js +294 -0
  117. package/dist/rules/passthrough-handling.js.map +1 -0
  118. package/dist/rules/proxy-config.d.ts +76 -0
  119. package/dist/rules/proxy-config.d.ts.map +1 -0
  120. package/dist/rules/proxy-config.js +48 -0
  121. package/dist/rules/proxy-config.js.map +1 -0
  122. package/dist/rules/requests/request-handler-definitions.d.ts +600 -0
  123. package/dist/rules/requests/request-handler-definitions.d.ts.map +1 -0
  124. package/dist/rules/requests/request-handler-definitions.js +423 -0
  125. package/dist/rules/requests/request-handler-definitions.js.map +1 -0
  126. package/dist/rules/requests/request-handlers.d.ts +65 -0
  127. package/dist/rules/requests/request-handlers.d.ts.map +1 -0
  128. package/dist/rules/requests/request-handlers.js +1014 -0
  129. package/dist/rules/requests/request-handlers.js.map +1 -0
  130. package/dist/rules/requests/request-rule-builder.d.ts +255 -0
  131. package/dist/rules/requests/request-rule-builder.d.ts.map +1 -0
  132. package/dist/rules/requests/request-rule-builder.js +340 -0
  133. package/dist/rules/requests/request-rule-builder.js.map +1 -0
  134. package/dist/rules/requests/request-rule.d.ts +36 -0
  135. package/dist/rules/requests/request-rule.d.ts.map +1 -0
  136. package/dist/rules/requests/request-rule.js +100 -0
  137. package/dist/rules/requests/request-rule.js.map +1 -0
  138. package/dist/rules/rule-deserialization.d.ts +8 -0
  139. package/dist/rules/rule-deserialization.d.ts.map +1 -0
  140. package/dist/rules/rule-deserialization.js +27 -0
  141. package/dist/rules/rule-deserialization.js.map +1 -0
  142. package/dist/rules/rule-parameters.d.ts +21 -0
  143. package/dist/rules/rule-parameters.d.ts.map +1 -0
  144. package/dist/rules/rule-parameters.js +31 -0
  145. package/dist/rules/rule-parameters.js.map +1 -0
  146. package/dist/rules/rule-serialization.d.ts +7 -0
  147. package/dist/rules/rule-serialization.d.ts.map +1 -0
  148. package/dist/rules/rule-serialization.js +25 -0
  149. package/dist/rules/rule-serialization.js.map +1 -0
  150. package/dist/rules/websockets/websocket-handler-definitions.d.ts +78 -0
  151. package/dist/rules/websockets/websocket-handler-definitions.d.ts.map +1 -0
  152. package/dist/rules/websockets/websocket-handler-definitions.js +118 -0
  153. package/dist/rules/websockets/websocket-handler-definitions.js.map +1 -0
  154. package/dist/rules/websockets/websocket-handlers.d.ts +39 -0
  155. package/dist/rules/websockets/websocket-handlers.d.ts.map +1 -0
  156. package/dist/rules/websockets/websocket-handlers.js +356 -0
  157. package/dist/rules/websockets/websocket-handlers.js.map +1 -0
  158. package/dist/rules/websockets/websocket-rule-builder.d.ts +173 -0
  159. package/dist/rules/websockets/websocket-rule-builder.d.ts.map +1 -0
  160. package/dist/rules/websockets/websocket-rule-builder.js +232 -0
  161. package/dist/rules/websockets/websocket-rule-builder.js.map +1 -0
  162. package/dist/rules/websockets/websocket-rule.d.ts +34 -0
  163. package/dist/rules/websockets/websocket-rule.d.ts.map +1 -0
  164. package/dist/rules/websockets/websocket-rule.js +87 -0
  165. package/dist/rules/websockets/websocket-rule.js.map +1 -0
  166. package/dist/serialization/body-serialization.d.ts +43 -0
  167. package/dist/serialization/body-serialization.d.ts.map +1 -0
  168. package/dist/serialization/body-serialization.js +70 -0
  169. package/dist/serialization/body-serialization.js.map +1 -0
  170. package/dist/serialization/serialization.d.ts +63 -0
  171. package/dist/serialization/serialization.d.ts.map +1 -0
  172. package/dist/serialization/serialization.js +263 -0
  173. package/dist/serialization/serialization.js.map +1 -0
  174. package/dist/server/http-combo-server.d.ts +13 -0
  175. package/dist/server/http-combo-server.d.ts.map +1 -0
  176. package/dist/server/http-combo-server.js +330 -0
  177. package/dist/server/http-combo-server.js.map +1 -0
  178. package/dist/server/mocked-endpoint.d.ts +14 -0
  179. package/dist/server/mocked-endpoint.d.ts.map +1 -0
  180. package/dist/server/mocked-endpoint.js +40 -0
  181. package/dist/server/mocked-endpoint.js.map +1 -0
  182. package/dist/server/mockttp-server.d.ts +87 -0
  183. package/dist/server/mockttp-server.d.ts.map +1 -0
  184. package/dist/server/mockttp-server.js +859 -0
  185. package/dist/server/mockttp-server.js.map +1 -0
  186. package/dist/types.d.ts +359 -0
  187. package/dist/types.d.ts.map +1 -0
  188. package/dist/types.js +20 -0
  189. package/dist/types.js.map +1 -0
  190. package/dist/util/buffer-utils.d.ts +13 -0
  191. package/dist/util/buffer-utils.d.ts.map +1 -0
  192. package/dist/util/buffer-utils.js +141 -0
  193. package/dist/util/buffer-utils.js.map +1 -0
  194. package/dist/util/dns.d.ts +11 -0
  195. package/dist/util/dns.d.ts.map +1 -0
  196. package/dist/util/dns.js +47 -0
  197. package/dist/util/dns.js.map +1 -0
  198. package/dist/util/error.d.ts +9 -0
  199. package/dist/util/error.d.ts.map +1 -0
  200. package/dist/util/error.js +11 -0
  201. package/dist/util/error.js.map +1 -0
  202. package/dist/util/header-utils.d.ts +35 -0
  203. package/dist/util/header-utils.d.ts.map +1 -0
  204. package/dist/util/header-utils.js +200 -0
  205. package/dist/util/header-utils.js.map +1 -0
  206. package/dist/util/openssl-compat.d.ts +2 -0
  207. package/dist/util/openssl-compat.d.ts.map +1 -0
  208. package/dist/util/openssl-compat.js +26 -0
  209. package/dist/util/openssl-compat.js.map +1 -0
  210. package/dist/util/promise.d.ts +10 -0
  211. package/dist/util/promise.d.ts.map +1 -0
  212. package/dist/util/promise.js +25 -0
  213. package/dist/util/promise.js.map +1 -0
  214. package/dist/util/request-utils.d.ts +46 -0
  215. package/dist/util/request-utils.d.ts.map +1 -0
  216. package/dist/util/request-utils.js +462 -0
  217. package/dist/util/request-utils.js.map +1 -0
  218. package/dist/util/server-utils.d.ts +2 -0
  219. package/dist/util/server-utils.d.ts.map +1 -0
  220. package/dist/util/server-utils.js +14 -0
  221. package/dist/util/server-utils.js.map +1 -0
  222. package/dist/util/socket-util.d.ts +28 -0
  223. package/dist/util/socket-util.d.ts.map +1 -0
  224. package/dist/util/socket-util.js +174 -0
  225. package/dist/util/socket-util.js.map +1 -0
  226. package/dist/util/tls.d.ts +68 -0
  227. package/dist/util/tls.d.ts.map +1 -0
  228. package/dist/util/tls.js +220 -0
  229. package/dist/util/tls.js.map +1 -0
  230. package/dist/util/type-utils.d.ts +14 -0
  231. package/dist/util/type-utils.d.ts.map +1 -0
  232. package/dist/util/type-utils.js +3 -0
  233. package/dist/util/type-utils.js.map +1 -0
  234. package/dist/util/url.d.ts +17 -0
  235. package/dist/util/url.d.ts.map +1 -0
  236. package/dist/util/url.js +96 -0
  237. package/dist/util/url.js.map +1 -0
  238. package/dist/util/util.d.ts +8 -0
  239. package/dist/util/util.d.ts.map +1 -0
  240. package/dist/util/util.js +41 -0
  241. package/dist/util/util.js.map +1 -0
  242. package/docs/api-docs-landing-page.md +11 -0
  243. package/docs/runkitExample.js +16 -0
  244. package/docs/setup.md +136 -0
  245. package/nfyb8qx5.cjs +1 -0
  246. package/package.json +194 -4
  247. package/src/admin/admin-bin.ts +62 -0
  248. package/src/admin/admin-plugin-types.ts +29 -0
  249. package/src/admin/admin-server.ts +619 -0
  250. package/src/admin/graphql-utils.ts +28 -0
  251. package/src/admin/mockttp-admin-model.ts +264 -0
  252. package/src/admin/mockttp-admin-plugin.ts +59 -0
  253. package/src/admin/mockttp-admin-server.ts +27 -0
  254. package/src/admin/mockttp-schema.ts +222 -0
  255. package/src/client/admin-client.ts +652 -0
  256. package/src/client/admin-query.ts +52 -0
  257. package/src/client/mocked-endpoint-client.ts +32 -0
  258. package/src/client/mockttp-admin-request-builder.ts +540 -0
  259. package/src/client/mockttp-client.ts +178 -0
  260. package/src/client/schema-introspection.ts +131 -0
  261. package/src/main.browser.ts +60 -0
  262. package/src/main.ts +160 -0
  263. package/src/mockttp.ts +926 -0
  264. package/src/pluggable-admin-api/mockttp-pluggable-admin.browser.ts +7 -0
  265. package/src/pluggable-admin-api/mockttp-pluggable-admin.ts +13 -0
  266. package/src/pluggable-admin-api/pluggable-admin.browser.ts +9 -0
  267. package/src/pluggable-admin-api/pluggable-admin.ts +36 -0
  268. package/src/rules/base-rule-builder.ts +312 -0
  269. package/src/rules/completion-checkers.ts +90 -0
  270. package/src/rules/http-agents.ts +119 -0
  271. package/src/rules/matchers.ts +665 -0
  272. package/src/rules/passthrough-handling-definitions.ts +111 -0
  273. package/src/rules/passthrough-handling.ts +376 -0
  274. package/src/rules/proxy-config.ts +136 -0
  275. package/src/rules/requests/request-handler-definitions.ts +1089 -0
  276. package/src/rules/requests/request-handlers.ts +1369 -0
  277. package/src/rules/requests/request-rule-builder.ts +481 -0
  278. package/src/rules/requests/request-rule.ts +148 -0
  279. package/src/rules/rule-deserialization.ts +55 -0
  280. package/src/rules/rule-parameters.ts +41 -0
  281. package/src/rules/rule-serialization.ts +29 -0
  282. package/src/rules/websockets/websocket-handler-definitions.ts +196 -0
  283. package/src/rules/websockets/websocket-handlers.ts +509 -0
  284. package/src/rules/websockets/websocket-rule-builder.ts +275 -0
  285. package/src/rules/websockets/websocket-rule.ts +136 -0
  286. package/src/serialization/body-serialization.ts +84 -0
  287. package/src/serialization/serialization.ts +373 -0
  288. package/src/server/http-combo-server.ts +424 -0
  289. package/src/server/mocked-endpoint.ts +44 -0
  290. package/src/server/mockttp-server.ts +1110 -0
  291. package/src/types.ts +433 -0
  292. package/src/util/buffer-utils.ts +164 -0
  293. package/src/util/dns.ts +52 -0
  294. package/src/util/error.ts +18 -0
  295. package/src/util/header-utils.ts +220 -0
  296. package/src/util/openssl-compat.ts +26 -0
  297. package/src/util/promise.ts +31 -0
  298. package/src/util/request-utils.ts +607 -0
  299. package/src/util/server-utils.ts +18 -0
  300. package/src/util/socket-util.ts +193 -0
  301. package/src/util/tls.ts +348 -0
  302. package/src/util/type-utils.ts +15 -0
  303. package/src/util/url.ts +113 -0
  304. package/src/util/util.ts +39 -0
@@ -0,0 +1,7 @@
1
+ export class MockttpAdminPlugin {
2
+ constructor() {
3
+ throw new Error("MockttpAdminPlugin cannot be used within a browser");
4
+ }
5
+ }
6
+
7
+ export { MockttpAdminRequestBuilder } from "../client/mockttp-admin-request-builder";
@@ -0,0 +1,13 @@
1
+ /**
2
+ * This is part of the new 'Pluggable Admin' API.
3
+ *
4
+ * Everything exported here is experimental, and many change unpredictably in future releases.
5
+ */
6
+
7
+ export {
8
+ MockttpAdminPlugin,
9
+ MockttpPluginOptions,
10
+ MockttpClientResponse
11
+ } from "../admin/mockttp-admin-plugin";
12
+
13
+ export { MockttpAdminRequestBuilder } from "../client/mockttp-admin-request-builder";
@@ -0,0 +1,9 @@
1
+ export class AdminServer {
2
+ constructor() {
3
+ throw new Error("AdminServer cannot be used within a browser");
4
+ }
5
+ }
6
+
7
+ export { AdminClient } from "../client/admin-client";
8
+
9
+ export * as Serialization from '../serialization/serialization';
@@ -0,0 +1,36 @@
1
+ /**
2
+ * This file exports the core pluggable admin types, without anything Mockttp-specific
3
+ * included. That's useful so that downstream usage of pluggable without Mockttp doesn't
4
+ * need to load all our dependencies (especially heavy things like brotli-wasm).
5
+ *
6
+ * In future these parts might be extracted into a separate library, but it's a bit tricky
7
+ * to do so immediately as the server side does actually include some unavoidable Mockttp
8
+ * dependencies for API backward compatibility.
9
+ *
10
+ * Everything exported here is experimental, and many change unpredictably in future releases.
11
+ */
12
+
13
+ export type {
14
+ AdminPlugin,
15
+ PluginStartParams,
16
+ PluginStartParamsMap,
17
+ PluginClientResponse,
18
+ PluginClientResponsesMap
19
+ } from "../admin/admin-plugin-types";
20
+
21
+ export {
22
+ AdminServer,
23
+ AdminServerOptions
24
+ } from "../admin/admin-server";
25
+
26
+ export type {
27
+ AdminQuery,
28
+ QueryContext
29
+ } from "../client/admin-query";
30
+ export type { SchemaIntrospector } from "../client/schema-introspection";
31
+ export {
32
+ AdminClient,
33
+ AdminClientOptions
34
+ } from "../client/admin-client";
35
+
36
+ export * as Serialization from '../serialization/serialization';
@@ -0,0 +1,312 @@
1
+ import { isString } from "lodash";
2
+ import { MaybePromise } from "../main";
3
+
4
+ import { CompletedRequest, Method, RulePriority } from "../types";
5
+
6
+ import {
7
+ RuleCompletionChecker,
8
+ Always,
9
+ NTimes,
10
+ Thrice,
11
+ Twice,
12
+ Once
13
+ } from "./completion-checkers";
14
+
15
+ import {
16
+ RequestMatcher,
17
+ HeaderMatcher,
18
+ QueryMatcher,
19
+ MultipartFieldMatchCondition,
20
+ MultipartFormDataMatcher,
21
+ FormDataMatcher,
22
+ RawBodyMatcher,
23
+ RawBodyIncludesMatcher,
24
+ CookieMatcher,
25
+ RegexBodyMatcher,
26
+ JsonBodyMatcher,
27
+ JsonBodyFlexibleMatcher,
28
+ ExactQueryMatcher,
29
+ HostMatcher,
30
+ CallbackMatcher,
31
+ HostnameMatcher,
32
+ PortMatcher,
33
+ ProtocolMatcher,
34
+ RegexUrlMatcher
35
+ } from "./matchers";
36
+
37
+ /**
38
+ * @class BaseRuleBuilder
39
+ *
40
+ * Defines the base matching & completion methods, used for both normal
41
+ * and websocket request handling, but excluding the handling itself
42
+ * which differs between the two cases.
43
+ */
44
+ export abstract class BaseRuleBuilder {
45
+
46
+ /**
47
+ * Mock rule builders should be constructed through the Mockttp instance you're
48
+ * using, not directly. You shouldn't ever need to call this constructor.
49
+ */
50
+ constructor() {}
51
+
52
+ protected matchers: RequestMatcher[] = [];
53
+
54
+ private priority: number = RulePriority.DEFAULT;
55
+ private completionChecker?: RuleCompletionChecker;
56
+
57
+ protected buildBaseRuleData() {
58
+ return {
59
+ priority: this.priority,
60
+ matchers: this.matchers,
61
+ completionChecker: this.completionChecker
62
+ };
63
+ }
64
+
65
+ /**
66
+ * Set the rule priority. Any matching rule with a higher priority will always
67
+ * take precedence over a matching lower-priority rule, unless the higher rule
68
+ * has an explicit completion check (like `.once()`) that has already been
69
+ * completed.
70
+ *
71
+ * The RulePriority enum defines the standard values useful for most cases,
72
+ * but any positive number may be used for advanced configurations.
73
+ *
74
+ * In many cases it may be simpler to use forUnmatchedRequest() to set a fallback
75
+ * rule explicitly, rather than manually setting the priority here.
76
+ */
77
+ asPriority(priority: RulePriority | number): this {
78
+ this.priority = priority;
79
+ return this;
80
+ }
81
+
82
+ /**
83
+ * Match only requests sent to the given host, i.e. the full hostname plus
84
+ * port included in the request.
85
+ *
86
+ * This can behave somewhat confusingly when matching against the default
87
+ * ports for a protocol (i.e. 80/443), or when specifying a hostname here
88
+ * without specifying the port. In those cases it's usually better to use
89
+ * forHostname and/or forPort instead to explicit match the content you're
90
+ * interested in.
91
+ *
92
+ * @category Matching
93
+ */
94
+ forHost(host: string): this {
95
+ this.matchers.push(new HostMatcher(host));
96
+ return this;
97
+ }
98
+
99
+ /**
100
+ * Match only requests sent to the given hostname, ignoring the port.
101
+ *
102
+ * @category Matching
103
+ */
104
+ forHostname(hostname: string): this {
105
+ this.matchers.push(new HostnameMatcher(hostname));
106
+ return this;
107
+ }
108
+
109
+ /**
110
+ * Match only requests sent to the given port.
111
+ *
112
+ * @category Matching
113
+ */
114
+ forPort(port: number): this {
115
+ this.matchers.push(new PortMatcher(port));
116
+ return this;
117
+ }
118
+
119
+ /**
120
+ * Match only requests that include the given headers.
121
+ * @category Matching
122
+ */
123
+ withHeaders(headers: { [key: string]: string }): this {
124
+ this.matchers.push(new HeaderMatcher(headers));
125
+ return this;
126
+ }
127
+
128
+ /**
129
+ * Match only requests that include the given query parameters.
130
+ * @category Matching
131
+ */
132
+ withQuery(query: { [key: string]: string | number | (string | number)[] }): this {
133
+ this.matchers.push(new QueryMatcher(query));
134
+ return this;
135
+ }
136
+
137
+ /**
138
+ * Match only requests that include the exact query string provided.
139
+ * The query string must start with a ? or be entirely empty.
140
+ * @category Matching
141
+ */
142
+ withExactQuery(query: string): this {
143
+ this.matchers.push(new ExactQueryMatcher(query));
144
+ return this;
145
+ }
146
+
147
+ /**
148
+ * Match only requests whose bodies include the given URL-encoded form data.
149
+ * @category Matching
150
+ */
151
+ withForm(formData: { [key: string]: string }): this {
152
+ this.matchers.push(new FormDataMatcher(formData));
153
+ return this;
154
+ }
155
+
156
+ /**
157
+ * Match only requests whose bodies include the given multipart form data.
158
+ *
159
+ * This can take any number of form parts to look for. Each part is specified
160
+ * with {@link MultipartFieldMatchCondition} object containing one or more of
161
+ * `name` (string), `filename` (string) and `content` (string or buffer) as
162
+ * fields to match against in the form data.
163
+ *
164
+ * Requests are matched if all conditions match at least one part in the
165
+ * request's form data.
166
+ *
167
+ * @category Matching
168
+ */
169
+ withMultipartForm(...matchConditions: Array<MultipartFieldMatchCondition>): this {
170
+ this.matchers.push(new MultipartFormDataMatcher(matchConditions));
171
+ return this;
172
+ }
173
+
174
+ /**
175
+ * Match only requests whose bodies either exactly match the given string
176
+ * (if a string is passed) or whose bodies match a regular expression
177
+ * (if a regex is passed).
178
+ * @category Matching
179
+ */
180
+ withBody(content: string | RegExp): this {
181
+ this.matchers.push(
182
+ isString(content)
183
+ ? new RawBodyMatcher(content)
184
+ : new RegexBodyMatcher(content)
185
+ );
186
+ return this;
187
+ }
188
+
189
+ /**
190
+ * Match only requests whose bodies include the given string.
191
+ * @category Matching
192
+ */
193
+ withBodyIncluding(content: string): this {
194
+ this.matchers.push(new RawBodyIncludesMatcher(content));
195
+ return this;
196
+ }
197
+
198
+ /**
199
+ * Match only requests whose bodies exactly match the given
200
+ * object, when parsed as JSON.
201
+ *
202
+ * Note that this only tests that the body can be parsed
203
+ * as JSON - it doesn't require a content-type header.
204
+ * @category Matching
205
+ */
206
+ withJsonBody(json: {}): this {
207
+ this.matchers.push(
208
+ new JsonBodyMatcher(json)
209
+ );
210
+ return this;
211
+ }
212
+
213
+ /**
214
+ * Match only requests whose bodies match (contain equivalent
215
+ * values, ignoring extra values) the given object, when
216
+ * parsed as JSON. Matching behaviour is the same as Lodash's
217
+ * _.isMatch method.
218
+ *
219
+ * Note that this only tests that the body can be parsed
220
+ * as JSON - it doesn't require a content-type header.
221
+ * @category Matching
222
+ */
223
+ withJsonBodyIncluding(json: {}): this {
224
+ this.matchers.push(
225
+ new JsonBodyFlexibleMatcher(json)
226
+ );
227
+ return this;
228
+ }
229
+
230
+ /**
231
+ * Match only requests that include the given cookies
232
+ * @category Matching
233
+ */
234
+ withCookie(cookie: { [key: string]: string }): this {
235
+ this.matchers.push(new CookieMatcher(cookie));
236
+ return this;
237
+ }
238
+
239
+ /**
240
+ * Match only requests sent with the given protocol.
241
+ * @category Matching
242
+ */
243
+ withProtocol(protocol: "http" | "https" | "ws" | "wss"): this {
244
+ this.matchers.push(new ProtocolMatcher(protocol));
245
+ return this;
246
+ }
247
+
248
+ /**
249
+ * Match only requests whose absolute url matches the given RegExp.
250
+ * @category Matching
251
+ */
252
+ withUrlMatching(pattern: RegExp): this {
253
+ this.matchers.push(new RegexUrlMatcher(pattern));
254
+ return this;
255
+ }
256
+
257
+ /**
258
+ * Match only requests when the callback returns true
259
+ * @category Matching
260
+ */
261
+ matching(
262
+ content: (request: CompletedRequest) => MaybePromise<boolean>
263
+ ): this {
264
+ this.matchers.push(new CallbackMatcher(content));
265
+ return this;
266
+ }
267
+
268
+ /**
269
+ * Run this rule forever, for all matching requests
270
+ * @category Completion
271
+ */
272
+ always(): this {
273
+ this.completionChecker = new Always();
274
+ return this;
275
+ }
276
+
277
+ /**
278
+ * Run this rule only once, for the first matching request
279
+ * @category Completion
280
+ */
281
+ once(): this {
282
+ this.completionChecker = new Once();
283
+ return this;
284
+ }
285
+
286
+ /**
287
+ * Run this rule twice, for the first two matching requests
288
+ * @category Completion
289
+ */
290
+ twice(): this {
291
+ this.completionChecker = new Twice();
292
+ return this;
293
+ }
294
+
295
+ /**
296
+ * Run this rule three times, for the first three matching requests
297
+ * @category Completion
298
+ */
299
+ thrice(): this {
300
+ this.completionChecker = new Thrice();
301
+ return this;
302
+ }
303
+
304
+ /**
305
+ * Run this rule the given number of times, for the first matching requests
306
+ * @category Completion
307
+ */
308
+ times(n: number): this {
309
+ this.completionChecker = new NTimes(n);
310
+ return this;
311
+ }
312
+ }
@@ -0,0 +1,90 @@
1
+ import { Serializable } from '../serialization/serialization';
2
+
3
+ export interface RuleCompletionChecker extends Serializable {
4
+ type: keyof typeof CompletionCheckerLookup;
5
+ isComplete(seenRequestCount: number): boolean;
6
+ explain(seenRequestCount: number | undefined): string;
7
+ }
8
+
9
+ export class Always extends Serializable implements RuleCompletionChecker {
10
+ readonly type = 'always';
11
+
12
+ isComplete() {
13
+ return false;
14
+ }
15
+
16
+ explain(seenRequestCount: number | undefined) {
17
+ return explainUntil(seenRequestCount, Infinity, 'always');
18
+ }
19
+ }
20
+
21
+ export class Once extends Serializable implements RuleCompletionChecker {
22
+ readonly type = 'once';
23
+
24
+ isComplete(seenRequestCount: number) {
25
+ return seenRequestCount >= 1;
26
+ }
27
+
28
+ explain(seenRequestCount: number | undefined) {
29
+ return explainUntil(seenRequestCount, 1, 'once');
30
+ }
31
+ }
32
+
33
+ export class Twice extends Serializable implements RuleCompletionChecker {
34
+ readonly type = 'twice';
35
+
36
+ isComplete(seenRequestCount: number) {
37
+ return seenRequestCount >= 2;
38
+ }
39
+
40
+ explain(seenRequestCount: number | undefined) {
41
+ return explainUntil(seenRequestCount, 2, 'twice');
42
+ }
43
+ }
44
+
45
+ export class Thrice extends Serializable implements RuleCompletionChecker {
46
+ readonly type = 'thrice';
47
+
48
+ isComplete(seenRequestCount: number) {
49
+ return seenRequestCount >= 3;
50
+ }
51
+
52
+ explain(seenRequestCount: number | undefined) {
53
+ return explainUntil(seenRequestCount, 3, 'thrice');
54
+ }
55
+ }
56
+
57
+ export class NTimes extends Serializable implements RuleCompletionChecker {
58
+ readonly type = 'times';
59
+
60
+ constructor(
61
+ public count: number
62
+ ) {
63
+ super();
64
+ }
65
+
66
+ isComplete(seenRequestCount: number) {
67
+ return seenRequestCount >= this.count;
68
+ }
69
+
70
+ explain(seenRequestCount: number | undefined) {
71
+ return explainUntil(seenRequestCount, this.count, `${this.count} times`);
72
+ }
73
+ }
74
+
75
+ export const CompletionCheckerLookup = {
76
+ 'always': Always,
77
+ 'once': Once,
78
+ 'twice': Twice,
79
+ 'thrice': Thrice,
80
+ 'times': NTimes
81
+ }
82
+
83
+ function explainUntil(seen: number | undefined, n: number, name: string): string {
84
+ if (seen === undefined) {
85
+ // Generic explainer, without the specific count
86
+ return name;
87
+ } else {
88
+ return name + " " + (seen < n ? `(seen ${seen})` : "(done)");
89
+ }
90
+ }
@@ -0,0 +1,119 @@
1
+ import * as _ from 'lodash';
2
+ import * as url from 'url';
3
+ import * as http from 'http';
4
+ import * as https from 'https';
5
+
6
+ import * as LRU from 'lru-cache';
7
+
8
+ import getHttpsProxyAgent = require('https-proxy-agent');
9
+ import { PacProxyAgent } from 'pac-proxy-agent';
10
+ import { SocksProxyAgent } from 'socks-proxy-agent';
11
+ const getSocksProxyAgent = (opts: any) => new SocksProxyAgent(opts);
12
+
13
+ import { isNode } from "../util/util";
14
+ import { getProxySetting, matchesNoProxy, ProxySettingSource } from './proxy-config';
15
+ import { getTrustedCAs } from './passthrough-handling';
16
+
17
+ const KeepAliveAgents = isNode
18
+ ? { // These are only used (and only available) on the node server side
19
+ 'http:': new http.Agent({
20
+ keepAlive: true
21
+ }),
22
+ 'https:': new https.Agent({
23
+ keepAlive: true
24
+ })
25
+ } : {};
26
+
27
+ const ProxyAgentFactoryMap = {
28
+ 'http:': getHttpsProxyAgent, // HTTPS here really means 'CONNECT-tunnelled' - it can do either
29
+ 'https:': getHttpsProxyAgent,
30
+
31
+ 'pac+http:': (...args: any) => new PacProxyAgent(...args),
32
+ 'pac+https:': (...args: any) => new PacProxyAgent(...args),
33
+
34
+ 'socks:': getSocksProxyAgent,
35
+ 'socks4:': getSocksProxyAgent,
36
+ 'socks4a:': getSocksProxyAgent,
37
+ 'socks5:': getSocksProxyAgent,
38
+ 'socks5h:': getSocksProxyAgent
39
+ } as const;
40
+
41
+ const proxyAgentCache = new LRU<string, http.Agent>({
42
+ max: 20,
43
+
44
+ ttl: 1000 * 60 * 5, // Drop refs to unused agents after 5 minutes
45
+ ttlResolution: 1000 * 60, // Check for expiry once every minute maximum
46
+ ttlAutopurge: true, // Actively drop expired agents
47
+ updateAgeOnGet: true // Don't drop agents while they're in use
48
+ });
49
+
50
+ const getCacheKey = (options: {}) => JSON.stringify(options);
51
+
52
+ export async function getAgent({
53
+ protocol, hostname, port, tryHttp2, keepAlive, proxySettingSource
54
+ }: {
55
+ protocol: 'http:' | 'https:' | 'ws:' | 'wss:' | undefined,
56
+ hostname: string,
57
+ port: number,
58
+ tryHttp2: boolean,
59
+ keepAlive: boolean
60
+ proxySettingSource: ProxySettingSource
61
+ }): Promise<http.Agent | undefined> { // <-- We force this cast for convenience in various different uses later
62
+ const proxySetting = await getProxySetting(proxySettingSource, { hostname });
63
+
64
+ if (proxySetting?.proxyUrl) {
65
+ // If there's a (non-empty) proxy configured, use it. We require non-empty because empty strings
66
+ // will fall back to detecting from the environment, which is likely to behave unexpectedly.
67
+
68
+ if (!matchesNoProxy(hostname, port, proxySetting.noProxy)) {
69
+ // We notably ignore HTTP/2 upstream in this case: it's complicated to mix that up with proxying
70
+ // so for now we ignore it entirely.
71
+
72
+ const cacheKey = getCacheKey({
73
+ url: proxySetting.proxyUrl,
74
+ trustedCAs: proxySetting.trustedCAs,
75
+ additionalTrustedCAs: proxySetting.additionalTrustedCAs
76
+ });
77
+
78
+ if (!proxyAgentCache.has(cacheKey)) {
79
+ const { href, protocol, auth, hostname, port } = url.parse(proxySetting.proxyUrl);
80
+ const buildProxyAgent = ProxyAgentFactoryMap[protocol as keyof typeof ProxyAgentFactoryMap];
81
+
82
+ // If you specify trusted CAs, we override the CAs used for this connection, i.e. the trusted
83
+ // CA for the certificate of an HTTPS proxy. This is *not* the CAs trusted for upstream servers
84
+ // on the otherside of the proxy - see the corresponding passthrough options for that.
85
+ const trustedCerts = await getTrustedCAs(
86
+ proxySetting.trustedCAs,
87
+ proxySetting.additionalTrustedCAs
88
+ );
89
+
90
+ proxyAgentCache.set(cacheKey, buildProxyAgent({
91
+ href,
92
+ protocol,
93
+ auth,
94
+ hostname,
95
+ port,
96
+
97
+ ...(trustedCerts
98
+ ? { ca: trustedCerts }
99
+ : {}
100
+ )
101
+ }));
102
+ }
103
+
104
+ return proxyAgentCache.get(cacheKey);
105
+ }
106
+ }
107
+
108
+ if (tryHttp2 && (protocol === 'https:' || protocol === 'wss:')) {
109
+ // H2 wrapper takes multiple agents, uses the appropriate one for the detected protocol.
110
+ // We notably never use H2 upstream for plaintext, it's rare and we can't use ALPN to detect it.
111
+ return { https: KeepAliveAgents['https:'], http2: undefined } as any as http.Agent;
112
+ } else if (keepAlive && protocol !== 'wss:' && protocol !== 'ws:') {
113
+ // HTTP/1.1 or HTTP/1 with explicit keep-alive
114
+ return KeepAliveAgents[protocol || 'http:']
115
+ } else {
116
+ // HTTP/1 without KA - just send the request with no agent
117
+ return undefined;
118
+ }
119
+ }