instagram: use different endpoint and fallback to two other options

This commit is contained in:
wukko 2024-04-20 20:33:34 +06:00
parent f48a1d9af6
commit 1ff49f0669
No known key found for this signature in database
GPG key ID: 3E30B3F26C7B4AA2

View file

@ -60,39 +60,99 @@ async function request(url, cookie, method = 'GET', requestData) {
return data.json();
}
async function getPost(id) {
let data;
try {
const cookie = getCookie('instagram');
let dtsgId;
if (cookie) {
dtsgId = await findDtsgId(cookie);
async function requestHTML(id, cookie = {}) {
const data = await fetch(`https://www.instagram.com/p/${id}/embed/captioned/`, {
headers: {
"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.7",
"Accept-Language": "en-GB,en;q=0.9",
"Cache-Control": "max-age=0",
"Dnt": "1",
"Priority": "u=0, i",
"Sec-Ch-Ua": 'Chromium";v="124", "Google Chrome";v="124", "Not-A.Brand";v="99',
"Sec-Ch-Ua-Mobile": "?0",
"Sec-Ch-Ua-Platform": "macOS",
"Sec-Fetch-Dest": "document",
"Sec-Fetch-Mode": "navigate",
"Sec-Fetch-Site": "none",
"Sec-Fetch-User": "?1",
"Upgrade-Insecure-Requests": "1",
"User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.0.0 Safari/537.36",
...cookie
}
}).then(r => r.text());
const url = new URL('https://www.instagram.com/api/graphql/');
let embedData = JSON.parse(data?.match(/"init",\[\],\[(.*?)\]\],/)[1]);
const requestData = {
jazoest: '26406',
variables: JSON.stringify({
shortcode: id,
__relay_internal__pv__PolarisShareMenurelayprovider: false
}),
doc_id: '7153618348081770'
};
if (dtsgId) {
requestData.fb_dtsg = dtsgId;
if (!embedData || !embedData?.contextJSON) return false;
embedData = JSON.parse(embedData.contextJSON);
return embedData;
}
async function requestGQL(id, cookie) {
let dtsgId;
if (cookie) {
dtsgId = await findDtsgId(cookie);
}
const url = new URL('https://www.instagram.com/api/graphql/');
const requestData = {
jazoest: '26406',
variables: JSON.stringify({
shortcode: id,
__relay_internal__pv__PolarisShareMenurelayprovider: false
}),
doc_id: '7153618348081770'
};
if (dtsgId) {
requestData.fb_dtsg = dtsgId;
}
return (await request(url, cookie, 'POST', requestData))
.data
?.xdt_api__v1__media__shortcode__web_info
?.items
?.[0];
}
async function extractOldPost(data, id) {
const sidecar = data?.gql_data?.shortcode_media?.edge_sidecar_to_children;
if (sidecar) {
const picker = sidecar.edges.filter(e => e.node?.display_url)
.map(e => {
const type = e.node?.is_video ? "video" : "photo";
const url = type === "video" ? e.node?.video_url : e.node?.display_url;
return {
type, url,
/* thumbnails have `Cross-Origin-Resource-Policy`
** set to `same-origin`, so we need to proxy them */
thumb: createStream({
service: "instagram",
type: "default",
u: e.node?.display_url,
filename: "image.jpg"
})
}
});
if (picker.length) return { picker }
} else if (data?.gql_data?.shortcode_media?.video_url) {
return {
urls: data.shortcode_media.video_url,
filename: `instagram_${id}.mp4`,
audioFilename: `instagram_${id}_audio`
}
} else if (data?.gql_data?.shortcode_media?.display_url) {
return {
urls: data.gql_data?.shortcode_media.display_url,
isPhoto: true
}
}
}
data = (await request(url, cookie, 'POST', requestData))
.data
?.xdt_api__v1__media__shortcode__web_info
?.items
?.[0];
} catch {}
if (!data) return { error: 'ErrorCouldntFetch' };
async function extractNewPost(data, id) {
const carousel = data.carousel_media;
if (carousel) {
const picker = carousel.filter(e => e?.image_versions2)
@ -133,7 +193,31 @@ async function getPost(id) {
isPhoto: true
}
}
}
async function getPost(id) {
let data, result, dataType = 'old';
try {
const cookie = getCookie('instagram');
data = await requestHTML(id);
if (!data) data = await requestHTML(id, cookie);
if (!data) {
dataType = 'new';
data = await requestGQL(id, cookie);
}
} catch {}
if (!data) return { error: 'ErrorCouldntFetch' };
if (dataType === 'new') {
result = extractNewPost(data, id)
} else {
result = extractOldPost(data, id)
}
if (result) return result;
return { error: 'ErrorEmptyDownload' }
}