@jaredwray/mockhttp 1.9.0 → 2.0.0
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.
- package/README.md +29 -7
- package/dist/index.d.mts +90 -11
- package/dist/index.mjs +202 -240
- package/package.json +17 -13
- package/site/dist/api/index.html +17983 -0
- package/site/dist/api/swagger.json +5487 -0
- package/site/dist/changelog/index.html +767 -0
- package/site/dist/changelog/page/2/index.html +578 -0
- package/site/dist/changelog/v0-1-0/index.html +453 -0
- package/site/dist/changelog/v0-2-0/index.html +437 -0
- package/site/dist/changelog/v0-2-1/index.html +438 -0
- package/site/dist/changelog/v0-2-2/index.html +436 -0
- package/site/dist/changelog/v0-2-3/index.html +440 -0
- package/site/dist/changelog/v0-3-0/index.html +443 -0
- package/site/dist/changelog/v0-4-0/index.html +437 -0
- package/site/dist/changelog/v0-4-1/index.html +441 -0
- package/site/dist/changelog/v0-4-2/index.html +446 -0
- package/site/dist/changelog/v0-4-3/index.html +437 -0
- package/site/dist/changelog/v0-5-0/index.html +443 -0
- package/site/dist/changelog/v0-6-0/index.html +444 -0
- package/site/dist/changelog/v0-6-1/index.html +441 -0
- package/site/dist/changelog/v0-7-0/index.html +445 -0
- package/site/dist/changelog/v0-8-0/index.html +440 -0
- package/site/dist/changelog/v0-9-0/index.html +437 -0
- package/site/dist/changelog/v1-0-0/index.html +446 -0
- package/site/dist/changelog/v1-0-1/index.html +437 -0
- package/site/dist/changelog/v1-1-0/index.html +445 -0
- package/site/dist/changelog/v1-2-0/index.html +443 -0
- package/site/dist/changelog/v1-3-0/index.html +448 -0
- package/site/dist/changelog/v1-4-0/index.html +445 -0
- package/site/dist/changelog/v1-5-0/index.html +439 -0
- package/site/dist/changelog/v1-5-1/index.html +443 -0
- package/site/dist/changelog/v1-6-0/index.html +467 -0
- package/site/dist/changelog/v1-7-0/index.html +462 -0
- package/site/dist/changelog/v1-8-0/index.html +481 -0
- package/site/dist/changelog/v1-8-1/index.html +457 -0
- package/site/dist/changelog/v1-9-0/index.html +495 -0
- package/site/dist/changelog/v2-0-0/index.html +500 -0
- package/site/dist/changelog-latest.json +269 -0
- package/site/dist/changelog.json +399 -0
- package/site/dist/css/api.css +1113 -0
- package/site/dist/css/highlight/highlight.min.js +1433 -0
- package/site/dist/css/highlight/styles/base16/docula.css +123 -0
- package/site/dist/css/home.css +133 -0
- package/site/dist/css/styles.css +1227 -0
- package/site/dist/css/variables.css +32 -0
- package/site/dist/docs/bins/index.html +942 -0
- package/site/dist/docs/configuration/index.html +771 -0
- package/site/dist/docs/hosted/index.html +544 -0
- package/site/dist/docs/https/index.html +758 -0
- package/site/dist/docs/index.html +601 -0
- package/site/dist/docs/library/index.html +780 -0
- package/site/dist/docs/taps/index.html +708 -0
- package/site/dist/favicon.svg +14 -0
- package/site/dist/feed.xml +1 -0
- package/site/dist/index.html +601 -0
- package/site/dist/js/api.js +363 -0
- package/site/dist/js/search.js +436 -0
- package/site/dist/llms-full.txt +7415 -0
- package/site/dist/llms.txt +40 -0
- package/site/dist/logo.svg +21 -0
- package/site/dist/robots.txt +2 -0
- package/site/dist/search-index.json +1 -0
- package/site/dist/sitemap.xml +1 -0
|
@@ -0,0 +1,767 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
|
|
4
|
+
<head>
|
|
5
|
+
<meta charset="UTF-8">
|
|
6
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
7
|
+
<meta name="description" content="HTTP mock server and httpbin replacement for API testing. Run it at mockhttp.org, in Docker, or in Node.js.">
|
|
8
|
+
<link rel="stylesheet" href="/css/variables.css">
|
|
9
|
+
<link rel="stylesheet" href="/css/styles.css">
|
|
10
|
+
<link rel="stylesheet" href="/css/highlight/styles/base16/docula.css">
|
|
11
|
+
<link rel="icon" href="/logo.svg">
|
|
12
|
+
<script>
|
|
13
|
+
(function(){
|
|
14
|
+
window.__doculaThemeKey = 'docula:theme:' + ('https://mockhttp.org').replace(/^https?:\/\//, '');
|
|
15
|
+
var mode = localStorage.getItem(window.__doculaThemeKey) || 'light';
|
|
16
|
+
var resolved = mode === 'system'
|
|
17
|
+
? (window.matchMedia('(prefers-color-scheme: light)').matches ? 'light' : 'dark')
|
|
18
|
+
: mode;
|
|
19
|
+
if (resolved === 'light') document.documentElement.setAttribute('data-theme', 'light');
|
|
20
|
+
try {
|
|
21
|
+
var authState = JSON.parse(localStorage.getItem('docula-auth-state'));
|
|
22
|
+
if (authState) {
|
|
23
|
+
window.__doculaAuth = authState;
|
|
24
|
+
if (authState.loggedIn) {
|
|
25
|
+
document.documentElement.classList.add('docula-auth-logged-in');
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
} catch (e) {
|
|
29
|
+
// Ignore localStorage parsing errors
|
|
30
|
+
}
|
|
31
|
+
if (!window.__doculaAuth) {
|
|
32
|
+
window.__doculaAuth = { loggedIn: false, displayName: null };
|
|
33
|
+
}
|
|
34
|
+
})();
|
|
35
|
+
</script>
|
|
36
|
+
<title>MockHTTP Changelog</title>
|
|
37
|
+
<script type="application/ld+json">
|
|
38
|
+
{"@context":"https://schema.org","@type":"CollectionPage","name":"MockHTTP Changelog","description":"Changelog for MockHTTP","url":"https://mockhttp.org/changelog/"}
|
|
39
|
+
</script>
|
|
40
|
+
</head>
|
|
41
|
+
|
|
42
|
+
<body>
|
|
43
|
+
<header class="header">
|
|
44
|
+
<div class="header-top">
|
|
45
|
+
<div class="header-top__content">
|
|
46
|
+
<button class="mobile-menu-toggle" id="mobile-menu-toggle" aria-label="Toggle navigation menu">
|
|
47
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="4" x2="20" y1="12" y2="12"/><line x1="4" x2="20" y1="6" y2="6"/><line x1="4" x2="20" y1="18" y2="18"/></svg>
|
|
48
|
+
</button>
|
|
49
|
+
<a href="/" class="logo-link">
|
|
50
|
+
<img alt="MockHTTP" class="logo__img" src="/logo.svg">
|
|
51
|
+
</a>
|
|
52
|
+
<nav class="header-bottom__nav">
|
|
53
|
+
<a class="header-bottom__item" href="/docs/" id="nav-docs">
|
|
54
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M12 7v14"/><path d="M3 18a1 1 0 0 1-1-1V4a1 1 0 0 1 1-1h5a4 4 0 0 1 4 4 4 4 0 0 1 4-4h5a1 1 0 0 1 1 1v13a1 1 0 0 1-1 1h-6a3 3 0 0 0-3 3 3 3 0 0 0-3-3z"/></svg>
|
|
55
|
+
<span>Documentation</span>
|
|
56
|
+
</a>
|
|
57
|
+
<a class="header-bottom__item" href="/api" id="nav-api">
|
|
58
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="m16 18 6-6-6-6"/><path d="m8 6-6 6 6 6"/></svg>
|
|
59
|
+
<span>API Reference</span>
|
|
60
|
+
</a>
|
|
61
|
+
<a class="header-bottom__item" href="/changelog/" id="nav-changelog">
|
|
62
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M11 6a13 13 0 0 0 8.4-2.8A1 1 0 0 1 21 4v12a1 1 0 0 1-1.6.8A13 13 0 0 0 11 14H5a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2z"/><path d="M6 14a12 12 0 0 0 2.4 7.2 2 2 0 0 0 3.2-2.4A8 8 0 0 1 10 14"/><path d="M8 6v8"/></svg>
|
|
63
|
+
<span>Changelog</span>
|
|
64
|
+
</a>
|
|
65
|
+
</nav>
|
|
66
|
+
<div class="header-actions">
|
|
67
|
+
<button class="search-button" id="search-button" type="button" aria-label="Search" aria-keyshortcuts="Meta+K Control+K">
|
|
68
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="11" cy="11" r="8"/><path d="m21 21-4.3-4.3"/></svg>
|
|
69
|
+
<span class="search-button__text">Search</span>
|
|
70
|
+
<span class="search-button__shortcut">⌘K</span>
|
|
71
|
+
</button>
|
|
72
|
+
<button class="theme-button" id="theme-toggle" aria-label="Theme: system (following system)">
|
|
73
|
+
<svg class="theme-button__icon theme-button__icon--system" xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect x="2" y="3" width="20" height="14" rx="2"/><line x1="8" x2="16" y1="21" y2="21"/><line x1="12" x2="12" y1="17" y2="21"/></svg>
|
|
74
|
+
<svg class="theme-button__icon theme-button__icon--sun theme-button__icon--hidden" xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="4"/><path d="M12 2v2"/><path d="M12 20v2"/><path d="m4.93 4.93 1.41 1.41"/><path d="m17.66 17.66 1.41 1.41"/><path d="M2 12h2"/><path d="M20 12h2"/><path d="m6.34 17.66-1.41 1.41"/><path d="m19.07 4.93-1.41 1.41"/></svg>
|
|
75
|
+
<svg class="theme-button__icon theme-button__icon--moon theme-button__icon--hidden" xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M20.985 12.486a9 9 0 1 1-9.473-9.472c.405-.022.617.46.402.803a6 6 0 0 0 8.268 8.268c.344-.215.825-.004.803.401"/></svg>
|
|
76
|
+
</button>
|
|
77
|
+
</div>
|
|
78
|
+
</div>
|
|
79
|
+
</div>
|
|
80
|
+
</header>
|
|
81
|
+
<aside class="mobile-sidebar" id="mobile-sidebar">
|
|
82
|
+
<nav class="mobile-nav">
|
|
83
|
+
<a class="mobile-nav__item" href="/docs/">
|
|
84
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M12 7v14"/><path d="M3 18a1 1 0 0 1-1-1V4a1 1 0 0 1 1-1h5a4 4 0 0 1 4 4 4 4 0 0 1 4-4h5a1 1 0 0 1 1 1v13a1 1 0 0 1-1 1h-6a3 3 0 0 0-3 3 3 3 0 0 0-3-3z"/></svg>
|
|
85
|
+
<span>Documentation</span>
|
|
86
|
+
</a>
|
|
87
|
+
<a class="mobile-nav__item" href="/api">
|
|
88
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="m16 18 6-6-6-6"/><path d="m8 6-6 6 6 6"/></svg>
|
|
89
|
+
<span>API Reference</span>
|
|
90
|
+
</a>
|
|
91
|
+
<a class="mobile-nav__item" href="/changelog/">
|
|
92
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M11 6a13 13 0 0 0 8.4-2.8A1 1 0 0 1 21 4v12a1 1 0 0 1-1.6.8A13 13 0 0 0 11 14H5a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2z"/><path d="M6 14a12 12 0 0 0 2.4 7.2 2 2 0 0 0 3.2-2.4A8 8 0 0 1 10 14"/><path d="M8 6v8"/></svg>
|
|
93
|
+
<span>Changelog</span>
|
|
94
|
+
</a>
|
|
95
|
+
</nav>
|
|
96
|
+
<div class="mobile-sidebar__docs" id="mobile-sidebar-docs"></div>
|
|
97
|
+
</aside>
|
|
98
|
+
<div class="sidebar-backdrop" id="sidebar-backdrop"></div>
|
|
99
|
+
<div class="search-modal" id="search-modal" hidden>
|
|
100
|
+
<div class="search-modal__backdrop" data-search-close></div>
|
|
101
|
+
<div class="search-modal__panel" role="dialog" aria-modal="true" aria-label="Search">
|
|
102
|
+
<div class="search-modal__header">
|
|
103
|
+
<svg class="search-modal__icon" xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="11" cy="11" r="8"/><path d="m21 21-4.3-4.3"/></svg>
|
|
104
|
+
<input
|
|
105
|
+
type="search"
|
|
106
|
+
id="search-input"
|
|
107
|
+
class="search-modal__input"
|
|
108
|
+
placeholder="Search"
|
|
109
|
+
autocomplete="off"
|
|
110
|
+
autocorrect="off"
|
|
111
|
+
autocapitalize="off"
|
|
112
|
+
spellcheck="false"
|
|
113
|
+
aria-label="Search"
|
|
114
|
+
aria-controls="search-results"
|
|
115
|
+
aria-activedescendant=""
|
|
116
|
+
role="combobox"
|
|
117
|
+
aria-expanded="true"
|
|
118
|
+
/>
|
|
119
|
+
<button class="search-modal__clear" id="search-clear" type="button" aria-label="Clear search" hidden>
|
|
120
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>
|
|
121
|
+
</button>
|
|
122
|
+
</div>
|
|
123
|
+
<div class="search-modal__body">
|
|
124
|
+
<ul class="search-results" id="search-results" role="listbox" aria-label="Search results"></ul>
|
|
125
|
+
<div class="search-modal__empty" id="search-empty" hidden>
|
|
126
|
+
No results for "<span class="search-modal__empty-query" id="search-empty-query"></span>"
|
|
127
|
+
</div>
|
|
128
|
+
<div class="search-modal__initial" id="search-initial">
|
|
129
|
+
Type to search the documentation.
|
|
130
|
+
</div>
|
|
131
|
+
</div>
|
|
132
|
+
<div class="search-modal__footer">
|
|
133
|
+
<span class="search-modal__hint"><kbd class="search-modal__kbd">↑</kbd><kbd class="search-modal__kbd">↓</kbd> to navigate</span>
|
|
134
|
+
<span class="search-modal__hint"><kbd class="search-modal__kbd">↵</kbd> to select</span>
|
|
135
|
+
<span class="search-modal__hint"><kbd class="search-modal__kbd">esc</kbd> to close</span>
|
|
136
|
+
</div>
|
|
137
|
+
</div>
|
|
138
|
+
</div>
|
|
139
|
+
<script>
|
|
140
|
+
window.__doculaSearch = { indexUrl: "/search-index.json" };
|
|
141
|
+
</script>
|
|
142
|
+
<script src="/js/search.js" defer></script>
|
|
143
|
+
<div class="content">
|
|
144
|
+
<main class="versions-container">
|
|
145
|
+
<div class="versions-content">
|
|
146
|
+
<h2 class="home-title">Changelog</h2>
|
|
147
|
+
<div class="changelog-entry">
|
|
148
|
+
<div class="changelog-entry-header">
|
|
149
|
+
<a class="changelog-entry-title" href="/changelog/v2-0-0/">v2.0.0</a>
|
|
150
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
151
|
+
</div>
|
|
152
|
+
<span class="changelog-entry-date">September 18, 2026</span>
|
|
153
|
+
<div class="changelog-entry-preview">
|
|
154
|
+
<p>Replace Scalar with a Docula site, run mockhttp.org on a Worker, and add initialize().</p>
|
|
155
|
+
<ul>
|
|
156
|
+
<li>
|
|
157
|
+
<p>replace Scalar with a Docula documentation site (#209)</p>
|
|
158
|
+
<pre><code class="hljs language-http"># Before 1.10.0 After 1.10.0
|
|
159
|
+
GET / → Scalar UI Docula Getting Started
|
|
160
|
+
GET /docs → Swagger UI Docula docs
|
|
161
|
+
GET /docs/json → OpenAPI JSON 404
|
|
162
|
+
GET /api/ → (none) Interactive OpenAPI
|
|
163
|
+
GET...
|
|
164
|
+
</code></pre>
|
|
165
|
+
</li>
|
|
166
|
+
</ul>
|
|
167
|
+
</div>
|
|
168
|
+
<span class="changelog-read-more">Read more →</span>
|
|
169
|
+
</div>
|
|
170
|
+
<div class="changelog-entry">
|
|
171
|
+
<div class="changelog-entry-header">
|
|
172
|
+
<a class="changelog-entry-title" href="/changelog/v1-9-0/">v1.9.0</a>
|
|
173
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
174
|
+
</div>
|
|
175
|
+
<span class="changelog-entry-date">August 19, 2026</span>
|
|
176
|
+
<div class="changelog-entry-preview">
|
|
177
|
+
<p>Stable indexed response-format templates, plus security hardening and dependency refreshes.</p>
|
|
178
|
+
<ul>
|
|
179
|
+
<li>
|
|
180
|
+
<p>add stable response format output via optional template index (#181)</p>
|
|
181
|
+
<pre><code class="hljs language-bash"><span class="hljs-comment"># Same index → byte-identical JSON. Omit the index for the previous random pick.</span>
|
|
182
|
+
curl http://localhost:3000/json/1
|
|
183
|
+
curl http://localhost:3000/html/1
|
|
184
|
+
curl http://localhost:3000/json/99
|
|
185
|
+
<span class="hljs-comment"># → 404 {"error":"Template index must be between 1 and 5"}</span>
|
|
186
|
+
</code></pre>
|
|
187
|
+
</li>
|
|
188
|
+
</ul>
|
|
189
|
+
</div>
|
|
190
|
+
<span class="changelog-read-more">Read more →</span>
|
|
191
|
+
</div>
|
|
192
|
+
<div class="changelog-entry">
|
|
193
|
+
<div class="changelog-entry-header">
|
|
194
|
+
<a class="changelog-entry-title" href="/changelog/v1-8-1/">v1.8.1</a>
|
|
195
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
196
|
+
</div>
|
|
197
|
+
<span class="changelog-entry-date">July 19, 2026</span>
|
|
198
|
+
<div class="changelog-entry-preview">
|
|
199
|
+
<p>Dependency maintenance: refresh runtime and build dependencies (incl. @fastify/static v10).</p>
|
|
200
|
+
<ul>
|
|
201
|
+
<li>update fastify, @fastify/cookie, @fastify/helmet, @fastify/rate-limit, @fastify/swagger, @fastify/swagger-ui to latest (<code>62d073a</code>, #174)</li>
|
|
202
|
+
<li>update @fastify/static to 10 (major) (<code>71501e3</code>, #178)</li>
|
|
203
|
+
<li>update @scalar/api-reference to latest (<code>7efd744</code>, #176)</li>
|
|
204
|
+
<li>update hookified to latest (<code>f46b91a</code>, #177)</li>
|
|
205
|
+
<li>update @biomejs/biome, @swc/core, tsx to latest (<code>68584a6</code>, #175)</li>
|
|
206
|
+
</ul>
|
|
207
|
+
</div>
|
|
208
|
+
<span class="changelog-read-more">Read more →</span>
|
|
209
|
+
</div>
|
|
210
|
+
<div class="changelog-entry">
|
|
211
|
+
<div class="changelog-entry-header">
|
|
212
|
+
<a class="changelog-entry-title" href="/changelog/v1-8-0/">v1.8.0</a>
|
|
213
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
214
|
+
</div>
|
|
215
|
+
<span class="changelog-entry-date">June 18, 2026</span>
|
|
216
|
+
<div class="changelog-entry-preview">
|
|
217
|
+
<p>Add request bins for capturing and inspecting HTTP requests; refresh runtime and build dependencies.</p>
|
|
218
|
+
<ul>
|
|
219
|
+
<li>
|
|
220
|
+
<p>add request bins for inspecting captured HTTP requests (<code>41e3d20</code>, #150)</p>
|
|
221
|
+
<p>Mint an ephemeral URL, send arbitrary requests to it, and read back what was captured — useful for webhook debugging.</p>
|
|
222
|
+
<pre><code class="hljs language-bash"><span class="hljs-comment"># Create a bin, send a request to it, then inspect what was captured</span>
|
|
223
|
+
ID=$(curl -s -X POST http://localhost:3000/bins | jq -r .<span class="hljs-built_in">id</span>)
|
|
224
|
+
curl -X POST...
|
|
225
|
+
</code></pre>
|
|
226
|
+
</li>
|
|
227
|
+
</ul>
|
|
228
|
+
</div>
|
|
229
|
+
<span class="changelog-read-more">Read more →</span>
|
|
230
|
+
</div>
|
|
231
|
+
<div class="changelog-entry">
|
|
232
|
+
<div class="changelog-entry-header">
|
|
233
|
+
<a class="changelog-entry-title" href="/changelog/v1-7-0/">v1.7.0</a>
|
|
234
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
235
|
+
</div>
|
|
236
|
+
<span class="changelog-entry-date">May 18, 2026</span>
|
|
237
|
+
<div class="changelog-entry-preview">
|
|
238
|
+
<p>Routine maintenance: dependency refresh (fastify, @scalar/api-reference, hookified), pnpm 11 supply-chain baseline, and GitHub Actions major upgrades.</p>
|
|
239
|
+
<ul>
|
|
240
|
+
<li>upgrade hookified 2.1.1 → 2.2.0 (<code>e431858</code>, #147)</li>
|
|
241
|
+
<li>upgrade @scalar/api-reference 1.52.1 → 1.55.3 (<code>e07afea</code>, #146)</li>
|
|
242
|
+
<li>upgrade @fastify/static 9.1.0→9.1.3, @fastify/swagger-ui 5.2.5→5.2.6, fastify 5.8.4→5.8.5 (<code>bcfddf6</code>, #145)</li>
|
|
243
|
+
</ul>
|
|
244
|
+
</div>
|
|
245
|
+
<span class="changelog-read-more">Read more →</span>
|
|
246
|
+
</div>
|
|
247
|
+
<div class="changelog-entry">
|
|
248
|
+
<div class="changelog-entry-header">
|
|
249
|
+
<a class="changelog-entry-title" href="/changelog/v1-6-0/">v1.6.0</a>
|
|
250
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
251
|
+
</div>
|
|
252
|
+
<span class="changelog-entry-date">May 16, 2026</span>
|
|
253
|
+
<div class="changelog-entry-preview">
|
|
254
|
+
<p>Flexible URL matching: trailing path segments fall back to the parsable route prefix (fixes #137).</p>
|
|
255
|
+
<ul>
|
|
256
|
+
<li>
|
|
257
|
+
<p>ignore trailing path segments after the parsable portion (<code>6f82897</code>, #139)</p>
|
|
258
|
+
<p>A Fastify <code>rewriteUrl</code> hook progressively strips trailing segments when only the static catch-all wildcard or nothing matches. Query strings are preserved and the first path segment is never stripped, so genuinely unknown URLs still 404.</p>
|
|
259
|
+
<pre><code class="hljs language-http"># Before — only an exact match worked:
|
|
260
|
+
GET /status/429 ...
|
|
261
|
+
</code></pre>
|
|
262
|
+
</li>
|
|
263
|
+
</ul>
|
|
264
|
+
</div>
|
|
265
|
+
<span class="changelog-read-more">Read more →</span>
|
|
266
|
+
</div>
|
|
267
|
+
<div class="changelog-entry">
|
|
268
|
+
<div class="changelog-entry-header">
|
|
269
|
+
<a class="changelog-entry-title" href="/changelog/v1-5-1/">v1.5.1</a>
|
|
270
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
271
|
+
</div>
|
|
272
|
+
<span class="changelog-entry-date">April 14, 2026</span>
|
|
273
|
+
<div class="changelog-entry-preview">
|
|
274
|
+
<ul>
|
|
275
|
+
<li>chore: upgrading biome, vitest, swc to latest by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/130">https://github.com/jaredwray/mockhttp/pull/130</a></li>
|
|
276
|
+
<li>chore: upgrading fastify to 5.8.4 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/131">https://github.com/jaredwray/mockhttp/pull/131</a></li>
|
|
277
|
+
<li>chore: upgrading hookified to 2.1.1 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/132">https://github.com/jaredwray/mockhttp/pull/132</a></li>
|
|
278
|
+
<li>chore: upgrading @scalar/api-reference to 1.52.1 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/133">https://github.com/jaredwray/mockhttp/pull/133</a></li>
|
|
279
|
+
</ul>
|
|
280
|
+
</div>
|
|
281
|
+
<span class="changelog-read-more">Read more →</span>
|
|
282
|
+
</div>
|
|
283
|
+
<div class="changelog-entry">
|
|
284
|
+
<div class="changelog-entry-header">
|
|
285
|
+
<a class="changelog-entry-title" href="/changelog/v1-5-0/">v1.5.0</a>
|
|
286
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
287
|
+
</div>
|
|
288
|
+
<span class="changelog-entry-date">March 17, 2026</span>
|
|
289
|
+
<div class="changelog-entry-preview">
|
|
290
|
+
<ul>
|
|
291
|
+
<li>chore: upgrading swc, biome, vitest, and rimraf by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/127">https://github.com/jaredwray/mockhttp/pull/127</a></li>
|
|
292
|
+
<li>chore: upgrading fastify and scalar by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/128">https://github.com/jaredwray/mockhttp/pull/128</a></li>
|
|
293
|
+
<li>feat: adding in http2 support by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/129">https://github.com/jaredwray/mockhttp/pull/129</a></li>
|
|
294
|
+
</ul>
|
|
295
|
+
<p><strong>Full Changelog</strong>:...</p>
|
|
296
|
+
</div>
|
|
297
|
+
<span class="changelog-read-more">Read more →</span>
|
|
298
|
+
</div>
|
|
299
|
+
<div class="changelog-entry">
|
|
300
|
+
<div class="changelog-entry-header">
|
|
301
|
+
<a class="changelog-entry-title" href="/changelog/v1-4-0/">v1.4.0</a>
|
|
302
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
303
|
+
</div>
|
|
304
|
+
<span class="changelog-entry-date">February 13, 2026</span>
|
|
305
|
+
<div class="changelog-entry-preview">
|
|
306
|
+
<ul>
|
|
307
|
+
<li>chore: removing route export files from code coverage by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/117">https://github.com/jaredwray/mockhttp/pull/117</a></li>
|
|
308
|
+
<li>chore: upgrading vitest and support modules to latest by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/118">https://github.com/jaredwray/mockhttp/pull/118</a></li>
|
|
309
|
+
<li>chore: upgrading fastify and supporting modules to latest by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/119">https://github.com/jaredwray/mockhttp/pull/119</a></li>
|
|
310
|
+
<li>chore: upgrading pino to 10.3.1 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/120">https://github.com/jaredwray/mockhttp/pull/120</a></li>
|
|
311
|
+
</ul>
|
|
312
|
+
</div>
|
|
313
|
+
<span class="changelog-read-more">Read more →</span>
|
|
314
|
+
</div>
|
|
315
|
+
<div class="changelog-entry">
|
|
316
|
+
<div class="changelog-entry-header">
|
|
317
|
+
<a class="changelog-entry-title" href="/changelog/v1-3-0/">v1.3.0</a>
|
|
318
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
319
|
+
</div>
|
|
320
|
+
<span class="changelog-entry-date">January 12, 2026</span>
|
|
321
|
+
<div class="changelog-entry-preview">
|
|
322
|
+
<ul>
|
|
323
|
+
<li>fix: [Aikido] Fix security issue in glob via minor version upgrade from 11.0.3 to 11.1.0 by @aikido-autofix[bot] in <a href="https://github.com/jaredwray/mockhttp/pull/107">https://github.com/jaredwray/mockhttp/pull/107</a></li>
|
|
324
|
+
<li>chore: upgrading vitest to 4.0.16 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/109">https://github.com/jaredwray/mockhttp/pull/109</a></li>
|
|
325
|
+
<li>chore: upgrading hookified to 1.15.0 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/110">https://github.com/jaredwray/mockhttp/pull/110</a></li>
|
|
326
|
+
<li>chore: upgrading pino to 10.1.1 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/111">https://github.com/jaredwray/mockhttp/pull/111</a></li>
|
|
327
|
+
</ul>
|
|
328
|
+
</div>
|
|
329
|
+
<span class="changelog-read-more">Read more →</span>
|
|
330
|
+
</div>
|
|
331
|
+
<div class="changelog-entry">
|
|
332
|
+
<div class="changelog-entry-header">
|
|
333
|
+
<a class="changelog-entry-title" href="/changelog/v1-2-0/">v1.2.0</a>
|
|
334
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
335
|
+
</div>
|
|
336
|
+
<span class="changelog-entry-date">December 12, 2025</span>
|
|
337
|
+
<div class="changelog-entry-preview">
|
|
338
|
+
<ul>
|
|
339
|
+
<li>chore: moving to nodejs 24 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/100">https://github.com/jaredwray/mockhttp/pull/100</a></li>
|
|
340
|
+
<li>chore: upgradint tsup to 8.5.1 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/101">https://github.com/jaredwray/mockhttp/pull/101</a></li>
|
|
341
|
+
<li>chore: upgrading hookified to 1.14.0 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/102">https://github.com/jaredwray/mockhttp/pull/102</a></li>
|
|
342
|
+
<li>chore: upgrading vitest to 4.0.15 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/103">https://github.com/jaredwray/mockhttp/pull/103</a></li>
|
|
343
|
+
</ul>
|
|
344
|
+
</div>
|
|
345
|
+
<span class="changelog-read-more">Read more →</span>
|
|
346
|
+
</div>
|
|
347
|
+
<div class="changelog-entry">
|
|
348
|
+
<div class="changelog-entry-header">
|
|
349
|
+
<a class="changelog-entry-title" href="/changelog/v1-1-0/">v1.1.0</a>
|
|
350
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
351
|
+
</div>
|
|
352
|
+
<span class="changelog-entry-date">November 11, 2025</span>
|
|
353
|
+
<div class="changelog-entry-preview">
|
|
354
|
+
<ul>
|
|
355
|
+
<li>chore: removing minify as it causes debugging issues by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/91">https://github.com/jaredwray/mockhttp/pull/91</a></li>
|
|
356
|
+
<li>fix: updating readme with correct spelling by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/92">https://github.com/jaredwray/mockhttp/pull/92</a></li>
|
|
357
|
+
<li>chore: upgrading vitest to 4.0.8 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/93">https://github.com/jaredwray/mockhttp/pull/93</a></li>
|
|
358
|
+
<li>chore: upgrading pino to 10.1.0 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/94">https://github.com/jaredwray/mockhttp/pull/94</a></li>
|
|
359
|
+
</ul>
|
|
360
|
+
</div>
|
|
361
|
+
<span class="changelog-read-more">Read more →</span>
|
|
362
|
+
</div>
|
|
363
|
+
<div class="changelog-entry">
|
|
364
|
+
<div class="changelog-entry-header">
|
|
365
|
+
<a class="changelog-entry-title" href="/changelog/v1-0-1/">v1.0.1</a>
|
|
366
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
367
|
+
</div>
|
|
368
|
+
<span class="changelog-entry-date">October 7, 2025</span>
|
|
369
|
+
<div class="changelog-entry-preview">
|
|
370
|
+
<ul>
|
|
371
|
+
<li>fix: delete endpoing allows string, JSON, or any by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/90">https://github.com/jaredwray/mockhttp/pull/90</a></li>
|
|
372
|
+
</ul>
|
|
373
|
+
<p><strong>Full Changelog</strong>: <a href="https://github.com/jaredwray/mockhttp/compare/v1.0.0...v1.0.1">https://github.com/jaredwray/mockhttp/compare/v1.0.0...v1.0.1</a></p>
|
|
374
|
+
</div>
|
|
375
|
+
<span class="changelog-read-more">Read more →</span>
|
|
376
|
+
</div>
|
|
377
|
+
<div class="changelog-entry">
|
|
378
|
+
<div class="changelog-entry-header">
|
|
379
|
+
<a class="changelog-entry-title" href="/changelog/v1-0-0/">v1.0.0</a>
|
|
380
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
381
|
+
</div>
|
|
382
|
+
<span class="changelog-entry-date">October 7, 2025</span>
|
|
383
|
+
<div class="changelog-entry-preview">
|
|
384
|
+
<ul>
|
|
385
|
+
<li>fix: docker no longer runs as default user by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/80">https://github.com/jaredwray/mockhttp/pull/80</a></li>
|
|
386
|
+
<li>chore: upgrading @biomejs/biome to 2.2.5 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/81">https://github.com/jaredwray/mockhttp/pull/81</a></li>
|
|
387
|
+
<li>chore: upgrading pino to 10.0.0 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/82">https://github.com/jaredwray/mockhttp/pull/82</a></li>
|
|
388
|
+
<li>chore: upgrading hookified to 1.12.1 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/83">https://github.com/jaredwray/mockhttp/pull/83</a></li>
|
|
389
|
+
</ul>
|
|
390
|
+
</div>
|
|
391
|
+
<span class="changelog-read-more">Read more →</span>
|
|
392
|
+
</div>
|
|
393
|
+
<div class="changelog-entry">
|
|
394
|
+
<div class="changelog-entry-header">
|
|
395
|
+
<a class="changelog-entry-title" href="/changelog/v0-9-0/">v0.9.0</a>
|
|
396
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
397
|
+
</div>
|
|
398
|
+
<span class="changelog-entry-date">August 27, 2025</span>
|
|
399
|
+
<div class="changelog-entry-preview">
|
|
400
|
+
<ul>
|
|
401
|
+
<li>feat: adding in multiple http methods for plain, html, and text by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/78">https://github.com/jaredwray/mockhttp/pull/78</a></li>
|
|
402
|
+
</ul>
|
|
403
|
+
<p><strong>Full Changelog</strong>: <a href="https://github.com/jaredwray/mockhttp/compare/v0.8.0...v0.9.0">https://github.com/jaredwray/mockhttp/compare/v0.8.0...v0.9.0</a></p>
|
|
404
|
+
</div>
|
|
405
|
+
<span class="changelog-read-more">Read more →</span>
|
|
406
|
+
</div>
|
|
407
|
+
<div class="changelog-entry">
|
|
408
|
+
<div class="changelog-entry-header">
|
|
409
|
+
<a class="changelog-entry-title" href="/changelog/v0-8-0/">v0.8.0</a>
|
|
410
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
411
|
+
</div>
|
|
412
|
+
<span class="changelog-entry-date">August 27, 2025</span>
|
|
413
|
+
<div class="changelog-entry-preview">
|
|
414
|
+
<ul>
|
|
415
|
+
<li>feat: adding in plain endpoint by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/74">https://github.com/jaredwray/mockhttp/pull/74</a></li>
|
|
416
|
+
<li>feat: adding in text endpoint by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/75">https://github.com/jaredwray/mockhttp/pull/75</a></li>
|
|
417
|
+
<li>feat: adding in html endpoint by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/76">https://github.com/jaredwray/mockhttp/pull/76</a></li>
|
|
418
|
+
<li>fix: removing eslint by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/77">https://github.com/jaredwray/mockhttp/pull/77</a></li>
|
|
419
|
+
</ul>
|
|
420
|
+
<p><strong>Full Changelog</strong>:...</p>
|
|
421
|
+
</div>
|
|
422
|
+
<span class="changelog-read-more">Read more →</span>
|
|
423
|
+
</div>
|
|
424
|
+
<div class="changelog-entry">
|
|
425
|
+
<div class="changelog-entry-header">
|
|
426
|
+
<a class="changelog-entry-title" href="/changelog/v0-7-0/">v0.7.0</a>
|
|
427
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
428
|
+
</div>
|
|
429
|
+
<span class="changelog-entry-date">August 23, 2025</span>
|
|
430
|
+
<div class="changelog-entry-preview">
|
|
431
|
+
<ul>
|
|
432
|
+
<li>feat: adding in custom traffic badge by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/65">https://github.com/jaredwray/mockhttp/pull/65</a></li>
|
|
433
|
+
<li>feat: adding in auth with basic, bearer, digest by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/66">https://github.com/jaredwray/mockhttp/pull/66</a></li>
|
|
434
|
+
<li>chore: upgrading typescript to 5.9.2 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/67">https://github.com/jaredwray/mockhttp/pull/67</a></li>
|
|
435
|
+
<li>chore: upgrading codecov to v5 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/68">https://github.com/jaredwray/mockhttp/pull/68</a></li>
|
|
436
|
+
</ul>
|
|
437
|
+
</div>
|
|
438
|
+
<span class="changelog-read-more">Read more →</span>
|
|
439
|
+
</div>
|
|
440
|
+
<div class="changelog-entry">
|
|
441
|
+
<div class="changelog-entry-header">
|
|
442
|
+
<a class="changelog-entry-title" href="/changelog/v0-6-1/">v0.6.1</a>
|
|
443
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
444
|
+
</div>
|
|
445
|
+
<span class="changelog-entry-date">July 19, 2025</span>
|
|
446
|
+
<div class="changelog-entry-preview">
|
|
447
|
+
<ul>
|
|
448
|
+
<li>chore: adding in min for cloud run by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/60">https://github.com/jaredwray/mockhttp/pull/60</a></li>
|
|
449
|
+
<li>chore: upgrading xo to 1.2.1 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/61">https://github.com/jaredwray/mockhttp/pull/61</a></li>
|
|
450
|
+
<li>chore: upgrading vitest to 3.2.4 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/62">https://github.com/jaredwray/mockhttp/pull/62</a></li>
|
|
451
|
+
<li>chore: upgrading @scalar/api-reference to 1.32.9 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/63">https://github.com/jaredwray/mockhttp/pull/63</a></li>
|
|
452
|
+
</ul>
|
|
453
|
+
</div>
|
|
454
|
+
<span class="changelog-read-more">Read more →</span>
|
|
455
|
+
</div>
|
|
456
|
+
<div class="changelog-entry">
|
|
457
|
+
<div class="changelog-entry-header">
|
|
458
|
+
<a class="changelog-entry-title" href="/changelog/v0-6-0/">v0.6.0</a>
|
|
459
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
460
|
+
</div>
|
|
461
|
+
<span class="changelog-entry-date">June 14, 2025</span>
|
|
462
|
+
<div class="changelog-entry-preview">
|
|
463
|
+
<ul>
|
|
464
|
+
<li>fix: adding in application/json for return time on cookies by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/52">https://github.com/jaredwray/mockhttp/pull/52</a></li>
|
|
465
|
+
<li>chore: upgrading vitest to 3.2.3 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/53">https://github.com/jaredwray/mockhttp/pull/53</a></li>
|
|
466
|
+
<li>chore: upgrading tsup to 8.5.0 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/54">https://github.com/jaredwray/mockhttp/pull/54</a></li>
|
|
467
|
+
<li>chore: upgrading pino to 9.7.0 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/55">https://github.com/jaredwray/mockhttp/pull/55</a></li>
|
|
468
|
+
</ul>
|
|
469
|
+
</div>
|
|
470
|
+
<span class="changelog-read-more">Read more →</span>
|
|
471
|
+
</div>
|
|
472
|
+
<div class="changelog-entry">
|
|
473
|
+
<div class="changelog-entry-header">
|
|
474
|
+
<a class="changelog-entry-title" href="/changelog/v0-5-0/">v0.5.0</a>
|
|
475
|
+
<span class="changelog-tag changelog-tag-release">Release</span>
|
|
476
|
+
</div>
|
|
477
|
+
<span class="changelog-entry-date">May 10, 2025</span>
|
|
478
|
+
<div class="changelog-entry-preview">
|
|
479
|
+
<ul>
|
|
480
|
+
<li>chore: updating github actions and scripts by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/45">https://github.com/jaredwray/mockhttp/pull/45</a></li>
|
|
481
|
+
<li>chore: upgrading @swc/core and tsx to latest by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/46">https://github.com/jaredwray/mockhttp/pull/46</a></li>
|
|
482
|
+
<li>chore: upgrading vitest to 3.1.3 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/47">https://github.com/jaredwray/mockhttp/pull/47</a></li>
|
|
483
|
+
<li>chore: upgrading hookified to 1.9.0 by @jaredwray in <a href="https://github.com/jaredwray/mockhttp/pull/48">https://github.com/jaredwray/mockhttp/pull/48</a></li>
|
|
484
|
+
</ul>
|
|
485
|
+
</div>
|
|
486
|
+
<span class="changelog-read-more">Read more →</span>
|
|
487
|
+
</div>
|
|
488
|
+
<nav class="changelog-pagination">
|
|
489
|
+
<span class="changelog-pagination-link changelog-pagination-disabled">← Newer</span>
|
|
490
|
+
<span class="changelog-pagination-info">Page 1 of 2</span>
|
|
491
|
+
<a class="changelog-pagination-link" href="/changelog/page/2/">Older →</a>
|
|
492
|
+
</nav>
|
|
493
|
+
</div>
|
|
494
|
+
</main>
|
|
495
|
+
</div>
|
|
496
|
+
<footer>
|
|
497
|
+
<a href="/llms.txt" class="footer__link">llms.txt</a>
|
|
498
|
+
<a href="/feed.xml" class="footer__link" aria-label="RSS Feed">
|
|
499
|
+
<svg class="footer__icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="currentColor"><circle cx="6.18" cy="17.82" r="2.18"/><path d="M4 4.44v2.83c7.03 0 12.73 5.7 12.73 12.73h2.83c0-8.59-6.97-15.56-15.56-15.56zm0 5.66v2.83c3.9 0 7.07 3.17 7.07 7.07h2.83c0-5.47-4.43-9.9-9.9-9.9z"/></svg>
|
|
500
|
+
</a>
|
|
501
|
+
|
|
502
|
+
<a href="https://docula.org/" target="_blank" rel="noopener noreferrer" class="footer__link" aria-label="Docula">
|
|
503
|
+
<svg class="footer__bat" xmlns="http://www.w3.org/2000/svg" viewBox="70 110 360 205" fill="currentColor"><path d="M420,173c-16.76-18-72.78-36.65-131.59-30.58A160.15,160.15,0,0,0,269,120.55c-3.78,4.52-11.15,9.45-19,9.45s-15.23-4.93-19-9.45a160.15,160.15,0,0,0-19.4,21.83C152.78,136.31,96.76,154.94,80,173c48.86,5.86,79.5,34.09,79.5,72.06,52.37,0,77,28,90.5,59.94C263.54,273,288.13,245,340.5,245,340.5,207,371.14,178.8,420,173Z"/><circle cx="239.19" cy="145.36" r="3.32" fill="#fff"/><circle cx="260.81" cy="145.36" r="3.32" fill="#fff"/></svg>
|
|
504
|
+
</a>
|
|
505
|
+
<span class="footer__updated">updated: 2026-09-18</span>
|
|
506
|
+
</footer>
|
|
507
|
+
<script src="/css/highlight/highlight.min.js"></script>
|
|
508
|
+
<script>
|
|
509
|
+
document.addEventListener('DOMContentLoaded', () => {
|
|
510
|
+
document.querySelectorAll('pre code').forEach(el => { el.textContent = el.textContent.trimEnd(); });
|
|
511
|
+
hljs.highlightAll();
|
|
512
|
+
var kbd = document.querySelector('.search-button__shortcut');
|
|
513
|
+
if (kbd) kbd.textContent = navigator.platform.indexOf('Mac') > -1 ? '⌘K' : 'Ctrl K';
|
|
514
|
+
|
|
515
|
+
// Copy code buttons
|
|
516
|
+
const copyIcon = '<svg xmlns="http://www.w3.org/2000/svg" width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect x="9" y="9" width="13" height="13" rx="2" ry="2"/><path d="M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2 2v1"/></svg>';
|
|
517
|
+
const checkIcon = '<svg xmlns="http://www.w3.org/2000/svg" width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="20 6 9 17 4 12"/></svg>';
|
|
518
|
+
document.querySelectorAll('pre').forEach(function(pre) {
|
|
519
|
+
const btn = document.createElement('button');
|
|
520
|
+
btn.className = 'copy-code-btn';
|
|
521
|
+
btn.innerHTML = copyIcon;
|
|
522
|
+
btn.setAttribute('aria-label', 'Copy code');
|
|
523
|
+
btn.addEventListener('click', function() {
|
|
524
|
+
const code = pre.querySelector('code');
|
|
525
|
+
const text = code ? code.textContent : pre.textContent;
|
|
526
|
+
navigator.clipboard.writeText(text || '').then(function() {
|
|
527
|
+
btn.innerHTML = checkIcon;
|
|
528
|
+
setTimeout(function() { btn.innerHTML = copyIcon; }, 2000);
|
|
529
|
+
});
|
|
530
|
+
});
|
|
531
|
+
pre.appendChild(btn);
|
|
532
|
+
});
|
|
533
|
+
});
|
|
534
|
+
</script>
|
|
535
|
+
<script>
|
|
536
|
+
(function() {
|
|
537
|
+
var themeKey = window.__doculaThemeKey;
|
|
538
|
+
function getMode() {
|
|
539
|
+
return localStorage.getItem(themeKey) || 'light';
|
|
540
|
+
}
|
|
541
|
+
|
|
542
|
+
function resolveTheme(mode) {
|
|
543
|
+
if (mode === 'system') {
|
|
544
|
+
return window.matchMedia('(prefers-color-scheme: light)').matches ? 'light' : 'dark';
|
|
545
|
+
}
|
|
546
|
+
return mode;
|
|
547
|
+
}
|
|
548
|
+
|
|
549
|
+
var cachedEls = null;
|
|
550
|
+
function getThemeEls() {
|
|
551
|
+
if (!cachedEls) {
|
|
552
|
+
cachedEls = {
|
|
553
|
+
systemIcon: document.querySelector('.theme-button__icon--system'),
|
|
554
|
+
sunIcon: document.querySelector('.theme-button__icon--sun'),
|
|
555
|
+
moonIcon: document.querySelector('.theme-button__icon--moon'),
|
|
556
|
+
toggle: document.getElementById('theme-toggle')
|
|
557
|
+
};
|
|
558
|
+
}
|
|
559
|
+
return cachedEls;
|
|
560
|
+
}
|
|
561
|
+
|
|
562
|
+
function applyTheme(mode) {
|
|
563
|
+
var resolved = resolveTheme(mode);
|
|
564
|
+
if (resolved === 'light') {
|
|
565
|
+
document.documentElement.setAttribute('data-theme', 'light');
|
|
566
|
+
} else {
|
|
567
|
+
document.documentElement.removeAttribute('data-theme');
|
|
568
|
+
}
|
|
569
|
+
|
|
570
|
+
var els = getThemeEls();
|
|
571
|
+
if (els.systemIcon && els.sunIcon && els.moonIcon) {
|
|
572
|
+
els.systemIcon.classList.add('theme-button__icon--hidden');
|
|
573
|
+
els.sunIcon.classList.add('theme-button__icon--hidden');
|
|
574
|
+
els.moonIcon.classList.add('theme-button__icon--hidden');
|
|
575
|
+
if (mode === 'system') {
|
|
576
|
+
els.systemIcon.classList.remove('theme-button__icon--hidden');
|
|
577
|
+
} else if (mode === 'light') {
|
|
578
|
+
els.sunIcon.classList.remove('theme-button__icon--hidden');
|
|
579
|
+
} else {
|
|
580
|
+
els.moonIcon.classList.remove('theme-button__icon--hidden');
|
|
581
|
+
}
|
|
582
|
+
}
|
|
583
|
+
|
|
584
|
+
if (els.toggle) {
|
|
585
|
+
var labels = { system: 'Theme: system (following system)', light: 'Theme: light', dark: 'Theme: dark' };
|
|
586
|
+
els.toggle.setAttribute('aria-label', labels[mode] || 'Toggle theme');
|
|
587
|
+
}
|
|
588
|
+
}
|
|
589
|
+
|
|
590
|
+
function nextMode(current) {
|
|
591
|
+
var cycle = { system: 'light', light: 'dark', dark: 'system' };
|
|
592
|
+
return cycle[current] || 'system';
|
|
593
|
+
}
|
|
594
|
+
|
|
595
|
+
var currentMode = getMode();
|
|
596
|
+
|
|
597
|
+
document.addEventListener('DOMContentLoaded', function() {
|
|
598
|
+
applyTheme(currentMode);
|
|
599
|
+
|
|
600
|
+
var els = getThemeEls();
|
|
601
|
+
if (els.toggle) {
|
|
602
|
+
els.toggle.addEventListener('click', function() {
|
|
603
|
+
currentMode = nextMode(currentMode);
|
|
604
|
+
localStorage.setItem(themeKey, currentMode);
|
|
605
|
+
applyTheme(currentMode);
|
|
606
|
+
});
|
|
607
|
+
}
|
|
608
|
+
});
|
|
609
|
+
|
|
610
|
+
window.matchMedia('(prefers-color-scheme: light)').addEventListener('change', function() {
|
|
611
|
+
if (getMode() === 'system') {
|
|
612
|
+
applyTheme('system');
|
|
613
|
+
}
|
|
614
|
+
});
|
|
615
|
+
})();
|
|
616
|
+
</script>
|
|
617
|
+
<script defer>
|
|
618
|
+
document.addEventListener('DOMContentLoaded', () => {
|
|
619
|
+
const menuToggle = document.getElementById('mobile-menu-toggle');
|
|
620
|
+
const mobileSidebar = document.getElementById('mobile-sidebar');
|
|
621
|
+
const backdrop = document.getElementById('sidebar-backdrop');
|
|
622
|
+
if (menuToggle && mobileSidebar) {
|
|
623
|
+
menuToggle.addEventListener('click', () => {
|
|
624
|
+
mobileSidebar.classList.toggle('mobile-sidebar--open');
|
|
625
|
+
if (backdrop) backdrop.classList.toggle('sidebar-backdrop--visible');
|
|
626
|
+
});
|
|
627
|
+
if (backdrop) {
|
|
628
|
+
backdrop.addEventListener('click', () => {
|
|
629
|
+
mobileSidebar.classList.remove('mobile-sidebar--open');
|
|
630
|
+
backdrop.classList.remove('sidebar-backdrop--visible');
|
|
631
|
+
});
|
|
632
|
+
}
|
|
633
|
+
}
|
|
634
|
+
|
|
635
|
+
// Page dropdown toggle (docs pages)
|
|
636
|
+
const dropdownToggle = document.getElementById('page-dropdown-toggle');
|
|
637
|
+
const dropdownList = document.getElementById('page-dropdown-list');
|
|
638
|
+
if (dropdownToggle && dropdownList) {
|
|
639
|
+
dropdownToggle.addEventListener('click', () => {
|
|
640
|
+
dropdownList.classList.toggle('page-dropdown__list--open');
|
|
641
|
+
});
|
|
642
|
+
}
|
|
643
|
+
|
|
644
|
+
// Active sidebar link highlighting
|
|
645
|
+
const sidebarLinks = document.querySelectorAll('.nav-sidebar__item');
|
|
646
|
+
const currentPath = window.location.pathname;
|
|
647
|
+
sidebarLinks.forEach((link) => {
|
|
648
|
+
if (link.getAttribute('href') === currentPath || link.getAttribute('href') === currentPath.replace(/\/$/, '')) {
|
|
649
|
+
link.classList.add('nav-sidebar__item--active');
|
|
650
|
+
}
|
|
651
|
+
});
|
|
652
|
+
|
|
653
|
+
// Sidebar section collapse/expand
|
|
654
|
+
const SIDEBAR_STORAGE_KEY = 'docula:sidebar-sections';
|
|
655
|
+
const collapsibleSections = document.querySelectorAll('.nav-sidebar__section--collapsible');
|
|
656
|
+
if (collapsibleSections.length > 0) {
|
|
657
|
+
let storedSectionState = {};
|
|
658
|
+
try {
|
|
659
|
+
storedSectionState = JSON.parse(localStorage.getItem(SIDEBAR_STORAGE_KEY) || '{}');
|
|
660
|
+
} catch (e) { storedSectionState = {}; }
|
|
661
|
+
|
|
662
|
+
const setSectionOpen = (section, toggle, open) => {
|
|
663
|
+
toggle.setAttribute('aria-expanded', open ? 'true' : 'false');
|
|
664
|
+
section.classList.toggle('nav-sidebar__section--collapsed', !open);
|
|
665
|
+
};
|
|
666
|
+
|
|
667
|
+
collapsibleSections.forEach((section, idx) => {
|
|
668
|
+
const toggle = section.querySelector('.nav-sidebar__toggle');
|
|
669
|
+
const list = section.querySelector('.nav-sidebar__list');
|
|
670
|
+
if (!toggle || !list) return;
|
|
671
|
+
const listId = 'nav-sidebar-section-' + idx;
|
|
672
|
+
list.id = listId;
|
|
673
|
+
toggle.setAttribute('aria-controls', listId);
|
|
674
|
+
|
|
675
|
+
const key = 'section-' + idx;
|
|
676
|
+
const hasStored = Object.prototype.hasOwnProperty.call(storedSectionState, key);
|
|
677
|
+
const isOpen = hasStored ? !!storedSectionState[key] : true;
|
|
678
|
+
setSectionOpen(section, toggle, isOpen);
|
|
679
|
+
|
|
680
|
+
toggle.addEventListener('click', () => {
|
|
681
|
+
const next = toggle.getAttribute('aria-expanded') !== 'true';
|
|
682
|
+
setSectionOpen(section, toggle, next);
|
|
683
|
+
storedSectionState[key] = next;
|
|
684
|
+
try {
|
|
685
|
+
localStorage.setItem(SIDEBAR_STORAGE_KEY, JSON.stringify(storedSectionState));
|
|
686
|
+
} catch (e) { /* storage unavailable */ }
|
|
687
|
+
});
|
|
688
|
+
});
|
|
689
|
+
}
|
|
690
|
+
|
|
691
|
+
// Active nav link highlighting (header + mobile). Highlight only the
|
|
692
|
+
// single most-specific link: the one whose path is the longest prefix of
|
|
693
|
+
// the current path. A plain startsWith() check lights up every link whose
|
|
694
|
+
// path merely prefixes the current one, so when the site is embedded under
|
|
695
|
+
// a base path (e.g. served at /developer with docs at that root) the
|
|
696
|
+
// Documentation link — whose path is a prefix of every page — would stay
|
|
697
|
+
// highlighted everywhere. Trailing slashes are normalized so matches stop
|
|
698
|
+
// at a path boundary. We read the anchor's resolved origin/pathname so
|
|
699
|
+
// absolute, relative, and same-origin hrefs all work, while cross-origin
|
|
700
|
+
// links and non-anchor items (e.g. the mobile logout button) are skipped.
|
|
701
|
+
const withTrailingSlash = (p) => (p.endsWith('/') ? p : p + '/');
|
|
702
|
+
const here = withTrailingSlash(currentPath);
|
|
703
|
+
const markActiveNav = (selector, activeClass) => {
|
|
704
|
+
let bestLink = null;
|
|
705
|
+
let bestLength = -1;
|
|
706
|
+
document.querySelectorAll(selector).forEach((link) => {
|
|
707
|
+
// Only same-origin anchors can match the current pathname.
|
|
708
|
+
if (!link.href || link.origin !== window.location.origin) return;
|
|
709
|
+
const base = withTrailingSlash(link.pathname);
|
|
710
|
+
if (here.startsWith(base) && base.length > bestLength) {
|
|
711
|
+
bestLink = link;
|
|
712
|
+
bestLength = base.length;
|
|
713
|
+
}
|
|
714
|
+
});
|
|
715
|
+
if (bestLink) bestLink.classList.add(activeClass);
|
|
716
|
+
};
|
|
717
|
+
markActiveNav('.header-bottom__item', 'header-bottom__item--active');
|
|
718
|
+
markActiveNav('.mobile-nav__item', 'mobile-nav__item--active');
|
|
719
|
+
|
|
720
|
+
// TOC extraction: move the inline TOC into the right sidebar and hide the original
|
|
721
|
+
const tocHeading = document.getElementById('table-of-contents');
|
|
722
|
+
if (tocHeading) {
|
|
723
|
+
const tocList = tocHeading.nextElementSibling;
|
|
724
|
+
const tocTarget = document.getElementById('toc-list');
|
|
725
|
+
if (tocList && tocList.tagName === 'UL' && tocTarget) {
|
|
726
|
+
tocTarget.innerHTML = tocList.innerHTML;
|
|
727
|
+
tocHeading.style.display = 'none';
|
|
728
|
+
tocList.style.display = 'none';
|
|
729
|
+
}
|
|
730
|
+
}
|
|
731
|
+
|
|
732
|
+
// Hide the TOC aside if it has no entries
|
|
733
|
+
const tocSidebar = document.getElementById('toc-list');
|
|
734
|
+
if (tocSidebar && tocSidebar.children.length === 0) {
|
|
735
|
+
const aside = tocSidebar.closest('.content-aside');
|
|
736
|
+
if (aside) { aside.style.display = 'none'; }
|
|
737
|
+
}
|
|
738
|
+
|
|
739
|
+
// Image lightbox
|
|
740
|
+
const lightboxOverlay = document.createElement('div');
|
|
741
|
+
lightboxOverlay.className = 'lightbox-overlay';
|
|
742
|
+
lightboxOverlay.addEventListener('click', function(e) {
|
|
743
|
+
if (e.target !== lightboxImg) lightboxOverlay.classList.remove('lightbox-overlay--visible');
|
|
744
|
+
});
|
|
745
|
+
const lightboxClose = document.createElement('button');
|
|
746
|
+
lightboxClose.className = 'lightbox-close';
|
|
747
|
+
lightboxClose.innerHTML = '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>';
|
|
748
|
+
lightboxClose.addEventListener('click', function() {
|
|
749
|
+
lightboxOverlay.classList.remove('lightbox-overlay--visible');
|
|
750
|
+
});
|
|
751
|
+
const lightboxImg = document.createElement('img');
|
|
752
|
+
lightboxOverlay.appendChild(lightboxClose);
|
|
753
|
+
lightboxOverlay.appendChild(lightboxImg);
|
|
754
|
+
document.body.appendChild(lightboxOverlay);
|
|
755
|
+
|
|
756
|
+
document.querySelectorAll('.article__main img, .changelog-entry-body img').forEach(function(img) {
|
|
757
|
+
if (img.closest('a')) return;
|
|
758
|
+
img.addEventListener('click', function() {
|
|
759
|
+
lightboxImg.src = img.src;
|
|
760
|
+
lightboxOverlay.classList.add('lightbox-overlay--visible');
|
|
761
|
+
});
|
|
762
|
+
});
|
|
763
|
+
});
|
|
764
|
+
</script>
|
|
765
|
+
</body>
|
|
766
|
+
|
|
767
|
+
</html>
|