"use strict"; /* * User Account認証(OAuth 2.0 認可コードフロー)の一回限りのセットアップスクリプト。 * Drive/共有ドライブAPIはService Account認証では利用できないため、実ユーザーの * 認可を一度だけ行い、refresh_tokenを.envに保存する。以降のbackup.js実行は * このrefresh_tokenからaccess_tokenを自動再発行する(ユーザー操作不要)。 * * 事前準備: * Developer Consoleの「User Account認証」欄の Redirect URL に、 * .env の LW_REDIRECT_URI と完全一致する値を登録しておくこと。 * * 使い方: * node lineworks-authorize.js */ const crypto = require("crypto"); const readline = require("readline"); const { loadEnv, updateEnvValue } = require("./lib/env"); loadEnv(); const { buildAuthorizeUrl, exchangeCodeForToken } = require("./lib/lineworksUserAuth"); function prompt(question) { const rl = readline.createInterface({ input: process.stdin, output: process.stdout }); return new Promise((resolve) => { rl.question(question, (answer) => { rl.close(); resolve(answer.trim()); }); }); } // リダイレクト後のURL全体、または code の値そのものが貼り付けられるケースの両方に対応する。 function extractCode(input) { if (input.includes("code=")) { try { const url = new URL(input); const code = url.searchParams.get("code"); if (code) return code; } catch (_err) { const match = input.match(/[?&]code=([^&\s]+)/); if (match) return decodeURIComponent(match[1]); } } return input; } async function main() { const state = crypto.randomBytes(16).toString("hex"); const authorizeUrl = buildAuthorizeUrl({ state }); console.log("以下のURLをブラウザで開き、対象のLINE WORKSアカウントでログイン・同意してください:"); console.log(""); console.log(authorizeUrl); console.log(""); console.log("同意後、Redirect URLへ遷移します(ページ自体が表示されなくても問題ありません)。"); console.log("遷移後のブラウザのアドレスバーのURL全体(または code= の値だけ)をコピーしてください。"); console.log(""); const input = await prompt("リダイレクト後のURL(またはcode)を貼り付けてEnter: "); const code = extractCode(input); if (!code) { console.error("codeを取得できませんでした。"); process.exitCode = 1; return; } console.log("アクセストークンに交換しています..."); const tokenData = await exchangeCodeForToken(code); if (!tokenData.refresh_token) { console.error("レスポンスに refresh_token が含まれていませんでした。"); process.exitCode = 1; return; } updateEnvValue("LW_USER_REFRESH_TOKEN", tokenData.refresh_token); console.log(""); console.log("成功しました。"); console.log(` scope: ${tokenData.scope}`); console.log(` access_tokenの有効期限: ${tokenData.expires_in}秒`); console.log(" refresh_token を .env の LW_USER_REFRESH_TOKEN に保存しました。"); console.log(""); console.log("これで 'node backup.js run' が共有ドライブへアクセスできるようになります。"); } main().catch((err) => { console.error(`セットアップに失敗しました: ${err.message}`); process.exitCode = 1; });