@onesignal/node-onesignal
Version:
OpenAPI client for @onesignal/node-onesignal
87 lines • 3.56 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.isMessageNotSent = exports.isMessageSent = exports.createNotificationWithRetry = void 0;
const crypto_1 = require("crypto");
const DefaultApi_1 = require("./apis/DefaultApi");
const RETRYABLE_STATUSES = [429, 503];
const MIN_BASE_DELAY_MS = 1000;
const MAX_BASE_DELAY_MS = 60000;
async function createNotificationWithRetry(configuration, notification, options) {
const maxRetries = options && options.maxRetries !== undefined ? options.maxRetries : 3;
const requestedBaseDelayMs = options && typeof options.baseDelayMs === 'number' && isFinite(options.baseDelayMs)
? options.baseDelayMs
: MIN_BASE_DELAY_MS;
const baseDelayMs = Math.min(MAX_BASE_DELAY_MS, Math.max(MIN_BASE_DELAY_MS, requestedBaseDelayMs));
if (!notification.idempotency_key) {
notification.idempotency_key = generateUuidV4();
}
const requestFactory = new DefaultApi_1.DefaultApiRequestFactory(configuration);
const responseProcessor = new DefaultApi_1.DefaultApiResponseProcessor();
let attempt = 0;
while (true) {
let response;
try {
const requestContext = await requestFactory.createNotification(notification, configuration);
response = await configuration.httpApi.send(requestContext).toPromise();
}
catch (e) {
if (attempt >= maxRetries) {
throw e;
}
await sleep(baseDelayMs * Math.pow(2, attempt));
attempt++;
continue;
}
if (RETRYABLE_STATUSES.indexOf(response.httpStatusCode) !== -1 && attempt < maxRetries) {
await sleep(retryDelayMs(response.headers, attempt, baseDelayMs));
attempt++;
continue;
}
const body = await responseProcessor.createNotification(response);
return { response: body, wasReplayed: isReplayed(response.headers) };
}
}
exports.createNotificationWithRetry = createNotificationWithRetry;
function headerValue(headers, name) {
const target = name.toLowerCase();
for (const key in headers) {
if (Object.prototype.hasOwnProperty.call(headers, key) && key.toLowerCase() === target) {
return headers[key];
}
}
return undefined;
}
function isReplayed(headers) {
const value = headerValue(headers, 'idempotent-replayed');
return value !== undefined && value.trim().toLowerCase() === 'true';
}
function retryDelayMs(headers, attempt, baseDelayMs) {
const retryAfter = headerValue(headers, 'retry-after');
if (retryAfter !== undefined && /^\d+$/.test(retryAfter.trim())) {
return parseInt(retryAfter.trim(), 10) * 1000;
}
return baseDelayMs * Math.pow(2, attempt);
}
function generateUuidV4() {
const bytes = (0, crypto_1.randomBytes)(16);
bytes[6] = (bytes[6] & 0x0f) | 0x40;
bytes[8] = (bytes[8] & 0x3f) | 0x80;
const hex = bytes.toString('hex');
return (hex.substring(0, 8) + '-' +
hex.substring(8, 12) + '-' +
hex.substring(12, 16) + '-' +
hex.substring(16, 20) + '-' +
hex.substring(20));
}
function sleep(ms) {
return new Promise((resolve) => setTimeout(resolve, ms));
}
function isMessageSent(response) {
return typeof response.id === 'string' && response.id.length > 0;
}
exports.isMessageSent = isMessageSent;
function isMessageNotSent(response) {
return !isMessageSent(response);
}
exports.isMessageNotSent = isMessageNotSent;
//# sourceMappingURL=helpers.js.map