pixiv-bookmarks-to-pleroma/common.js

125 lines
4.2 KiB
JavaScript

export var credentials = JSON.parse(Deno.readTextFileSync("credentials.json"));
var {client_id, client_secret, username, password, pixiv_cookie, access_token} = credentials;
export var known_ids = {};
try {
known_ids = Object.fromEntries(Deno.readTextFileSync("known_ids.csv").trim().split("\n").map(line => line.split(",")));
} catch (e) {}
if (!access_token) {
let form = new FormData();
form.append("client_id", client_id);
form.append("client_secret", client_secret);
form.append("grant_type", "password");
form.append("username", username);
form.append("password", password);
let data = await fetch("https://pleroma.lamp.wtf/oauth/token", {
method: "POST",
body: form
}).then(res => res.json());
console.log ("logged in", data);
credentials.access_token = access_token = data.access_token;
Deno.writeTextFileSync("credentials.json", JSON.stringify(credentials, null, '\t'));
}
async function uploadFile({data, name}) {
var form = new FormData();
form.append("file", data, name);
var res = await fetch("https://pleroma.lamp.wtf/api/v1/media", {
method: "POST",
body: form,
headers: {"Authorization": `Bearer ${access_token}`}
});
if (!res.ok) throw new Error("HTTP " + res.status);
var json = await res.json();
console.log("uploaded file", res.status, json.url);
return json;
}
async function postStatus({status, visibility = "unlisted", content_type = "text/plain", media_ids = [], sensitive, files}) {
if (files) {
media_ids = (await Promise.all(files.map(file => uploadFile(file)))).map(d => d.id);
}
var form = new FormData();
form.append("status", status);
form.append("visibility", visibility);
form.append("source", "bot");
form.append("content_type", content_type);
for (let media_id of media_ids) {
form.append("media_ids[]", media_id);
}
if (sensitive) form.append("sensitive", "true");
var res = await fetch("https://pleroma.lamp.wtf/api/v1/statuses", {
method: "POST",
body: form,
headers: {"Authorization": `Bearer ${access_token}`}
});
if (!res.ok) throw new Error("HTTP " + res.status);
var json = await res.json();
console.log("posted", res.status, json.uri || json);
return json;
}
async function downloadPixivIllust(illust_id) {
var url = `https://www.pixiv.net/en/artworks/${illust_id}`;
console.log("fetch", url);
var res = await fetch(url, {headers: {"Cookie": pixiv_cookie}});
if (!res.ok) throw new Error("HTTP " + res.status);
var html = await res.text();
var illust = Object.values(JSON.parse(html.match(/<meta name="preload-data" id="meta-preload-data" content='(.*)'>/)[1]).illust)[0];
try {
let u = `https://www.pixiv.net/ajax/illust/${illust_id}/pages`;
console.log("fetch", u);
let res = await fetch(u, {headers: {"Cookie": pixiv_cookie}});
if (!res.ok) throw new Error("HTTP " + res.status);
let json = await res.json();
var images = json.body.map(x => ({
url: x.urls.original,
width: x.width,
height: x.height
}));
} catch (error) {
console.error(error.stack);
var images = [];
for (let i = 0; i < illust.pageCount; i++) {
images.push({
url: illust.urls.original.replace('p0', 'p'+i)
});
}
}
for (let image of images) {
image.name = image.url.split('/').pop();
console.log("fetch", image.url);
image.data = await fetch(image.url, {headers: {"Referer": "https://www.pixiv.net/"}}).then(res => res.blob());
};
return {illust, images};
}
export async function pixivToPleroma(illust_id) {
try {
var {illust, images} = await downloadPixivIllust(illust_id);
var {url} = await postStatus({
status: `https://www.pixiv.net/en/artworks/${illust_id}`
+ ((images.length > 4) ? `\n⚠ There are ${images.length} attachments` : '')
+ ((illust.illustType == 2) ? '\n⚠ ugoira conversion not implemented, view on Pixiv' : ''),
files: images,
visibility: "unlisted",
sensitive: Boolean(illust.xRestrict)
});
Deno.writeTextFileSync("known_ids.csv", `${illust_id},${url}\n`, {append: true});
var {postPixivIllustToMatrix} = await import("./matrix.js"); //circular dependency -.-
await postPixivIllustToMatrix(illust, images, url);
} catch (error) {
console.error(error.stack);
postStatus({
status: `https://www.pixiv.net/en/artworks/${illust_id}` +
`\n#error:\n${error.stack}`
});
}
}