|
|
@@ -505,13 +505,78 @@ async function handleHomeAssistantLogin(config, credentials) {
|
|
|
const name = cookie.split('=')[0];
|
|
|
cookieMap.set(name, cookie);
|
|
|
});
|
|
|
- const uniqueCookies = Array.from(cookieMap.values());
|
|
|
+ let uniqueCookies = Array.from(cookieMap.values());
|
|
|
|
|
|
console.log(`登录成功!获取到 ${uniqueCookies.length} 个唯一 Cookie`);
|
|
|
uniqueCookies.forEach((cookie, index) => {
|
|
|
console.log(`Cookie ${index + 1}: ${cookie.substring(0, 100)}...`);
|
|
|
});
|
|
|
|
|
|
+ // 步骤3: 处理 OAuth2 授权流程
|
|
|
+ // 登录成功后,Home Assistant 需要完成 OAuth2 授权才能访问主页面
|
|
|
+ console.log('步骤3: 处理 OAuth2 授权流程...');
|
|
|
+ try {
|
|
|
+ // 构建 state 参数(base64 编码的 JSON)
|
|
|
+ const stateData = {
|
|
|
+ hassUrl: targetBaseUrl,
|
|
|
+ clientId: `${targetBaseUrl}/`
|
|
|
+ };
|
|
|
+ const state = Buffer.from(JSON.stringify(stateData)).toString('base64');
|
|
|
+
|
|
|
+ // 构建授权 URL
|
|
|
+ const redirectUri = `${targetBaseUrl}/?auth_callback=1`;
|
|
|
+ const clientId = `${targetBaseUrl}/`;
|
|
|
+ const authorizeUrl = `${targetBaseUrl}/auth/authorize?response_type=code&redirect_uri=${encodeURIComponent(redirectUri)}&client_id=${encodeURIComponent(clientId)}&state=${encodeURIComponent(state)}`;
|
|
|
+
|
|
|
+ console.log(`访问授权端点: ${authorizeUrl}`);
|
|
|
+
|
|
|
+ // 构建 Cookie 字符串用于授权请求
|
|
|
+ const cookieHeader = uniqueCookies.map(cookie => {
|
|
|
+ const cookieStr = cookie.split(';')[0]; // 只取 name=value 部分
|
|
|
+ return cookieStr;
|
|
|
+ }).join('; ');
|
|
|
+
|
|
|
+ console.log(`使用 Cookie 头: ${cookieHeader.substring(0, 100)}...`);
|
|
|
+
|
|
|
+ const authorizeResponse = await axios.get(authorizeUrl, {
|
|
|
+ headers: {
|
|
|
+ 'User-Agent': baseHeaders['User-Agent'],
|
|
|
+ 'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8',
|
|
|
+ 'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8',
|
|
|
+ 'Referer': `${targetBaseUrl}/`,
|
|
|
+ 'Cookie': cookieHeader
|
|
|
+ },
|
|
|
+ withCredentials: true,
|
|
|
+ maxRedirects: 5,
|
|
|
+ validateStatus: function (status) {
|
|
|
+ return status >= 200 && status < 400;
|
|
|
+ }
|
|
|
+ });
|
|
|
+
|
|
|
+ console.log(`授权响应状态码: ${authorizeResponse.status}`);
|
|
|
+ console.log(`授权响应 URL: ${authorizeResponse.request?.res?.responseUrl || authorizeResponse.config?.url}`);
|
|
|
+
|
|
|
+ // 获取授权响应中的 Cookie
|
|
|
+ const authorizeCookies = authorizeResponse.headers['set-cookie'] || [];
|
|
|
+ console.log(`授权响应获取到 ${authorizeCookies.length} 个 Cookie`);
|
|
|
+
|
|
|
+ // 合并授权 Cookie
|
|
|
+ authorizeCookies.forEach(cookie => {
|
|
|
+ const name = cookie.split('=')[0];
|
|
|
+ cookieMap.set(name, cookie);
|
|
|
+ });
|
|
|
+ uniqueCookies = Array.from(cookieMap.values());
|
|
|
+
|
|
|
+ console.log(`授权完成!最终获取到 ${uniqueCookies.length} 个唯一 Cookie`);
|
|
|
+ } catch (error) {
|
|
|
+ console.log('授权流程失败(可能不需要):', error.message);
|
|
|
+ if (error.response) {
|
|
|
+ console.log('授权响应状态:', error.response.status);
|
|
|
+ console.log('授权响应 URL:', error.response.request?.res?.responseUrl || error.config?.url);
|
|
|
+ }
|
|
|
+ // 授权失败不影响登录,继续使用已有的 Cookie
|
|
|
+ }
|
|
|
+
|
|
|
return {
|
|
|
success: true,
|
|
|
cookies: uniqueCookies,
|