diff --git a/app/index.ts b/app/index.ts index 02995f0..41b7124 100644 --- a/app/index.ts +++ b/app/index.ts @@ -10,7 +10,9 @@ async function main() { try { const data = await Login(); console.log("✨ | Instagram login successful"); - console.log(`πŸ€” | Login as ${data.currentUser.full_name}`); + if (data) { + console.log(`πŸ€” | Login as ${data.currentUser.full_name}`); + } } catch (error) { console.error("❌ | Instagram login failed:", error); } finally { diff --git a/app/lib/instagram.ts b/app/lib/instagram.ts index 79ef883..65bb37c 100644 --- a/app/lib/instagram.ts +++ b/app/lib/instagram.ts @@ -7,38 +7,59 @@ export async function Login() { ig.state.generateDevice(process.env.IG_USERNAME!); ig.state.appUserAgent + ig.request.end$.subscribe(async () => { + const serialized = await ig.state.serialize(); + delete serialized.constants; // this deletes the version info, so you'll always use the version provided by the library + await Bun.write('./temp/session.json', JSON.stringify(serialized)); + }); try { - await ig.simulate.preLoginFlow(); - const loggedInUser = await ig.account.login( - process.env.IG_USERNAME!, - process.env.IG_PASSWORD! - ); - process.nextTick(async () => await ig.simulate.postLoginFlow()); - const currentUser = await ig.account.currentUser(); + let loggedInUser; + try { - return { loggedInUser, currentUser }; + if (await Bun.file('./temp/session.json').exists()) { + const sessionData = await Bun.file('./temp/session.json').json(); + await ig.state.deserialize(sessionData); + loggedInUser = await ig.account.login( + process.env.IG_USERNAME!, + process.env.IG_PASSWORD! + ); + } else { + loggedInUser = await ig.account.login( + process.env.IG_USERNAME!, + process.env.IG_PASSWORD! + ); + await ig.simulate.preLoginFlow(); - } catch (error: any) { - if (error.name === "IgCheckpointError") { - console.error( - "Instagram checkpoint required. Please verify your account in the Instagram app or handle the challenge." - ); - // Optionally, you can trigger challenge handling here - // await ig.challenge.auto(true); // Requesting sms-code or click "It was me" button - } else { - console.error("πŸ”’ | Login failed:", error); + process.nextTick(async () => await ig.simulate.postLoginFlow()); + } + } catch (error: any) { + if (error.name === "IgCheckpointError") { + console.error( + "Instagram checkpoint required. Please verify your account in the Instagram app or handle the challenge." + ); + // Optionally, you can trigger challenge handling here + // await ig.challenge.auto(true); // Requesting sms-code or click "It was me" button + } else { + console.error("πŸ”’ | Login failed:", error); + } + throw error; } - throw error; + + const currentUser = await ig.account.currentUser(); + return { loggedInUser, currentUser }; + } catch (error) { + console.warn("⚠️ | Failed to load session data:", error); + } } export class Upload { static async Post(filePath: string, caption: string) { try { - const ImagePath = path.resolve(`${filePath}`); + const ImagePath = path.resolve(`${filePath}`); const bunFile = Bun.file(ImagePath); const ImageBuffer = Buffer.from(await bunFile.arrayBuffer()); - + await ig.publish.photo({ file: ImageBuffer, caption: caption, @@ -47,13 +68,13 @@ export class Upload { console.error("Error uploading post:", error); } } - + static async Story(filePath: string, MLSV_YMD: string) { try { const ImagePath = path.resolve(`${filePath}`); const bunFile = Bun.file(ImagePath); const ImageBuffer = Buffer.from(await bunFile.arrayBuffer()); - + await ig.publish.story({ file: ImageBuffer, caption: `#μΈμ²œμƒμ •μ€‘ν•™κ΅ #상정쀑학ꡐ #급식 \n${MLSV_YMD}일자 급식`, diff --git a/app/playground.ts b/app/playground.ts index 214e1dd..3d1fa1c 100644 --- a/app/playground.ts +++ b/app/playground.ts @@ -1,63 +1,22 @@ -//import { Discord } from "./lib/discord"; -import { CreateImage } from "./lib/image"; +// //import { Discord } from "./lib/discord"; +// import {getAllSchedules} from "./lib/schedules"; +// import { CreateImage } from "./lib/image"; +// await CreateImage.PostSchedule(); -//const YYMMDD = new Date().toISOString().slice(0, 10).replace(/-/g, "").toString(); -const YYMMDD = "20250530" -//console.log(YYMMDD); +// import { Login, Upload } from "./lib/instagram"; +// try { +// const data = await Login(); +// console.log("✨ | Instagram login successful"); +// console.log(`πŸ€” | Login as ${data.currentUser.full_name}`); +// } catch (error) { +// console.error("❌ | Instagram login failed:", error); +// } finally { +// console.timeEnd("πŸ”“ | Instagram login"); +// } -//Discord("20250509") -async function run() { - console.time("Post"); - const post = await CreateImage.PostMeal(YYMMDD); - console.timeEnd("Post"); - console.log("Post created:", post); - let NutritionInfoText = ""; - const entries = Object.entries(post ?? {}).filter(([_, value]) => value.toString().length > 0); - entries.forEach(([name, value], idx) => { - NutritionInfoText += `${name} : ${value.toString().replace(",", ", ")}`; - if (idx !== entries.length - 1) { - NutritionInfoText += "\n"; - } - }); - console.log("Nutrition Info Text:", NutritionInfoText); - - console.time("Story"); - await CreateImage.ConvertToStory(`./temp/${YYMMDD}.png`); - console.timeEnd("Story"); -} - -run(); - -import { getAllSchedules } from "./lib/schedule"; - - -//import { CreateImage } from "./lib/image"; - -//CreateImage.PostSchedule() - -//const tomorrow = new Date(); -//tomorrow.setDate(tomorrow.getDate() + 1); - -// 내일이 1일이면 -//console.log(tomorrow.getDate()); - - -/*import { VTSList } from "./lib/vts"; - -VTSList().then(results => { - if (results.length > 0) { - console.log("\n5번째 ν–‰μ˜ λ…Έλž€μƒ‰ μ…€ λ‚΄μš© 리슀트:"); - results.forEach(value => console.log(value)); - } else { - console.log("\n5번째 ν–‰μ—μ„œ λ…Έλž€μƒ‰ 배경의 셀을 μ°Ύμ§€ λͺ»ν–ˆκ±°λ‚˜, 'V.T.S.' 쑰건 뢈좩쑱."); - } -});*/ -/* -getAllSchedules() - .then((schedules) => { - console.log("학사 일정:", schedules); - }) - .catch((error) => { - console.error("Error fetching schedules:", error); - }); - */ \ No newline at end of file +// await Upload.Post( +// `/home/neko/today.isangjeong/app/temp/schedule-2025-06.png`, +// `#μΈμ²œμƒμ •μ€‘ν•™κ΅ #상정쀑학ꡐ #학사일정 \n${new Date().getFullYear()}년도 ${ +// new Date().getMonth() + 1 +// }μ›” 학사 일정` +// ); diff --git a/compose.yml b/compose.yml index fdc5300..cddde1a 100644 --- a/compose.yml +++ b/compose.yml @@ -1,6 +1,15 @@ services: app: build: . - restart: always + restart: unless-stopped volumes: - - ./logs:/code/app/temp/logs \ No newline at end of file + - ./logs:/code/app/temp/logs + networks: + hikari: + +networks: + hikari: + ipam: + driver: default + config: + - subnet: 172.30.0.0/16