Last active
April 10, 2024 19:11
-
-
Save stonetip/0d7e91465b31e5fc7d17a42276e12486 to your computer and use it in GitHub Desktop.
Demonstration of using a Promise within a function (redundant...see fetchLib.js file instead)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Helper function to determine the appropriate content type and body formatting | |
function prepareData(data) { | |
if (data instanceof FormData) { | |
return { body: data }; | |
} | |
if (data instanceof Object) { | |
return { | |
body: JSON.stringify(data), | |
headers: { "Content-type": "application/json; charset=UTF-8" } | |
}; | |
} | |
return {}; | |
} | |
// Generalized function to send data with specific HTTP methods | |
async function sendData(url, method, data) { | |
try { | |
const { body, headers } = prepareData(data); | |
const response = await fetch(url, { | |
method: method, | |
body: body, | |
headers: headers | |
}); | |
return processFetchResponse(response); | |
} catch (error) { | |
console.error("error (internal):", error); | |
throw error; | |
} | |
} | |
async function getData(url) { | |
try { | |
const response = await fetch(url); | |
return processFetchResponse(response); | |
} catch (error) { | |
console.error("error (internal):", error, url); | |
throw error; | |
} | |
} | |
function postData(url, data) { | |
return sendData(url, 'POST', data); | |
} | |
function putData(url, data) { | |
return sendData(url, 'PUT', data); | |
} | |
function deleteData(url) { | |
return sendData(url, 'DELETE'); | |
} | |
// Processing the fetch response based on content type | |
async function processFetchResponse(response) { | |
if (!response.ok) { | |
const errorMsg = await response.text(); // Attempt to read body for detailed error message | |
throw { | |
"status": response.status, | |
"statusText": response.statusText, | |
"message": errorMsg | |
}; | |
} | |
const contentType = response.headers.get("Content-Type") || ""; | |
switch(true) { | |
case contentType.includes("application/json"): | |
return response.json(); | |
case contentType.includes("application/octet-stream") || contentType.includes("application/gzip"): | |
return response.arrayBuffer(); | |
case contentType.includes("text/html"): | |
const html = await response.text(); | |
return { | |
page_type: "generic", | |
html: html | |
}; | |
default: | |
throw new Error(`Invalid content type: ${contentType}`); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
function makeCall() { | |
return new Promise(function (resolve, reject) { | |
// If the initial call is okay, we'll try processing it. | |
resolve( | |
fetch("/myAPI/getData") | |
.then(response => { | |
if (!response.ok) | |
{ throw Error(response) } | |
return response.json(); | |
}) | |
.then(json => { | |
console.log(json); | |
// Note: These are specific to the API being called, not generic results | |
if (json.exception !== null || json.isFaulted || json.isCanceled) { | |
throw Error(json); | |
} else { | |
// If everything goes alright, let the caller know. (This could contain more info, if necessary) | |
return "Operation completed."; | |
} | |
}) | |
.catch(error => { | |
console.error(error); | |
return ("There was an error."); | |
}) | |
); | |
// If the initial call was bad, no processing happens | |
reject(Error("An error occurred.")); | |
} | |
); | |
} | |
window.onload = function () { | |
const testBtn = document.querySelector("#btnTest"); | |
testBtn.onclick = function () { | |
makeCall().then(result => console.log(`result: ${result}`)); | |
}; | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
In the course of working with Fetch, I learned it already is Promise-based. The code above is redundant, so adding adding another gist that has some useful functionality but less wrapping.