@ebowwa/hetzner 0.1.0 → 0.2.1
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/actions.js +721 -439
- package/auth.js +15 -11
- package/bootstrap/cloud-init.js +109 -65
- package/bootstrap/firewall.js +30 -17
- package/bootstrap/genesis.js +89 -71
- package/bootstrap/index.js +31 -7
- package/bootstrap/kernel-hardening.js +10 -6
- package/bootstrap/kernel-hardening.test.js +182 -0
- package/bootstrap/security-audit.js +10 -6
- package/bootstrap/ssh-hardening.js +10 -6
- package/client.js +180 -83
- package/config.js +4 -2
- package/errors.js +183 -108
- package/index.js +57 -12
- package/index.ts +4 -0
- package/onboarding/doppler.ts +116 -0
- package/onboarding/git.ts +133 -0
- package/onboarding/index.ts +18 -0
- package/onboarding/onboarding.ts +193 -0
- package/onboarding/tailscale.ts +159 -0
- package/onboarding/types.ts +115 -0
- package/package.json +11 -6
- package/pricing.js +216 -113
- package/schemas.js +322 -315
- package/server-status.js +122 -0
- package/servers.js +530 -287
- package/ssh-keys.js +153 -63
- package/ssh-setup.js +253 -0
- package/ssh-setup.ts +1 -1
- package/types.js +11 -8
- package/types.ts +6 -6
- package/volumes.js +205 -82
package/actions.js
CHANGED
|
@@ -1,11 +1,83 @@
|
|
|
1
|
+
"use strict";
|
|
1
2
|
/**
|
|
2
3
|
* Hetzner Cloud API action polling and management
|
|
3
4
|
*
|
|
4
5
|
* Provides a robust polling service for monitoring async Hetzner actions
|
|
5
6
|
* with progress tracking, error handling, and cancellation support.
|
|
6
7
|
*/
|
|
7
|
-
|
|
8
|
-
|
|
8
|
+
var __assign = (this && this.__assign) || function () {
|
|
9
|
+
__assign = Object.assign || function(t) {
|
|
10
|
+
for (var s, i = 1, n = arguments.length; i < n; i++) {
|
|
11
|
+
s = arguments[i];
|
|
12
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
|
|
13
|
+
t[p] = s[p];
|
|
14
|
+
}
|
|
15
|
+
return t;
|
|
16
|
+
};
|
|
17
|
+
return __assign.apply(this, arguments);
|
|
18
|
+
};
|
|
19
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
20
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
21
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
22
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
23
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
24
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
25
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
26
|
+
});
|
|
27
|
+
};
|
|
28
|
+
var __generator = (this && this.__generator) || function (thisArg, body) {
|
|
29
|
+
var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g = Object.create((typeof Iterator === "function" ? Iterator : Object).prototype);
|
|
30
|
+
return g.next = verb(0), g["throw"] = verb(1), g["return"] = verb(2), typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
|
|
31
|
+
function verb(n) { return function (v) { return step([n, v]); }; }
|
|
32
|
+
function step(op) {
|
|
33
|
+
if (f) throw new TypeError("Generator is already executing.");
|
|
34
|
+
while (g && (g = 0, op[0] && (_ = 0)), _) try {
|
|
35
|
+
if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
|
|
36
|
+
if (y = 0, t) op = [op[0] & 2, t.value];
|
|
37
|
+
switch (op[0]) {
|
|
38
|
+
case 0: case 1: t = op; break;
|
|
39
|
+
case 4: _.label++; return { value: op[1], done: false };
|
|
40
|
+
case 5: _.label++; y = op[1]; op = [0]; continue;
|
|
41
|
+
case 7: op = _.ops.pop(); _.trys.pop(); continue;
|
|
42
|
+
default:
|
|
43
|
+
if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
|
|
44
|
+
if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
|
|
45
|
+
if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
|
|
46
|
+
if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
|
|
47
|
+
if (t[2]) _.ops.pop();
|
|
48
|
+
_.trys.pop(); continue;
|
|
49
|
+
}
|
|
50
|
+
op = body.call(thisArg, _);
|
|
51
|
+
} catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
|
|
52
|
+
if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
var _a;
|
|
56
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
57
|
+
exports.ACTION_TIMEOUTS = exports.ActionOperations = void 0;
|
|
58
|
+
exports.getActionTimeout = getActionTimeout;
|
|
59
|
+
exports.pollAction = pollAction;
|
|
60
|
+
exports.pollActions = pollActions;
|
|
61
|
+
exports.pollActionsDetailed = pollActionsDetailed;
|
|
62
|
+
exports.waitForAction = waitForAction;
|
|
63
|
+
exports.waitForMultipleActions = waitForMultipleActions;
|
|
64
|
+
exports.waitForMultipleActionsWithLimit = waitForMultipleActionsWithLimit;
|
|
65
|
+
exports.batchCheckActions = batchCheckActions;
|
|
66
|
+
exports.isActionRunning = isActionRunning;
|
|
67
|
+
exports.isActionSuccess = isActionSuccess;
|
|
68
|
+
exports.isActionError = isActionError;
|
|
69
|
+
exports.formatActionProgress = formatActionProgress;
|
|
70
|
+
exports.getActionDescription = getActionDescription;
|
|
71
|
+
exports.getPollInterval = getPollInterval;
|
|
72
|
+
exports.getAdaptivePollInterval = getAdaptivePollInterval;
|
|
73
|
+
exports.waitForActionAdaptive = waitForActionAdaptive;
|
|
74
|
+
exports.parseRateLimitHeaders = parseRateLimitHeaders;
|
|
75
|
+
exports.isRateLimitLow = isRateLimitLow;
|
|
76
|
+
exports.formatRateLimitStatus = formatRateLimitStatus;
|
|
77
|
+
exports.waitForRateLimitReset = waitForRateLimitReset;
|
|
78
|
+
exports.createProgressLogger = createProgressLogger;
|
|
79
|
+
var types_js_1 = require("./types.js");
|
|
80
|
+
var errors_js_1 = require("./errors.js");
|
|
9
81
|
// ============================================================================
|
|
10
82
|
// Action Operations Class
|
|
11
83
|
// ============================================================================
|
|
@@ -16,9 +88,8 @@ import { HetznerActionError, HetznerTimeoutError, isRetryableError, calculateRet
|
|
|
16
88
|
* polling capabilities including cancellation, progress tracking,
|
|
17
89
|
* and batch operations.
|
|
18
90
|
*/
|
|
19
|
-
|
|
20
|
-
client
|
|
21
|
-
constructor(client) {
|
|
91
|
+
var ActionOperations = /** @class */ (function () {
|
|
92
|
+
function ActionOperations(client) {
|
|
22
93
|
this.client = client;
|
|
23
94
|
}
|
|
24
95
|
/**
|
|
@@ -27,30 +98,51 @@ export class ActionOperations {
|
|
|
27
98
|
* @param id - Action ID
|
|
28
99
|
* @returns Action details
|
|
29
100
|
*/
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
101
|
+
ActionOperations.prototype.get = function (id) {
|
|
102
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
103
|
+
var response;
|
|
104
|
+
return __generator(this, function (_a) {
|
|
105
|
+
switch (_a.label) {
|
|
106
|
+
case 0: return [4 /*yield*/, this.client.request("/actions/".concat(id))];
|
|
107
|
+
case 1:
|
|
108
|
+
response = _a.sent();
|
|
109
|
+
return [2 /*return*/, response.action];
|
|
110
|
+
}
|
|
111
|
+
});
|
|
112
|
+
});
|
|
113
|
+
};
|
|
34
114
|
/**
|
|
35
115
|
* List all actions
|
|
36
116
|
*
|
|
37
|
-
* @param options - Optional filters (status, sort, etc.)
|
|
117
|
+
* @param options - Optional filters (status, sort, server_id, etc.)
|
|
38
118
|
* @returns Array of actions
|
|
39
119
|
*/
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
120
|
+
ActionOperations.prototype.list = function (options) {
|
|
121
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
122
|
+
var params, query, response;
|
|
123
|
+
return __generator(this, function (_a) {
|
|
124
|
+
switch (_a.label) {
|
|
125
|
+
case 0:
|
|
126
|
+
params = new URLSearchParams();
|
|
127
|
+
if (options === null || options === void 0 ? void 0 : options.status)
|
|
128
|
+
params.append("status", options.status);
|
|
129
|
+
if (options === null || options === void 0 ? void 0 : options.sort)
|
|
130
|
+
params.append("sort", options.sort);
|
|
131
|
+
if (options === null || options === void 0 ? void 0 : options.page)
|
|
132
|
+
params.append("page", options.page.toString());
|
|
133
|
+
if (options === null || options === void 0 ? void 0 : options.per_page)
|
|
134
|
+
params.append("per_page", options.per_page.toString());
|
|
135
|
+
if (options === null || options === void 0 ? void 0 : options.server_id)
|
|
136
|
+
params.append("server_id", options.server_id.toString());
|
|
137
|
+
query = params.toString();
|
|
138
|
+
return [4 /*yield*/, this.client.request("/actions".concat(query ? "?".concat(query) : ""))];
|
|
139
|
+
case 1:
|
|
140
|
+
response = _a.sent();
|
|
141
|
+
return [2 /*return*/, response.actions];
|
|
142
|
+
}
|
|
143
|
+
});
|
|
144
|
+
});
|
|
145
|
+
};
|
|
54
146
|
/**
|
|
55
147
|
* Poll a single action until completion (enhanced version)
|
|
56
148
|
*
|
|
@@ -76,9 +168,14 @@ export class ActionOperations {
|
|
|
76
168
|
* });
|
|
77
169
|
* ```
|
|
78
170
|
*/
|
|
79
|
-
|
|
80
|
-
return
|
|
81
|
-
|
|
171
|
+
ActionOperations.prototype.poll = function (actionId_1) {
|
|
172
|
+
return __awaiter(this, arguments, void 0, function (actionId, options) {
|
|
173
|
+
if (options === void 0) { options = {}; }
|
|
174
|
+
return __generator(this, function (_a) {
|
|
175
|
+
return [2 /*return*/, pollAction(this.client, actionId, options)];
|
|
176
|
+
});
|
|
177
|
+
});
|
|
178
|
+
};
|
|
82
179
|
/**
|
|
83
180
|
* Poll multiple actions until completion
|
|
84
181
|
*
|
|
@@ -98,9 +195,14 @@ export class ActionOperations {
|
|
|
98
195
|
* });
|
|
99
196
|
* ```
|
|
100
197
|
*/
|
|
101
|
-
|
|
102
|
-
return
|
|
103
|
-
|
|
198
|
+
ActionOperations.prototype.pollMany = function (actionIds_1) {
|
|
199
|
+
return __awaiter(this, arguments, void 0, function (actionIds, options) {
|
|
200
|
+
if (options === void 0) { options = {}; }
|
|
201
|
+
return __generator(this, function (_a) {
|
|
202
|
+
return [2 /*return*/, pollActions(this.client, actionIds, options)];
|
|
203
|
+
});
|
|
204
|
+
});
|
|
205
|
+
};
|
|
104
206
|
/**
|
|
105
207
|
* Poll multiple actions with detailed result tracking
|
|
106
208
|
*
|
|
@@ -122,9 +224,14 @@ export class ActionOperations {
|
|
|
122
224
|
* }
|
|
123
225
|
* ```
|
|
124
226
|
*/
|
|
125
|
-
|
|
126
|
-
return
|
|
127
|
-
|
|
227
|
+
ActionOperations.prototype.pollManyDetailed = function (actionIds_1) {
|
|
228
|
+
return __awaiter(this, arguments, void 0, function (actionIds, options) {
|
|
229
|
+
if (options === void 0) { options = {}; }
|
|
230
|
+
return __generator(this, function (_a) {
|
|
231
|
+
return [2 /*return*/, pollActionsDetailed(this.client, actionIds, options)];
|
|
232
|
+
});
|
|
233
|
+
});
|
|
234
|
+
};
|
|
128
235
|
/**
|
|
129
236
|
* Wait for an action to complete (backward compatible alias)
|
|
130
237
|
*
|
|
@@ -133,9 +240,13 @@ export class ActionOperations {
|
|
|
133
240
|
* @returns Completed action
|
|
134
241
|
* @deprecated Use poll() instead for new code
|
|
135
242
|
*/
|
|
136
|
-
|
|
137
|
-
return
|
|
138
|
-
|
|
243
|
+
ActionOperations.prototype.waitFor = function (id, options) {
|
|
244
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
245
|
+
return __generator(this, function (_a) {
|
|
246
|
+
return [2 /*return*/, waitForAction(this.client, id, options)];
|
|
247
|
+
});
|
|
248
|
+
});
|
|
249
|
+
};
|
|
139
250
|
/**
|
|
140
251
|
* Wait for multiple actions to complete (backward compatible alias)
|
|
141
252
|
*
|
|
@@ -144,19 +255,29 @@ export class ActionOperations {
|
|
|
144
255
|
* @returns Array of completed actions
|
|
145
256
|
* @deprecated Use pollMany() instead for new code
|
|
146
257
|
*/
|
|
147
|
-
|
|
148
|
-
return
|
|
149
|
-
|
|
258
|
+
ActionOperations.prototype.waitForMany = function (ids, options) {
|
|
259
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
260
|
+
return __generator(this, function (_a) {
|
|
261
|
+
return [2 /*return*/, waitForMultipleActions(this.client, ids, options)];
|
|
262
|
+
});
|
|
263
|
+
});
|
|
264
|
+
};
|
|
150
265
|
/**
|
|
151
266
|
* Batch check multiple actions (no polling, single fetch)
|
|
152
267
|
*
|
|
153
268
|
* @param ids - Array of action IDs
|
|
154
269
|
* @returns Map of action ID to action
|
|
155
270
|
*/
|
|
156
|
-
|
|
157
|
-
return
|
|
158
|
-
|
|
159
|
-
|
|
271
|
+
ActionOperations.prototype.batchCheck = function (ids) {
|
|
272
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
273
|
+
return __generator(this, function (_a) {
|
|
274
|
+
return [2 /*return*/, batchCheckActions(this.client, ids)];
|
|
275
|
+
});
|
|
276
|
+
});
|
|
277
|
+
};
|
|
278
|
+
return ActionOperations;
|
|
279
|
+
}());
|
|
280
|
+
exports.ActionOperations = ActionOperations;
|
|
160
281
|
// ============================================================================
|
|
161
282
|
// Action Timeouts
|
|
162
283
|
// ============================================================================
|
|
@@ -164,81 +285,81 @@ export class ActionOperations {
|
|
|
164
285
|
* Default timeouts for different action types (in milliseconds)
|
|
165
286
|
* Adjusted based on typical operation durations
|
|
166
287
|
*/
|
|
167
|
-
|
|
288
|
+
exports.ACTION_TIMEOUTS = (_a = {},
|
|
168
289
|
// Quick operations (under 1 minute)
|
|
169
|
-
[ActionCommand.StartServer]
|
|
170
|
-
[ActionCommand.StopServer]
|
|
171
|
-
[ActionCommand.RebootServer]
|
|
172
|
-
[ActionCommand.Poweroff]
|
|
173
|
-
[ActionCommand.ShutdownServer]
|
|
174
|
-
[ActionCommand.ResetServer]
|
|
290
|
+
_a[types_js_1.ActionCommand.StartServer] = 60000,
|
|
291
|
+
_a[types_js_1.ActionCommand.StopServer] = 60000,
|
|
292
|
+
_a[types_js_1.ActionCommand.RebootServer] = 120000,
|
|
293
|
+
_a[types_js_1.ActionCommand.Poweroff] = 60000,
|
|
294
|
+
_a[types_js_1.ActionCommand.ShutdownServer] = 60000,
|
|
295
|
+
_a[types_js_1.ActionCommand.ResetServer] = 60000,
|
|
175
296
|
// Medium operations (1-5 minutes)
|
|
176
|
-
[ActionCommand.CreateServer]
|
|
177
|
-
[ActionCommand.DeleteServer]
|
|
178
|
-
[ActionCommand.ChangeServerType]
|
|
179
|
-
[ActionCommand.ChangeDnsPtr]
|
|
297
|
+
_a[types_js_1.ActionCommand.CreateServer] = 300000,
|
|
298
|
+
_a[types_js_1.ActionCommand.DeleteServer] = 180000,
|
|
299
|
+
_a[types_js_1.ActionCommand.ChangeServerType] = 600000,
|
|
300
|
+
_a[types_js_1.ActionCommand.ChangeDnsPtr] = 30000,
|
|
180
301
|
// Long operations (5-30 minutes)
|
|
181
|
-
[ActionCommand.RebuildServer]
|
|
182
|
-
[ActionCommand.CreateImage]
|
|
183
|
-
[ActionCommand.EnableRescue]
|
|
184
|
-
[ActionCommand.DisableRescue]
|
|
302
|
+
_a[types_js_1.ActionCommand.RebuildServer] = 900000,
|
|
303
|
+
_a[types_js_1.ActionCommand.CreateImage] = 1800000,
|
|
304
|
+
_a[types_js_1.ActionCommand.EnableRescue] = 120000,
|
|
305
|
+
_a[types_js_1.ActionCommand.DisableRescue] = 60000,
|
|
185
306
|
// Volume operations
|
|
186
|
-
[ActionCommand.CreateVolume]
|
|
187
|
-
[ActionCommand.DeleteVolume]
|
|
188
|
-
[ActionCommand.AttachVolume]
|
|
189
|
-
[ActionCommand.DetachVolume]
|
|
190
|
-
[ActionCommand.ResizeVolume]
|
|
307
|
+
_a[types_js_1.ActionCommand.CreateVolume] = 300000,
|
|
308
|
+
_a[types_js_1.ActionCommand.DeleteVolume] = 180000,
|
|
309
|
+
_a[types_js_1.ActionCommand.AttachVolume] = 120000,
|
|
310
|
+
_a[types_js_1.ActionCommand.DetachVolume] = 60000,
|
|
311
|
+
_a[types_js_1.ActionCommand.ResizeVolume] = 600000,
|
|
191
312
|
// Network operations
|
|
192
|
-
[ActionCommand.AddSubnet]
|
|
193
|
-
[ActionCommand.DeleteSubnet]
|
|
194
|
-
[ActionCommand.AddRoute]
|
|
195
|
-
[ActionCommand.DeleteRoute]
|
|
196
|
-
[ActionCommand.ChangeIpRange]
|
|
197
|
-
[ActionCommand.AttachToNetwork]
|
|
198
|
-
[ActionCommand.DetachFromNetwork]
|
|
313
|
+
_a[types_js_1.ActionCommand.AddSubnet] = 60000,
|
|
314
|
+
_a[types_js_1.ActionCommand.DeleteSubnet] = 60000,
|
|
315
|
+
_a[types_js_1.ActionCommand.AddRoute] = 60000,
|
|
316
|
+
_a[types_js_1.ActionCommand.DeleteRoute] = 60000,
|
|
317
|
+
_a[types_js_1.ActionCommand.ChangeIpRange] = 120000,
|
|
318
|
+
_a[types_js_1.ActionCommand.AttachToNetwork] = 60000,
|
|
319
|
+
_a[types_js_1.ActionCommand.DetachFromNetwork] = 60000,
|
|
199
320
|
// Floating IP operations
|
|
200
|
-
[ActionCommand.AssignFloatingIp]
|
|
201
|
-
[ActionCommand.UnassignFloatingIp]
|
|
321
|
+
_a[types_js_1.ActionCommand.AssignFloatingIp] = 60000,
|
|
322
|
+
_a[types_js_1.ActionCommand.UnassignFloatingIp] = 60000,
|
|
202
323
|
// Load Balancer operations
|
|
203
|
-
[ActionCommand.CreateLoadBalancer]
|
|
204
|
-
[ActionCommand.DeleteLoadBalancer]
|
|
205
|
-
[ActionCommand.AddTarget]
|
|
206
|
-
[ActionCommand.RemoveTarget]
|
|
207
|
-
[ActionCommand.AddService]
|
|
208
|
-
[ActionCommand.UpdateService]
|
|
209
|
-
[ActionCommand.DeleteService]
|
|
210
|
-
[ActionCommand.LoadBalancerAttachToNetwork]
|
|
211
|
-
[ActionCommand.LoadBalancerDetachFromNetwork]
|
|
212
|
-
[ActionCommand.ChangeAlgorithm]
|
|
213
|
-
[ActionCommand.ChangeType]
|
|
324
|
+
_a[types_js_1.ActionCommand.CreateLoadBalancer] = 300000,
|
|
325
|
+
_a[types_js_1.ActionCommand.DeleteLoadBalancer] = 180000,
|
|
326
|
+
_a[types_js_1.ActionCommand.AddTarget] = 60000,
|
|
327
|
+
_a[types_js_1.ActionCommand.RemoveTarget] = 60000,
|
|
328
|
+
_a[types_js_1.ActionCommand.AddService] = 60000,
|
|
329
|
+
_a[types_js_1.ActionCommand.UpdateService] = 60000,
|
|
330
|
+
_a[types_js_1.ActionCommand.DeleteService] = 60000,
|
|
331
|
+
_a[types_js_1.ActionCommand.LoadBalancerAttachToNetwork] = 60000,
|
|
332
|
+
_a[types_js_1.ActionCommand.LoadBalancerDetachFromNetwork] = 60000,
|
|
333
|
+
_a[types_js_1.ActionCommand.ChangeAlgorithm] = 60000,
|
|
334
|
+
_a[types_js_1.ActionCommand.ChangeType] = 60000,
|
|
214
335
|
// Certificate operations
|
|
215
|
-
[ActionCommand.IssueCertificate]
|
|
216
|
-
[ActionCommand.RetryCertificate]
|
|
336
|
+
_a[types_js_1.ActionCommand.IssueCertificate] = 600000, // Can take up to 10 minutes
|
|
337
|
+
_a[types_js_1.ActionCommand.RetryCertificate] = 600000,
|
|
217
338
|
// Firewall operations
|
|
218
|
-
[ActionCommand.SetFirewallRules]
|
|
219
|
-
[ActionCommand.ApplyFirewall]
|
|
220
|
-
[ActionCommand.RemoveFirewall]
|
|
339
|
+
_a[types_js_1.ActionCommand.SetFirewallRules] = 60000,
|
|
340
|
+
_a[types_js_1.ActionCommand.ApplyFirewall] = 120000,
|
|
341
|
+
_a[types_js_1.ActionCommand.RemoveFirewall] = 60000,
|
|
221
342
|
// Floating IP DNS
|
|
222
|
-
[ActionCommand.FloatingIpChangeDnsPtr]
|
|
343
|
+
_a[types_js_1.ActionCommand.FloatingIpChangeDnsPtr] = 30000,
|
|
223
344
|
// Backup operations
|
|
224
|
-
[ActionCommand.EnableBackup]
|
|
225
|
-
[ActionCommand.DisableBackup]
|
|
345
|
+
_a[types_js_1.ActionCommand.EnableBackup] = 60000,
|
|
346
|
+
_a[types_js_1.ActionCommand.DisableBackup] = 60000,
|
|
226
347
|
// Protection operations
|
|
227
|
-
[ActionCommand.ChangeProtection]
|
|
228
|
-
[ActionCommand.VolumeChangeProtection]
|
|
229
|
-
[ActionCommand.NetworkChangeProtection]
|
|
230
|
-
[ActionCommand.FloatingIpChangeProtection]
|
|
231
|
-
[ActionCommand.LoadBalancerChangeProtection]
|
|
232
|
-
[ActionCommand.FirewallChangeProtection]
|
|
233
|
-
[ActionCommand.ImageChangeProtection]
|
|
348
|
+
_a[types_js_1.ActionCommand.ChangeProtection] = 30000,
|
|
349
|
+
_a[types_js_1.ActionCommand.VolumeChangeProtection] = 30000,
|
|
350
|
+
_a[types_js_1.ActionCommand.NetworkChangeProtection] = 30000,
|
|
351
|
+
_a[types_js_1.ActionCommand.FloatingIpChangeProtection] = 30000,
|
|
352
|
+
_a[types_js_1.ActionCommand.LoadBalancerChangeProtection] = 30000,
|
|
353
|
+
_a[types_js_1.ActionCommand.FirewallChangeProtection] = 30000,
|
|
354
|
+
_a[types_js_1.ActionCommand.ImageChangeProtection] = 30000,
|
|
234
355
|
// Other operations
|
|
235
|
-
[ActionCommand.ChangeAliasIps]
|
|
236
|
-
|
|
356
|
+
_a[types_js_1.ActionCommand.ChangeAliasIps] = 60000,
|
|
357
|
+
_a);
|
|
237
358
|
/**
|
|
238
359
|
* Get default timeout for an action command
|
|
239
360
|
*/
|
|
240
|
-
|
|
241
|
-
return ACTION_TIMEOUTS[command] || 300000; // Default 5 minutes
|
|
361
|
+
function getActionTimeout(command) {
|
|
362
|
+
return exports.ACTION_TIMEOUTS[command] || 300000; // Default 5 minutes
|
|
242
363
|
}
|
|
243
364
|
// ============================================================================
|
|
244
365
|
// Enhanced Action Polling Service
|
|
@@ -246,14 +367,14 @@ export function getActionTimeout(command) {
|
|
|
246
367
|
/**
|
|
247
368
|
* Default polling options
|
|
248
369
|
*/
|
|
249
|
-
|
|
370
|
+
var DEFAULT_POLLING_OPTIONS = {
|
|
250
371
|
pollInterval: 2000,
|
|
251
372
|
maxRetries: 60,
|
|
252
373
|
timeout: 300000,
|
|
253
|
-
onProgress: ()
|
|
254
|
-
onComplete: ()
|
|
255
|
-
onError: ()
|
|
256
|
-
onRetry: ()
|
|
374
|
+
onProgress: function () { },
|
|
375
|
+
onComplete: function () { },
|
|
376
|
+
onError: function () { },
|
|
377
|
+
onRetry: function () { },
|
|
257
378
|
signal: undefined,
|
|
258
379
|
adaptive: false,
|
|
259
380
|
concurrency: 5,
|
|
@@ -286,76 +407,95 @@ const DEFAULT_POLLING_OPTIONS = {
|
|
|
286
407
|
* });
|
|
287
408
|
* ```
|
|
288
409
|
*/
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
return
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
410
|
+
function pollAction(client_1, actionId_1) {
|
|
411
|
+
return __awaiter(this, arguments, void 0, function (client, actionId, options) {
|
|
412
|
+
var opts, startTime, lastProgress, lastError, attempt, abortListener, elapsed, response, action, error, waitTime, error_1, delay;
|
|
413
|
+
var _a, _b, _c, _d;
|
|
414
|
+
if (options === void 0) { options = {}; }
|
|
415
|
+
return __generator(this, function (_e) {
|
|
416
|
+
switch (_e.label) {
|
|
417
|
+
case 0:
|
|
418
|
+
opts = __assign(__assign({}, DEFAULT_POLLING_OPTIONS), options);
|
|
419
|
+
startTime = Date.now();
|
|
420
|
+
lastProgress = 0;
|
|
421
|
+
lastError = null;
|
|
422
|
+
attempt = 0;
|
|
423
|
+
// Check if already aborted
|
|
424
|
+
if ((_a = opts.signal) === null || _a === void 0 ? void 0 : _a.aborted) {
|
|
425
|
+
throw new Error("Polling aborted before start");
|
|
426
|
+
}
|
|
427
|
+
abortListener = function () {
|
|
428
|
+
throw new Error("Polling aborted");
|
|
429
|
+
};
|
|
430
|
+
(_b = opts.signal) === null || _b === void 0 ? void 0 : _b.addEventListener("abort", abortListener);
|
|
431
|
+
_e.label = 1;
|
|
432
|
+
case 1:
|
|
433
|
+
_e.trys.push([1, , 11, 12]);
|
|
434
|
+
_e.label = 2;
|
|
435
|
+
case 2:
|
|
436
|
+
if (!(attempt < opts.maxRetries)) return [3 /*break*/, 10];
|
|
437
|
+
elapsed = Date.now() - startTime;
|
|
438
|
+
if (elapsed > opts.timeout) {
|
|
439
|
+
throw new errors_js_1.HetznerTimeoutError(actionId, opts.timeout, lastProgress);
|
|
440
|
+
}
|
|
441
|
+
_e.label = 3;
|
|
442
|
+
case 3:
|
|
443
|
+
_e.trys.push([3, 6, , 9]);
|
|
444
|
+
return [4 /*yield*/, client.request("/actions/".concat(actionId))];
|
|
445
|
+
case 4:
|
|
446
|
+
response = _e.sent();
|
|
447
|
+
action = response.action;
|
|
448
|
+
attempt++;
|
|
449
|
+
// Notify progress callback on any change
|
|
450
|
+
if (action.progress !== lastProgress) {
|
|
451
|
+
lastProgress = action.progress;
|
|
452
|
+
opts.onProgress(action);
|
|
453
|
+
}
|
|
454
|
+
// Check if action completed successfully
|
|
455
|
+
if (action.status === "success") {
|
|
456
|
+
opts.onComplete(action);
|
|
457
|
+
return [2 /*return*/, action];
|
|
458
|
+
}
|
|
459
|
+
// Check if action failed
|
|
460
|
+
if (action.status === "error") {
|
|
461
|
+
error = new errors_js_1.HetznerActionError(action.error, actionId);
|
|
462
|
+
opts.onError(error, action);
|
|
463
|
+
throw error;
|
|
464
|
+
}
|
|
465
|
+
waitTime = opts.pollInterval;
|
|
466
|
+
if (opts.adaptive) {
|
|
467
|
+
waitTime = getAdaptivePollInterval(action.progress);
|
|
468
|
+
}
|
|
469
|
+
return [4 /*yield*/, sleep(waitTime)];
|
|
470
|
+
case 5:
|
|
471
|
+
_e.sent();
|
|
472
|
+
return [3 /*break*/, 9];
|
|
473
|
+
case 6:
|
|
474
|
+
error_1 = _e.sent();
|
|
475
|
+
if (!(0, errors_js_1.isRetryableError)(error_1)) return [3 /*break*/, 8];
|
|
476
|
+
delay = (0, errors_js_1.calculateRetryDelay)(attempt);
|
|
342
477
|
opts.onRetry(attempt, delay);
|
|
343
|
-
if (opts.signal
|
|
478
|
+
if ((_c = opts.signal) === null || _c === void 0 ? void 0 : _c.aborted) {
|
|
344
479
|
throw new Error("Polling aborted during retry");
|
|
345
480
|
}
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
481
|
+
return [4 /*yield*/, sleep(delay)];
|
|
482
|
+
case 7:
|
|
483
|
+
_e.sent();
|
|
484
|
+
return [3 /*break*/, 2];
|
|
485
|
+
case 8:
|
|
349
486
|
// Non-retryable error - throw immediately
|
|
350
|
-
throw
|
|
487
|
+
throw error_1;
|
|
488
|
+
case 9: return [3 /*break*/, 2];
|
|
489
|
+
case 10:
|
|
490
|
+
// Max retries exceeded
|
|
491
|
+
throw new errors_js_1.HetznerTimeoutError(actionId, opts.timeout, lastProgress);
|
|
492
|
+
case 11:
|
|
493
|
+
(_d = opts.signal) === null || _d === void 0 ? void 0 : _d.removeEventListener("abort", abortListener);
|
|
494
|
+
return [7 /*endfinally*/];
|
|
495
|
+
case 12: return [2 /*return*/];
|
|
351
496
|
}
|
|
352
|
-
}
|
|
353
|
-
|
|
354
|
-
throw new HetznerTimeoutError(actionId, opts.timeout, lastProgress);
|
|
355
|
-
}
|
|
356
|
-
finally {
|
|
357
|
-
opts.signal?.removeEventListener("abort", abortListener);
|
|
358
|
-
}
|
|
497
|
+
});
|
|
498
|
+
});
|
|
359
499
|
}
|
|
360
500
|
/**
|
|
361
501
|
* Poll multiple actions concurrently
|
|
@@ -377,32 +517,70 @@ export async function pollAction(client, actionId, options = {}) {
|
|
|
377
517
|
* });
|
|
378
518
|
* ```
|
|
379
519
|
*/
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
520
|
+
function pollActions(client_1, actionIds_1) {
|
|
521
|
+
return __awaiter(this, arguments, void 0, function (client, actionIds, options) {
|
|
522
|
+
var concurrency, promises, results, currentIndex, processBatch;
|
|
523
|
+
var _this = this;
|
|
524
|
+
var _a;
|
|
525
|
+
if (options === void 0) { options = {}; }
|
|
526
|
+
return __generator(this, function (_b) {
|
|
527
|
+
switch (_b.label) {
|
|
528
|
+
case 0:
|
|
529
|
+
concurrency = (_a = options.concurrency) !== null && _a !== void 0 ? _a : DEFAULT_POLLING_OPTIONS.concurrency;
|
|
530
|
+
// If concurrency is high enough, poll all at once
|
|
531
|
+
if (concurrency >= actionIds.length) {
|
|
532
|
+
promises = actionIds.map(function (id) {
|
|
533
|
+
return pollAction(client, id, options);
|
|
534
|
+
});
|
|
535
|
+
return [2 /*return*/, Promise.all(promises)];
|
|
536
|
+
}
|
|
537
|
+
results = new Array(actionIds.length);
|
|
538
|
+
currentIndex = 0;
|
|
539
|
+
processBatch = function () { return __awaiter(_this, void 0, void 0, function () {
|
|
540
|
+
var _loop_1;
|
|
541
|
+
return __generator(this, function (_a) {
|
|
542
|
+
switch (_a.label) {
|
|
543
|
+
case 0:
|
|
544
|
+
_loop_1 = function () {
|
|
545
|
+
var batchStart, batchEnd, batchIds, batchResults;
|
|
546
|
+
return __generator(this, function (_b) {
|
|
547
|
+
switch (_b.label) {
|
|
548
|
+
case 0:
|
|
549
|
+
batchStart = currentIndex;
|
|
550
|
+
batchEnd = Math.min(currentIndex + concurrency, actionIds.length);
|
|
551
|
+
batchIds = actionIds.slice(batchStart, batchEnd);
|
|
552
|
+
currentIndex = batchEnd;
|
|
553
|
+
return [4 /*yield*/, Promise.all(batchIds.map(function (id, i) { return pollAction(client, id, options); }))];
|
|
554
|
+
case 1:
|
|
555
|
+
batchResults = _b.sent();
|
|
556
|
+
// Store results in correct positions
|
|
557
|
+
batchResults.forEach(function (result, i) {
|
|
558
|
+
results[batchStart + i] = result;
|
|
559
|
+
});
|
|
560
|
+
return [2 /*return*/];
|
|
561
|
+
}
|
|
562
|
+
});
|
|
563
|
+
};
|
|
564
|
+
_a.label = 1;
|
|
565
|
+
case 1:
|
|
566
|
+
if (!(currentIndex < actionIds.length)) return [3 /*break*/, 3];
|
|
567
|
+
return [5 /*yield**/, _loop_1()];
|
|
568
|
+
case 2:
|
|
569
|
+
_a.sent();
|
|
570
|
+
return [3 /*break*/, 1];
|
|
571
|
+
case 3: return [2 /*return*/];
|
|
572
|
+
}
|
|
573
|
+
});
|
|
574
|
+
}); };
|
|
575
|
+
// Process batches sequentially but actions within each batch concurrently
|
|
576
|
+
return [4 /*yield*/, processBatch()];
|
|
577
|
+
case 1:
|
|
578
|
+
// Process batches sequentially but actions within each batch concurrently
|
|
579
|
+
_b.sent();
|
|
580
|
+
return [2 /*return*/, results];
|
|
581
|
+
}
|
|
582
|
+
});
|
|
583
|
+
});
|
|
406
584
|
}
|
|
407
585
|
/**
|
|
408
586
|
* Poll multiple actions with detailed result tracking
|
|
@@ -430,50 +608,62 @@ export async function pollActions(client, actionIds, options = {}) {
|
|
|
430
608
|
* }
|
|
431
609
|
* ```
|
|
432
610
|
*/
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
611
|
+
function pollActionsDetailed(client_1, actionIds_1) {
|
|
612
|
+
return __awaiter(this, arguments, void 0, function (client, actionIds, options) {
|
|
613
|
+
var startTime, results, successful, failed, wrappedOptions, error_2;
|
|
614
|
+
if (options === void 0) { options = {}; }
|
|
615
|
+
return __generator(this, function (_a) {
|
|
616
|
+
switch (_a.label) {
|
|
617
|
+
case 0:
|
|
618
|
+
startTime = Date.now();
|
|
619
|
+
results = new Map();
|
|
620
|
+
successful = 0;
|
|
621
|
+
failed = 0;
|
|
622
|
+
wrappedOptions = __assign(__assign({}, options), { onComplete: function (action) {
|
|
623
|
+
var _a;
|
|
624
|
+
results.set(action.id, {
|
|
625
|
+
success: true,
|
|
626
|
+
action: action,
|
|
627
|
+
attempts: 0,
|
|
628
|
+
elapsed: Date.now() - startTime,
|
|
629
|
+
});
|
|
630
|
+
successful++;
|
|
631
|
+
(_a = options.onComplete) === null || _a === void 0 ? void 0 : _a.call(options, action);
|
|
632
|
+
}, onError: function (error, action) {
|
|
633
|
+
var _a;
|
|
634
|
+
results.set(action.id, {
|
|
635
|
+
success: false,
|
|
636
|
+
action: action,
|
|
637
|
+
error: error,
|
|
638
|
+
attempts: 0,
|
|
639
|
+
elapsed: Date.now() - startTime,
|
|
640
|
+
});
|
|
641
|
+
failed++;
|
|
642
|
+
(_a = options.onError) === null || _a === void 0 ? void 0 : _a.call(options, error, action);
|
|
643
|
+
} });
|
|
644
|
+
_a.label = 1;
|
|
645
|
+
case 1:
|
|
646
|
+
_a.trys.push([1, 3, , 4]);
|
|
647
|
+
// Poll all actions
|
|
648
|
+
return [4 /*yield*/, pollActions(client, actionIds, wrappedOptions)];
|
|
649
|
+
case 2:
|
|
650
|
+
// Poll all actions
|
|
651
|
+
_a.sent();
|
|
652
|
+
return [3 /*break*/, 4];
|
|
653
|
+
case 3:
|
|
654
|
+
error_2 = _a.sent();
|
|
655
|
+
// Some actions may have failed, but we still return results
|
|
656
|
+
console.warn("Some actions failed during batch polling:", error_2);
|
|
657
|
+
return [3 /*break*/, 4];
|
|
658
|
+
case 4: return [2 /*return*/, {
|
|
659
|
+
results: results,
|
|
660
|
+
successful: successful,
|
|
661
|
+
failed: failed,
|
|
662
|
+
elapsed: Date.now() - startTime,
|
|
663
|
+
}];
|
|
664
|
+
}
|
|
665
|
+
});
|
|
666
|
+
});
|
|
477
667
|
}
|
|
478
668
|
// ============================================================================
|
|
479
669
|
// Backward Compatible Polling Functions
|
|
@@ -483,75 +673,122 @@ export async function pollActionsDetailed(client, actionIds, options = {}) {
|
|
|
483
673
|
*
|
|
484
674
|
* @deprecated Use pollAction() instead for new code
|
|
485
675
|
*/
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
676
|
+
function waitForAction(client_1, actionId_1) {
|
|
677
|
+
return __awaiter(this, arguments, void 0, function (client, actionId, options) {
|
|
678
|
+
var opts, startTime, lastProgress, lastError, attempt, action, error_3, delay;
|
|
679
|
+
if (options === void 0) { options = {}; }
|
|
680
|
+
return __generator(this, function (_a) {
|
|
681
|
+
switch (_a.label) {
|
|
682
|
+
case 0:
|
|
683
|
+
opts = __assign(__assign({}, DEFAULT_POLLING_OPTIONS), options);
|
|
684
|
+
startTime = Date.now();
|
|
685
|
+
lastProgress = 0;
|
|
686
|
+
lastError = null;
|
|
687
|
+
attempt = 0;
|
|
688
|
+
_a.label = 1;
|
|
689
|
+
case 1:
|
|
690
|
+
if (!(attempt < opts.maxRetries)) return [3 /*break*/, 9];
|
|
691
|
+
// Check timeout
|
|
692
|
+
if (Date.now() - startTime > opts.timeout) {
|
|
693
|
+
throw new errors_js_1.HetznerTimeoutError(actionId, opts.timeout, lastProgress);
|
|
694
|
+
}
|
|
695
|
+
_a.label = 2;
|
|
696
|
+
case 2:
|
|
697
|
+
_a.trys.push([2, 5, , 8]);
|
|
698
|
+
return [4 /*yield*/, client.request("/actions/".concat(actionId))];
|
|
699
|
+
case 3:
|
|
700
|
+
action = _a.sent();
|
|
701
|
+
// Notify progress callback
|
|
702
|
+
if (action.action.progress !== lastProgress) {
|
|
703
|
+
lastProgress = action.action.progress;
|
|
704
|
+
opts.onProgress(action.action);
|
|
705
|
+
}
|
|
706
|
+
// Check if action is complete
|
|
707
|
+
if (action.action.status === "success") {
|
|
708
|
+
return [2 /*return*/, action.action];
|
|
709
|
+
}
|
|
710
|
+
if (action.action.status === "error") {
|
|
711
|
+
throw new errors_js_1.HetznerActionError(action.action.error, actionId);
|
|
712
|
+
}
|
|
713
|
+
// Still running - wait before next poll
|
|
714
|
+
return [4 /*yield*/, sleep(opts.pollInterval)];
|
|
715
|
+
case 4:
|
|
716
|
+
// Still running - wait before next poll
|
|
717
|
+
_a.sent();
|
|
718
|
+
return [3 /*break*/, 8];
|
|
719
|
+
case 5:
|
|
720
|
+
error_3 = _a.sent();
|
|
721
|
+
if (!(0, errors_js_1.isRetryableError)(error_3)) return [3 /*break*/, 7];
|
|
722
|
+
delay = (0, errors_js_1.calculateRetryDelay)(attempt);
|
|
723
|
+
console.warn("Retrying action ".concat(actionId, " after ").concat(delay, "ms (attempt ").concat(attempt + 1, "/").concat(opts.maxRetries, ")"));
|
|
724
|
+
return [4 /*yield*/, sleep(delay)];
|
|
725
|
+
case 6:
|
|
726
|
+
_a.sent();
|
|
727
|
+
return [3 /*break*/, 8];
|
|
728
|
+
case 7:
|
|
729
|
+
// Non-retryable error - throw immediately
|
|
730
|
+
throw error_3;
|
|
731
|
+
case 8:
|
|
732
|
+
attempt++;
|
|
733
|
+
return [3 /*break*/, 1];
|
|
734
|
+
case 9:
|
|
735
|
+
// Max retries exceeded
|
|
736
|
+
throw new errors_js_1.HetznerTimeoutError(actionId, opts.timeout, lastProgress);
|
|
520
737
|
}
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
}
|
|
524
|
-
}
|
|
525
|
-
// Max retries exceeded
|
|
526
|
-
throw new HetznerTimeoutError(actionId, opts.timeout, lastProgress);
|
|
738
|
+
});
|
|
739
|
+
});
|
|
527
740
|
}
|
|
528
741
|
/**
|
|
529
742
|
* Poll for multiple actions concurrently (backward compatible)
|
|
530
743
|
*
|
|
531
744
|
* @deprecated Use pollActions() instead for new code
|
|
532
745
|
*/
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
746
|
+
function waitForMultipleActions(client_1, actionIds_1) {
|
|
747
|
+
return __awaiter(this, arguments, void 0, function (client, actionIds, options) {
|
|
748
|
+
var promises;
|
|
749
|
+
if (options === void 0) { options = {}; }
|
|
750
|
+
return __generator(this, function (_a) {
|
|
751
|
+
promises = actionIds.map(function (id) { return waitForAction(client, id, options); });
|
|
752
|
+
return [2 /*return*/, Promise.all(promises)];
|
|
753
|
+
});
|
|
754
|
+
});
|
|
536
755
|
}
|
|
537
756
|
/**
|
|
538
757
|
* Poll for multiple actions with concurrency limit (backward compatible)
|
|
539
758
|
*
|
|
540
759
|
* @deprecated Use pollActions() with concurrency option instead
|
|
541
760
|
*/
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
761
|
+
function waitForMultipleActionsWithLimit(client_1, actionIds_1) {
|
|
762
|
+
return __awaiter(this, arguments, void 0, function (client, actionIds, concurrency, options) {
|
|
763
|
+
var results, chunks, i, _i, chunks_1, chunk, chunkResults;
|
|
764
|
+
if (concurrency === void 0) { concurrency = 5; }
|
|
765
|
+
if (options === void 0) { options = {}; }
|
|
766
|
+
return __generator(this, function (_a) {
|
|
767
|
+
switch (_a.label) {
|
|
768
|
+
case 0:
|
|
769
|
+
results = [];
|
|
770
|
+
chunks = [];
|
|
771
|
+
// Split action IDs into chunks
|
|
772
|
+
for (i = 0; i < actionIds.length; i += concurrency) {
|
|
773
|
+
chunks.push(actionIds.slice(i, i + concurrency));
|
|
774
|
+
}
|
|
775
|
+
_i = 0, chunks_1 = chunks;
|
|
776
|
+
_a.label = 1;
|
|
777
|
+
case 1:
|
|
778
|
+
if (!(_i < chunks_1.length)) return [3 /*break*/, 4];
|
|
779
|
+
chunk = chunks_1[_i];
|
|
780
|
+
return [4 /*yield*/, waitForMultipleActions(client, chunk, options)];
|
|
781
|
+
case 2:
|
|
782
|
+
chunkResults = _a.sent();
|
|
783
|
+
results.push.apply(results, chunkResults);
|
|
784
|
+
_a.label = 3;
|
|
785
|
+
case 3:
|
|
786
|
+
_i++;
|
|
787
|
+
return [3 /*break*/, 1];
|
|
788
|
+
case 4: return [2 /*return*/, results];
|
|
789
|
+
}
|
|
790
|
+
});
|
|
791
|
+
});
|
|
555
792
|
}
|
|
556
793
|
/**
|
|
557
794
|
* Batch check multiple actions in a single API call
|
|
@@ -562,19 +799,35 @@ export async function waitForMultipleActionsWithLimit(client, actionIds, concurr
|
|
|
562
799
|
* @param actionIds - Array of action IDs to check
|
|
563
800
|
* @returns Map of action ID to action
|
|
564
801
|
*/
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
802
|
+
function batchCheckActions(client, actionIds) {
|
|
803
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
804
|
+
var MAX_BATCH_SIZE, results, i, batch, idParams, response, _i, _a, action;
|
|
805
|
+
return __generator(this, function (_b) {
|
|
806
|
+
switch (_b.label) {
|
|
807
|
+
case 0:
|
|
808
|
+
MAX_BATCH_SIZE = 50;
|
|
809
|
+
results = new Map();
|
|
810
|
+
i = 0;
|
|
811
|
+
_b.label = 1;
|
|
812
|
+
case 1:
|
|
813
|
+
if (!(i < actionIds.length)) return [3 /*break*/, 4];
|
|
814
|
+
batch = actionIds.slice(i, i + MAX_BATCH_SIZE);
|
|
815
|
+
idParams = batch.map(function (id) { return "id=".concat(id); }).join("&");
|
|
816
|
+
return [4 /*yield*/, client.request("/actions?".concat(idParams))];
|
|
817
|
+
case 2:
|
|
818
|
+
response = _b.sent();
|
|
819
|
+
for (_i = 0, _a = response.actions; _i < _a.length; _i++) {
|
|
820
|
+
action = _a[_i];
|
|
821
|
+
results.set(action.id, action);
|
|
822
|
+
}
|
|
823
|
+
_b.label = 3;
|
|
824
|
+
case 3:
|
|
825
|
+
i += MAX_BATCH_SIZE;
|
|
826
|
+
return [3 /*break*/, 1];
|
|
827
|
+
case 4: return [2 /*return*/, results];
|
|
828
|
+
}
|
|
829
|
+
});
|
|
830
|
+
});
|
|
578
831
|
}
|
|
579
832
|
// ============================================================================
|
|
580
833
|
// Action Status Utilities
|
|
@@ -582,90 +835,91 @@ export async function batchCheckActions(client, actionIds) {
|
|
|
582
835
|
/**
|
|
583
836
|
* Check if an action is running
|
|
584
837
|
*/
|
|
585
|
-
|
|
838
|
+
function isActionRunning(action) {
|
|
586
839
|
return action.status === "running";
|
|
587
840
|
}
|
|
588
841
|
/**
|
|
589
842
|
* Check if an action completed successfully
|
|
590
843
|
*/
|
|
591
|
-
|
|
844
|
+
function isActionSuccess(action) {
|
|
592
845
|
return action.status === "success";
|
|
593
846
|
}
|
|
594
847
|
/**
|
|
595
848
|
* Check if an action failed
|
|
596
849
|
*/
|
|
597
|
-
|
|
850
|
+
function isActionError(action) {
|
|
598
851
|
return action.status === "error";
|
|
599
852
|
}
|
|
600
853
|
/**
|
|
601
854
|
* Format action progress for display
|
|
602
855
|
*/
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
return
|
|
856
|
+
function formatActionProgress(action) {
|
|
857
|
+
var command = action.command.replace(/_/g, " ");
|
|
858
|
+
var status = action.status.toUpperCase();
|
|
859
|
+
return "".concat(status, ": ").concat(command, " (").concat(action.progress, "%)");
|
|
607
860
|
}
|
|
608
861
|
/**
|
|
609
862
|
* Get human-readable action description
|
|
610
863
|
*/
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
[ActionCommand.
|
|
615
|
-
[ActionCommand.
|
|
616
|
-
[ActionCommand.
|
|
617
|
-
[ActionCommand.
|
|
618
|
-
[ActionCommand.
|
|
619
|
-
[ActionCommand.
|
|
620
|
-
[ActionCommand.
|
|
621
|
-
[ActionCommand.
|
|
622
|
-
[ActionCommand.
|
|
623
|
-
[ActionCommand.
|
|
624
|
-
[ActionCommand.
|
|
625
|
-
[ActionCommand.
|
|
626
|
-
[ActionCommand.
|
|
627
|
-
[ActionCommand.
|
|
628
|
-
[ActionCommand.
|
|
629
|
-
[ActionCommand.
|
|
630
|
-
[ActionCommand.
|
|
631
|
-
[ActionCommand.
|
|
632
|
-
[ActionCommand.
|
|
633
|
-
[ActionCommand.
|
|
634
|
-
[ActionCommand.
|
|
635
|
-
[ActionCommand.
|
|
636
|
-
[ActionCommand.
|
|
637
|
-
[ActionCommand.
|
|
638
|
-
[ActionCommand.
|
|
639
|
-
[ActionCommand.
|
|
640
|
-
[ActionCommand.
|
|
641
|
-
[ActionCommand.
|
|
642
|
-
[ActionCommand.
|
|
643
|
-
[ActionCommand.
|
|
644
|
-
[ActionCommand.
|
|
645
|
-
[ActionCommand.
|
|
646
|
-
[ActionCommand.
|
|
647
|
-
[ActionCommand.
|
|
648
|
-
[ActionCommand.
|
|
649
|
-
[ActionCommand.
|
|
650
|
-
[ActionCommand.
|
|
651
|
-
[ActionCommand.
|
|
652
|
-
[ActionCommand.
|
|
653
|
-
[ActionCommand.
|
|
654
|
-
[ActionCommand.
|
|
655
|
-
[ActionCommand.
|
|
656
|
-
[ActionCommand.
|
|
657
|
-
[ActionCommand.
|
|
658
|
-
[ActionCommand.
|
|
659
|
-
[ActionCommand.
|
|
660
|
-
[ActionCommand.
|
|
661
|
-
[ActionCommand.
|
|
662
|
-
[ActionCommand.
|
|
663
|
-
[ActionCommand.
|
|
664
|
-
[ActionCommand.
|
|
665
|
-
[ActionCommand.
|
|
666
|
-
[ActionCommand.
|
|
667
|
-
[ActionCommand.
|
|
668
|
-
|
|
864
|
+
function getActionDescription(command) {
|
|
865
|
+
var _a;
|
|
866
|
+
var descriptions = (_a = {},
|
|
867
|
+
_a[types_js_1.ActionCommand.CreateServer] = "Creating server",
|
|
868
|
+
_a[types_js_1.ActionCommand.DeleteServer] = "Deleting server",
|
|
869
|
+
_a[types_js_1.ActionCommand.StartServer] = "Starting server",
|
|
870
|
+
_a[types_js_1.ActionCommand.StopServer] = "Stopping server",
|
|
871
|
+
_a[types_js_1.ActionCommand.RebootServer] = "Rebooting server",
|
|
872
|
+
_a[types_js_1.ActionCommand.ResetServer] = "Resetting server",
|
|
873
|
+
_a[types_js_1.ActionCommand.ShutdownServer] = "Shutting down server",
|
|
874
|
+
_a[types_js_1.ActionCommand.Poweroff] = "Cutting power to server",
|
|
875
|
+
_a[types_js_1.ActionCommand.ChangeServerType] = "Changing server type",
|
|
876
|
+
_a[types_js_1.ActionCommand.RebuildServer] = "Rebuilding server",
|
|
877
|
+
_a[types_js_1.ActionCommand.EnableBackup] = "Enabling backups",
|
|
878
|
+
_a[types_js_1.ActionCommand.DisableBackup] = "Disabling backups",
|
|
879
|
+
_a[types_js_1.ActionCommand.CreateImage] = "Creating image",
|
|
880
|
+
_a[types_js_1.ActionCommand.ChangeDnsPtr] = "Changing reverse DNS",
|
|
881
|
+
_a[types_js_1.ActionCommand.AttachToNetwork] = "Attaching to network",
|
|
882
|
+
_a[types_js_1.ActionCommand.DetachFromNetwork] = "Detaching from network",
|
|
883
|
+
_a[types_js_1.ActionCommand.ChangeAliasIps] = "Changing alias IPs",
|
|
884
|
+
_a[types_js_1.ActionCommand.EnableRescue] = "Enabling rescue mode",
|
|
885
|
+
_a[types_js_1.ActionCommand.DisableRescue] = "Disabling rescue mode",
|
|
886
|
+
_a[types_js_1.ActionCommand.ChangeProtection] = "Changing protection",
|
|
887
|
+
_a[types_js_1.ActionCommand.CreateVolume] = "Creating volume",
|
|
888
|
+
_a[types_js_1.ActionCommand.DeleteVolume] = "Deleting volume",
|
|
889
|
+
_a[types_js_1.ActionCommand.AttachVolume] = "Attaching volume",
|
|
890
|
+
_a[types_js_1.ActionCommand.DetachVolume] = "Detaching volume",
|
|
891
|
+
_a[types_js_1.ActionCommand.ResizeVolume] = "Resizing volume",
|
|
892
|
+
_a[types_js_1.ActionCommand.VolumeChangeProtection] = "Changing volume protection",
|
|
893
|
+
_a[types_js_1.ActionCommand.AddSubnet] = "Adding subnet",
|
|
894
|
+
_a[types_js_1.ActionCommand.DeleteSubnet] = "Deleting subnet",
|
|
895
|
+
_a[types_js_1.ActionCommand.AddRoute] = "Adding route",
|
|
896
|
+
_a[types_js_1.ActionCommand.DeleteRoute] = "Deleting route",
|
|
897
|
+
_a[types_js_1.ActionCommand.ChangeIpRange] = "Changing IP range",
|
|
898
|
+
_a[types_js_1.ActionCommand.NetworkChangeProtection] = "Changing network protection",
|
|
899
|
+
_a[types_js_1.ActionCommand.AssignFloatingIp] = "Assigning floating IP",
|
|
900
|
+
_a[types_js_1.ActionCommand.UnassignFloatingIp] = "Unassigning floating IP",
|
|
901
|
+
_a[types_js_1.ActionCommand.FloatingIpChangeDnsPtr] = "Changing floating IP DNS",
|
|
902
|
+
_a[types_js_1.ActionCommand.FloatingIpChangeProtection] = "Changing floating IP protection",
|
|
903
|
+
_a[types_js_1.ActionCommand.CreateLoadBalancer] = "Creating load balancer",
|
|
904
|
+
_a[types_js_1.ActionCommand.DeleteLoadBalancer] = "Deleting load balancer",
|
|
905
|
+
_a[types_js_1.ActionCommand.AddTarget] = "Adding target to load balancer",
|
|
906
|
+
_a[types_js_1.ActionCommand.RemoveTarget] = "Removing target from load balancer",
|
|
907
|
+
_a[types_js_1.ActionCommand.AddService] = "Adding service to load balancer",
|
|
908
|
+
_a[types_js_1.ActionCommand.UpdateService] = "Updating load balancer service",
|
|
909
|
+
_a[types_js_1.ActionCommand.DeleteService] = "Deleting load balancer service",
|
|
910
|
+
_a[types_js_1.ActionCommand.LoadBalancerAttachToNetwork] = "Attaching load balancer to network",
|
|
911
|
+
_a[types_js_1.ActionCommand.LoadBalancerDetachFromNetwork] = "Detaching load balancer from network",
|
|
912
|
+
_a[types_js_1.ActionCommand.ChangeAlgorithm] = "Changing load balancer algorithm",
|
|
913
|
+
_a[types_js_1.ActionCommand.ChangeType] = "Changing load balancer type",
|
|
914
|
+
_a[types_js_1.ActionCommand.LoadBalancerChangeProtection] = "Changing load balancer protection",
|
|
915
|
+
_a[types_js_1.ActionCommand.IssueCertificate] = "Issuing certificate",
|
|
916
|
+
_a[types_js_1.ActionCommand.RetryCertificate] = "Retrying certificate",
|
|
917
|
+
_a[types_js_1.ActionCommand.SetFirewallRules] = "Setting firewall rules",
|
|
918
|
+
_a[types_js_1.ActionCommand.ApplyFirewall] = "Applying firewall",
|
|
919
|
+
_a[types_js_1.ActionCommand.RemoveFirewall] = "Removing firewall",
|
|
920
|
+
_a[types_js_1.ActionCommand.FirewallChangeProtection] = "Changing firewall protection",
|
|
921
|
+
_a[types_js_1.ActionCommand.ImageChangeProtection] = "Changing image protection",
|
|
922
|
+
_a);
|
|
669
923
|
return descriptions[command] || command.replace(/_/g, " ");
|
|
670
924
|
}
|
|
671
925
|
// ============================================================================
|
|
@@ -674,30 +928,31 @@ export function getActionDescription(command) {
|
|
|
674
928
|
/**
|
|
675
929
|
* Get adaptive polling interval based on operation type
|
|
676
930
|
*/
|
|
677
|
-
|
|
678
|
-
|
|
931
|
+
function getPollInterval(command) {
|
|
932
|
+
var _a;
|
|
933
|
+
var intervals = (_a = {},
|
|
679
934
|
// Quick operations - poll frequently
|
|
680
|
-
[ActionCommand.StartServer]
|
|
681
|
-
[ActionCommand.StopServer]
|
|
682
|
-
[ActionCommand.RebootServer]
|
|
683
|
-
[ActionCommand.Poweroff]
|
|
684
|
-
[ActionCommand.ShutdownServer]
|
|
935
|
+
_a[types_js_1.ActionCommand.StartServer] = 5000,
|
|
936
|
+
_a[types_js_1.ActionCommand.StopServer] = 5000,
|
|
937
|
+
_a[types_js_1.ActionCommand.RebootServer] = 10000,
|
|
938
|
+
_a[types_js_1.ActionCommand.Poweroff] = 5000,
|
|
939
|
+
_a[types_js_1.ActionCommand.ShutdownServer] = 5000,
|
|
685
940
|
// Medium operations
|
|
686
|
-
[ActionCommand.CreateServer]
|
|
687
|
-
[ActionCommand.CreateVolume]
|
|
688
|
-
[ActionCommand.AttachVolume]
|
|
689
|
-
[ActionCommand.DetachVolume]
|
|
941
|
+
_a[types_js_1.ActionCommand.CreateServer] = 15000,
|
|
942
|
+
_a[types_js_1.ActionCommand.CreateVolume] = 10000,
|
|
943
|
+
_a[types_js_1.ActionCommand.AttachVolume] = 8000,
|
|
944
|
+
_a[types_js_1.ActionCommand.DetachVolume] = 5000,
|
|
690
945
|
// Long operations - poll less frequently
|
|
691
|
-
[ActionCommand.RebuildServer]
|
|
692
|
-
[ActionCommand.CreateImage]
|
|
693
|
-
[ActionCommand.IssueCertificate]
|
|
694
|
-
|
|
946
|
+
_a[types_js_1.ActionCommand.RebuildServer] = 30000,
|
|
947
|
+
_a[types_js_1.ActionCommand.CreateImage] = 60000,
|
|
948
|
+
_a[types_js_1.ActionCommand.IssueCertificate] = 30000,
|
|
949
|
+
_a);
|
|
695
950
|
return intervals[command] || 10000; // Default 10 seconds
|
|
696
951
|
}
|
|
697
952
|
/**
|
|
698
953
|
* Get adaptive polling interval based on action progress
|
|
699
954
|
*/
|
|
700
|
-
|
|
955
|
+
function getAdaptivePollInterval(progress) {
|
|
701
956
|
if (progress < 10)
|
|
702
957
|
return 2000; // Quick progress at start
|
|
703
958
|
if (progress < 50)
|
|
@@ -711,28 +966,43 @@ export function getAdaptivePollInterval(progress) {
|
|
|
711
966
|
*
|
|
712
967
|
* @deprecated Use pollAction() with adaptive: true option instead
|
|
713
968
|
*/
|
|
714
|
-
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
969
|
+
function waitForActionAdaptive(client_1, actionId_1, command_1) {
|
|
970
|
+
return __awaiter(this, arguments, void 0, function (client, actionId, command, options) {
|
|
971
|
+
var startTime, timeout, lastProgress, action, interval;
|
|
972
|
+
var _a, _b;
|
|
973
|
+
if (options === void 0) { options = {}; }
|
|
974
|
+
return __generator(this, function (_c) {
|
|
975
|
+
switch (_c.label) {
|
|
976
|
+
case 0:
|
|
977
|
+
startTime = Date.now();
|
|
978
|
+
timeout = (_a = options.timeout) !== null && _a !== void 0 ? _a : getActionTimeout(command);
|
|
979
|
+
lastProgress = -1;
|
|
980
|
+
_c.label = 1;
|
|
981
|
+
case 1:
|
|
982
|
+
if (!(Date.now() - startTime < timeout)) return [3 /*break*/, 4];
|
|
983
|
+
return [4 /*yield*/, client.request("/actions/".concat(actionId))];
|
|
984
|
+
case 2:
|
|
985
|
+
action = _c.sent();
|
|
986
|
+
// Notify progress callback
|
|
987
|
+
if (action.action.progress !== lastProgress) {
|
|
988
|
+
lastProgress = action.action.progress;
|
|
989
|
+
(_b = options.onProgress) === null || _b === void 0 ? void 0 : _b.call(options, action.action);
|
|
990
|
+
}
|
|
991
|
+
if (action.action.status === "success") {
|
|
992
|
+
return [2 /*return*/, action.action];
|
|
993
|
+
}
|
|
994
|
+
if (action.action.status === "error") {
|
|
995
|
+
throw new errors_js_1.HetznerActionError(action.action.error, actionId);
|
|
996
|
+
}
|
|
997
|
+
interval = getAdaptivePollInterval(action.action.progress);
|
|
998
|
+
return [4 /*yield*/, sleep(interval)];
|
|
999
|
+
case 3:
|
|
1000
|
+
_c.sent();
|
|
1001
|
+
return [3 /*break*/, 1];
|
|
1002
|
+
case 4: throw new errors_js_1.HetznerTimeoutError(actionId, timeout, lastProgress);
|
|
1003
|
+
}
|
|
1004
|
+
});
|
|
1005
|
+
});
|
|
736
1006
|
}
|
|
737
1007
|
// ============================================================================
|
|
738
1008
|
// Rate Limit Handling
|
|
@@ -740,10 +1010,10 @@ export async function waitForActionAdaptive(client, actionId, command, options =
|
|
|
740
1010
|
/**
|
|
741
1011
|
* Parse rate limit headers from response
|
|
742
1012
|
*/
|
|
743
|
-
|
|
744
|
-
|
|
745
|
-
|
|
746
|
-
|
|
1013
|
+
function parseRateLimitHeaders(headers) {
|
|
1014
|
+
var limit = headers.get("RateLimit-Limit");
|
|
1015
|
+
var remaining = headers.get("RateLimit-Remaining");
|
|
1016
|
+
var reset = headers.get("RateLimit-Reset");
|
|
747
1017
|
if (!limit || !remaining || !reset) {
|
|
748
1018
|
return null;
|
|
749
1019
|
}
|
|
@@ -756,31 +1026,43 @@ export function parseRateLimitHeaders(headers) {
|
|
|
756
1026
|
/**
|
|
757
1027
|
* Check if rate limit is low (should warn user)
|
|
758
1028
|
*/
|
|
759
|
-
|
|
1029
|
+
function isRateLimitLow(info, threshold) {
|
|
1030
|
+
if (threshold === void 0) { threshold = 100; }
|
|
760
1031
|
return info.remaining < threshold;
|
|
761
1032
|
}
|
|
762
1033
|
/**
|
|
763
1034
|
* Get human-readable rate limit status
|
|
764
1035
|
*/
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
768
|
-
|
|
769
|
-
|
|
770
|
-
return
|
|
1036
|
+
function formatRateLimitStatus(info) {
|
|
1037
|
+
var resetDate = new Date(info.reset * 1000);
|
|
1038
|
+
var remaining = info.remaining;
|
|
1039
|
+
var limit = info.limit;
|
|
1040
|
+
var percentage = ((remaining / limit) * 100).toFixed(1);
|
|
1041
|
+
return "".concat(remaining, "/").concat(limit, " (").concat(percentage, "%) - resets at ").concat(resetDate.toISOString());
|
|
771
1042
|
}
|
|
772
1043
|
/**
|
|
773
1044
|
* Wait for rate limit to reset
|
|
774
1045
|
*/
|
|
775
|
-
|
|
776
|
-
|
|
777
|
-
|
|
778
|
-
|
|
779
|
-
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
1046
|
+
function waitForRateLimitReset(info) {
|
|
1047
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
1048
|
+
var resetTime, now, waitTime, waitSeconds;
|
|
1049
|
+
return __generator(this, function (_a) {
|
|
1050
|
+
switch (_a.label) {
|
|
1051
|
+
case 0:
|
|
1052
|
+
resetTime = info.reset * 1000;
|
|
1053
|
+
now = Date.now();
|
|
1054
|
+
waitTime = Math.max(0, resetTime - now);
|
|
1055
|
+
if (!(waitTime > 0)) return [3 /*break*/, 2];
|
|
1056
|
+
waitSeconds = Math.ceil(waitTime / 1000);
|
|
1057
|
+
console.log("Rate limit exhausted. Waiting ".concat(waitSeconds, "s for reset..."));
|
|
1058
|
+
return [4 /*yield*/, sleep(waitTime)];
|
|
1059
|
+
case 1:
|
|
1060
|
+
_a.sent();
|
|
1061
|
+
_a.label = 2;
|
|
1062
|
+
case 2: return [2 /*return*/];
|
|
1063
|
+
}
|
|
1064
|
+
});
|
|
1065
|
+
});
|
|
784
1066
|
}
|
|
785
1067
|
// ============================================================================
|
|
786
1068
|
// Utilities
|
|
@@ -789,14 +1071,14 @@ export async function waitForRateLimitReset(info) {
|
|
|
789
1071
|
* Sleep for specified milliseconds
|
|
790
1072
|
*/
|
|
791
1073
|
function sleep(ms) {
|
|
792
|
-
return new Promise((resolve)
|
|
1074
|
+
return new Promise(function (resolve) { return setTimeout(resolve, ms); });
|
|
793
1075
|
}
|
|
794
1076
|
/**
|
|
795
1077
|
* Create a progress logger for actions
|
|
796
1078
|
*/
|
|
797
|
-
|
|
798
|
-
|
|
799
|
-
|
|
1079
|
+
function createProgressLogger(prefix) {
|
|
1080
|
+
if (prefix === void 0) { prefix = "Action"; }
|
|
1081
|
+
return function (action) {
|
|
1082
|
+
console.log("[".concat(prefix, "] ").concat(getActionDescription(action.command), ": ").concat(action.progress, "%"));
|
|
800
1083
|
};
|
|
801
1084
|
}
|
|
802
|
-
//# sourceMappingURL=actions.js.map
|