diff --git a/lib/sources/minimedcarelink/index.js b/lib/sources/minimedcarelink/index.js index c45dfa9..10b36f5 100644 --- a/lib/sources/minimedcarelink/index.js +++ b/lib/sources/minimedcarelink/index.js @@ -2,11 +2,13 @@ var qs = require('qs'); var url = require('url'); var tough = require('tough-cookie'); +var crypto = require('crypto'); var ACS = require('axios-cookiejar-support'); var software = require('../../../package.json'); -//var user_agent_string = [software.name, `${software.name}@${software.version}`, 'M2M@V6', software.homepage].join(', '); -var user_agent_string = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.85 Safari/537.36 Edg/90.0.818.46"; +var software_string = [software.name, `${software.name}/${software.version}`, '(M2M@V6)', software.homepage].join(' '); +var browser_string = `Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.85 Safari/537.36 Edg/90.0.818.46 ${software.name}/${software.version} (M2M/V6)`; +var user_agent_string = software_string; // https://github.com/NightscoutFoundation/xDrip/blob/990df119a8404cff56cb68b92a7e0bb640da95ef/app/src/main/java/com/eveningoutpost/dexdrip/cgm/carelinkfollow/client/CareLinkClient.java#L559 // https://github.com/nightscout/minimed-connect-to-nightscout/blob/master/carelink.js @@ -221,7 +223,7 @@ function carelinkSource (opts, axios) { 'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9' , 'Accept-Language': "en;q=0.9, *;q=0.8" , 'sec-ch-ua': "\"Chromium\";v=\"112\", \"Google Chrome\";v=\"112\", \"Not:A-Brand\";v=\"99\"" - , "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/112.0.0.0 Safari/537.36" + , "User-Agent": browser_string }; @@ -236,19 +238,22 @@ function carelinkSource (opts, axios) { country: opts.countryCode , lang: opts.languageCode }; - var headers = { }; + var headers = { + 'x-uniq-req': crypto.randomUUID() + , ...html_headers + }; console.log("AUTH WITH", modDefaults.login_url, params, headers); return http.get(modDefaults.login_url, { params, headers }).then((resp) => { console.log("FIRST STEP LOGIN FLOW", resp.headers, resp.data); - let regex = /(
{ console.log("SUCCESS LOGGING IN", resp.headers, resp.data); - let regex = /( { return new tough.Cookie(c).cookieString( ); }) }; console.log("SUBMITTING CONSENT FLOW", flow.endpoint, payload, params, headers); @@ -375,6 +386,10 @@ function carelinkSource (opts, axios) { headers = authed_headers; } function getUser ( ) { + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; return http.get(modDefaults.me_url, { headers }).then((resp) => { console.log("SUCCESS FETCHING USER", resp.headers, resp); account.user = resp.data; @@ -390,7 +405,11 @@ function carelinkSource (opts, axios) { } function getProfile ( ) { - return http.get(modDefaults.my_profile_url, { headers: authed_headers }).then((resp) => { + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; + return http.get(modDefaults.my_profile_url, { headers }).then((resp) => { console.log("GOT PROFILE", resp.headers, resp.data); account.profile = resp.data; return resp.data; @@ -404,7 +423,11 @@ function carelinkSource (opts, axios) { countryCode: opts.countryCode , language: opts.languageCode }; - return http.get(modDefaults.country_settings_url, { params, headers: authed_headers }).then((resp) => { + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; + return http.get(modDefaults.country_settings_url, { params, headers }).then((resp) => { console.log("GOT COUNTRY SETTINGS", resp.headers, resp.data); account.requirements = resp.data; return resp.data; @@ -414,7 +437,11 @@ function carelinkSource (opts, axios) { } function getM2M ( ) { - return http.get(modDefaults.config_check_url, { headers: authed_headers }).then((resp) => { + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; + return http.get(modDefaults.config_check_url, { headers }).then((resp) => { console.log("GOT M2M SETTINGS", resp.headers, resp.data); account.m2m_enabled = resp.data.value; return resp.data; @@ -433,7 +460,11 @@ function carelinkSource (opts, axios) { return false; } - return http.get(modDefaults.patient_list_url, { headers: authed_headers }).then((resp) => { + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; + return http.get(modDefaults.patient_list_url, { headers }).then((resp) => { console.log("PATIENT LIST", resp.data); account.patient_list = resp.data; return resp.data; @@ -477,6 +508,10 @@ function carelinkSource (opts, axios) { , msgType: 'last24hours' , requestTime: Date.now( ) }; + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; if (!session.patientUsername) { return Promise.resolve(new Error("no patientUsername")); } @@ -496,12 +531,16 @@ function carelinkSource (opts, axios) { username: session.profile.username , role: "patient" }; + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; if (!session.isPatient) { body.role = "carepartner"; body.patientId = session.patientUsername; } // if (session.isPatient) { return Promise.resolve( ); } - return http.post(session.requirements.blePereodicDataEndpoint, body, { headers: authed_headers }).then((resp) => { + return http.post(session.requirements.blePereodicDataEndpoint, body, { headers }).then((resp) => { console.log("BLE PERIODIC ENDPOINT DATA", resp.headers, resp.data); return resp.data; }).catch((error) => { @@ -512,7 +551,11 @@ function carelinkSource (opts, axios) { function getMonitorData ( ) { // TODO: obsoleted by M2M? // deviceFamily determines whether to use M2M or BLE endpoint. - return http.get(modDefaults.monitor_data_url, { headers: authed_headers }).then((resp) => { + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; + return http.get(modDefaults.monitor_data_url, { headers }).then((resp) => { console.log("MONITOR DATA ENDPOINT DATA", resp.headers, resp.data); return resp.data; @@ -525,7 +568,11 @@ function carelinkSource (opts, axios) { var params = { numUploads: 1 }; - return http.get(modDefaults.recent_uploads_url, { params, headers: authed_headers }).then((resp) => { + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; + return http.get(modDefaults.recent_uploads_url, { params, headers }).then((resp) => { console.log("RECENT UPLOADS DATA", resp.headers, resp.data); return resp.data; }).catch((error) => { @@ -561,7 +608,10 @@ function carelinkSource (opts, axios) { var authed_headers = { Authorization: `Bearer ${session.token}` }; - var headers = authed_headers; + var headers = { + ...authed_headers + , 'x-uniq-req': crypto.randomUUID( ) + }; http.post(modDefaults.refresh_token_url, '', { headers }).then((resp) => { console.log("SUCCESS WITH REFRESH FOR", resp.headers, resp.data); var cookies = jar.getCookiesSync(baseURL);