UNPKG

homebridge-hatch-baby-rest

Version:
104 lines (103 loc) 3.6 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.RestClient = void 0; exports.apiPath = apiPath; exports.requestWithRetry = requestWithRetry; const util_1 = require("../shared/util"); const apiBaseUrl = 'https://prod-sleep.hatchbaby.com/', defaultRequestOptions = { method: 'GET', }, defaultHeaders = { USER_AGENT: 'hatch_rest_api', 'content-type': 'application/json', }; function apiPath(path) { return apiBaseUrl + path; } async function requestWithRetry(options) { try { const optionsWithDefaults = { ...defaultRequestOptions, ...options, headers: { ...defaultHeaders, ...options.headers, }, }; if (options.json) { optionsWithDefaults.body = JSON.stringify(options.json); } const response = await fetch(new Request(options.url, optionsWithDefaults)); if (!response.ok) { const errorWithResponse = new Error(`Failed to fetch ${options.url}. Response: ${response.status} ${response.statusText}. ${await response.text()}`); errorWithResponse.response = response; throw errorWithResponse; } const responseJson = await response.json(); return responseJson; } catch (e) { if (!e.response) { (0, util_1.logError)(`Failed to reach Hatch Baby server at ${options.url}. ${e.message}. Trying again in 5 seconds...`); await (0, util_1.delay)(5000); return requestWithRetry(options); } throw e; } } class RestClient { constructor(authOptions) { this.authOptions = authOptions; this.loginPromise = this.logIn(); } async logIn() { try { const resp = await requestWithRetry({ url: apiPath('public/v1/login'), json: { email: this.authOptions.email, password: this.authOptions.password, }, method: 'POST', }); return resp; } catch (requestError) { const errorMessage = 'Failed to fetch oauth token from Hatch Baby. Verify that your email and password are correct.'; (0, util_1.logError)(requestError.response || requestError); (0, util_1.logError)(errorMessage); throw new Error(errorMessage); } } refreshAuth() { this.loginPromise = this.logIn(); } async request(options) { try { const loginResponse = await this.loginPromise, headers = { ...options.headers, 'X-HatchBaby-Auth': loginResponse.token, }, response = await requestWithRetry({ ...options, headers, }); return response.payload; } catch (e) { const response = e.response || {}, { url } = options; if (response.status === 401) { this.refreshAuth(); return this.request(options); } if (response.status === 404 && url.startsWith(apiBaseUrl)) { (0, util_1.logError)('404 from endpoint ' + url); throw new Error('Not found with response: ' + JSON.stringify(response.data)); } (0, util_1.logError)(`Request to ${url} failed`); throw e; } } getAccount() { return this.loginPromise.then((l) => l.payload); } } exports.RestClient = RestClient;