@iflyrpa/actions 4.0.0-beta.6 → 4.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/bundle.js CHANGED
@@ -8734,9 +8734,11 @@ var __webpack_exports__ = {};
8734
8734
  origin: ()=>utils_origin
8735
8735
  });
8736
8736
  var package_namespaceObject = {
8737
- i8: "0.1.1"
8737
+ i8: "0.1.2"
8738
+ };
8739
+ var package_namespaceObject_0 = {
8740
+ i8: "3.1.1"
8738
8741
  };
8739
- var package_namespaceObject_0 = JSON.parse('{"i8":"4.0.0-beta.5"}');
8740
8742
  const external_node_fs_namespaceObject = require("node:fs");
8741
8743
  var external_node_fs_default = /*#__PURE__*/ __webpack_require__.n(external_node_fs_namespaceObject);
8742
8744
  const external_node_http_namespaceObject = require("node:http");
@@ -23368,7 +23370,8 @@ var __webpack_exports__ = {};
23368
23370
  url: error.config?.url,
23369
23371
  isProxyRequest: !!(error.config && (error.config.httpAgent || error.config.httpsAgent)),
23370
23372
  params: error.config?.params,
23371
- data: error.config?.data
23373
+ data: error.config?.data,
23374
+ serverDate: error.response?.headers?.date
23372
23375
  }
23373
23376
  };
23374
23377
  if (foundError) Object.assign(errorResponse, foundError);
@@ -23446,7 +23449,7 @@ var __webpack_exports__ = {};
23446
23449
  try {
23447
23450
  this.proxyInfo = agent ? `${agent.ip}:${agent.port}` : void 0;
23448
23451
  const controller = new AbortController();
23449
- const timeoutId = setTimeout(()=>controller.abort(), reqTimeout);
23452
+ const timeoutId = setTimeout(()=>controller.abort(), reqTimeout + 500);
23450
23453
  const response = await this.apiClient({
23451
23454
  ...config,
23452
23455
  timeout: reqTimeout,
@@ -23470,7 +23473,7 @@ var __webpack_exports__ = {};
23470
23473
  599
23471
23474
  ].includes(handledError.code);
23472
23475
  if (Rtimes < retries && isRetry) {
23473
- this.logger?.info(`进入第${Rtimes + 1}次重试!`);
23476
+ this.logger?.info(`进入第${Rtimes + 1}次重试!错误码: ${handledError.code}`);
23474
23477
  await new Promise((resolve)=>setTimeout(resolve, retryDelay));
23475
23478
  return sessionRt(Rtimes + 1);
23476
23479
  }
@@ -28655,23 +28658,26 @@ var __webpack_exports__ = {};
28655
28658
  };
28656
28659
  }
28657
28660
  case types_ExecutionState.SUCCESS:
28658
- await updateTaskState?.({
28659
- state: types_TaskState.SUCCESS,
28660
- result: {
28661
- cookie: JSON.stringify(await task.steelBrowserContext?.cookies()).replace(/\\"/g, ""),
28662
- token,
28663
- userInfo: userInfo
28664
- }
28665
- });
28666
- return {
28667
- code: 0,
28668
- message: "成功",
28669
- data: {
28670
- cookie: JSON.stringify(await task.steelBrowserContext?.cookies()).replace(/\\"/g, ""),
28671
- token,
28672
- userInfo
28673
- }
28674
- };
28661
+ {
28662
+ const cookie = JSON.stringify(await task.steelBrowserContext?.cookies());
28663
+ await updateTaskState?.({
28664
+ state: types_TaskState.SUCCESS,
28665
+ result: {
28666
+ cookie,
28667
+ token,
28668
+ userInfo: userInfo
28669
+ }
28670
+ });
28671
+ return {
28672
+ code: 0,
28673
+ message: "成功",
28674
+ data: {
28675
+ cookie,
28676
+ token,
28677
+ userInfo
28678
+ }
28679
+ };
28680
+ }
28675
28681
  default:
28676
28682
  return {
28677
28683
  code: 500,
@@ -28845,6 +28851,16 @@ var __webpack_exports__ = {};
28845
28851
  const images = _images.filter((url)=>!!url && "" !== url.trim());
28846
28852
  return await Promise.all(images.map(async (url)=>{
28847
28853
  const fileName = getFilenameFromUrl(url);
28854
+ const ext = external_node_path_default().extname(fileName).toLowerCase();
28855
+ if (![
28856
+ ".jpg",
28857
+ ".jpeg",
28858
+ ".png"
28859
+ ].includes(ext)) throw {
28860
+ code: 414,
28861
+ message: `图片格式不支持:${fileName}。百家号仅支持 jpg、png 格式,请转换后重试。`,
28862
+ data: ""
28863
+ };
28848
28864
  const image = await downloadImage(url, external_node_path_default().join(tmpCachePath, fileName));
28849
28865
  const formData = new (form_data_default())();
28850
28866
  formData.append("org_file_name", fileName);
@@ -29028,20 +29044,11 @@ var __webpack_exports__ = {};
29028
29044
  };
29029
29045
  const rpa_rpaAction = async (task, params)=>{
29030
29046
  const tmpCachePath = task.getTmpPath();
29031
- const commonCookies = {
29032
- path: "/",
29033
- secure: true,
29034
- domain: "baijiahao.baidu.com",
29035
- url: "https://baijiahao.baidu.com",
29036
- httpOnly: true
29037
- };
29047
+ const validCookies = (params.cookies || []).filter((it)=>it.name && it.value && "undefined" !== it.value);
29038
29048
  const page = await task.createPage({
29039
29049
  show: task.debug,
29040
29050
  url: params.url || "https://baijiahao.baidu.com/builder/rc/edit?type=news&is_from_cms=1",
29041
- cookies: params.cookies?.map((it)=>({
29042
- ...it,
29043
- ...commonCookies
29044
- })) || []
29051
+ cookies: validCookies
29045
29052
  });
29046
29053
  page.setDefaultTimeout(60000);
29047
29054
  page.setDefaultNavigationTimeout(60000);
@@ -29446,6 +29453,7 @@ var __webpack_exports__ = {};
29446
29453
  })
29447
29454
  });
29448
29455
  const baijiahaoPublish = async (task, params)=>{
29456
+ task.logger.info(`baijiahaoPublish actionType: ${params.actionType}`);
29449
29457
  params.content = formatSectionHtml(params.content);
29450
29458
  if ("rpa" === params.actionType) return rpa_rpaAction(task, params);
29451
29459
  if ("mockApi" === params.actionType) return mockAction(task, params);
@@ -30574,6 +30582,8 @@ var __webpack_exports__ = {};
30574
30582
  }
30575
30583
  new Xhshow();
30576
30584
  const sessionCheck_xsEncrypt = new Xhshow();
30585
+ let lastEnvLogTime = 0;
30586
+ const ENV_LOG_INTERVAL_MS = 5000;
30577
30587
  const SessionCheckResultSchema = classic_schemas_object({
30578
30588
  isValidSession: classic_schemas_boolean()
30579
30589
  });
@@ -30638,6 +30648,23 @@ var __webpack_exports__ = {};
30638
30648
  }, "微信账号有效性检测完成!");
30639
30649
  };
30640
30650
  const XhsSessionCheck = async (_task, params)=>{
30651
+ const now = Date.now();
30652
+ const shouldLogEnv = now - lastEnvLogTime >= ENV_LOG_INTERVAL_MS;
30653
+ if (shouldLogEnv) {
30654
+ lastEnvLogTime = now;
30655
+ _task.logger?.debug("[XhsSessionCheck] 环境信息", {
30656
+ processType: process.type,
30657
+ pid: process.pid,
30658
+ nodeVersion: process.version,
30659
+ platform: process.platform,
30660
+ memoryUsage: {
30661
+ heapUsed: `${Math.round(process.memoryUsage().heapUsed / 1024 / 1024)} MB`,
30662
+ heapTotal: `${Math.round(process.memoryUsage().heapTotal / 1024 / 1024)} MB`
30663
+ },
30664
+ accountId: params.accountId,
30665
+ hasProxy: !!(params.proxyLoc || params.localIP)
30666
+ });
30667
+ }
30641
30668
  const check = {
30642
30669
  isValidSession: false,
30643
30670
  isValidWebSession: false
@@ -30674,7 +30701,32 @@ var __webpack_exports__ = {};
30674
30701
  if (cookie.name && cookie.value) acc[cookie.name] = cookie.value;
30675
30702
  return acc;
30676
30703
  }, {});
30677
- const loginBaseXsHeader = sessionCheck_xsEncrypt.signHeadersGet(loginBasePath, recordCookie, "xhs-pc-web", null);
30704
+ let loginBaseXsHeader;
30705
+ try {
30706
+ loginBaseXsHeader = sessionCheck_xsEncrypt.signHeadersGet(loginBasePath, recordCookie, "xhs-pc-web", null);
30707
+ } catch (signError) {
30708
+ _task.logger?.error("[XhsSessionCheck] 签名生成失败 - 环境快照", {
30709
+ accountId: params.accountId,
30710
+ error: signError instanceof Error ? signError.message : String(signError),
30711
+ stack: _task.debug ? signError instanceof Error ? signError.stack : void 0 : void 0,
30712
+ hasA1: !!recordCookie.a1,
30713
+ env: {
30714
+ processType: process.type,
30715
+ memoryUsage: {
30716
+ heapUsed: `${Math.round(process.memoryUsage().heapUsed / 1024 / 1024)} MB`,
30717
+ heapTotal: `${Math.round(process.memoryUsage().heapTotal / 1024 / 1024)} MB`
30718
+ },
30719
+ hasProxy: !!(params.proxyLoc || params.localIP),
30720
+ timeSinceLastLog: Date.now() - lastEnvLogTime
30721
+ }
30722
+ });
30723
+ return {
30724
+ code: 500,
30725
+ message: "账号签名生成失败,请稍后重试。",
30726
+ data: check
30727
+ };
30728
+ }
30729
+ const baseInfoStart = Date.now();
30678
30730
  const _baseInfo = http.api({
30679
30731
  method: "get",
30680
30732
  baseURL: "https://creator.xiaohongshu.com",
@@ -30683,23 +30735,43 @@ var __webpack_exports__ = {};
30683
30735
  }, {
30684
30736
  retries: 3,
30685
30737
  retryDelay: 20,
30686
- timeout: 3000
30687
- }).catch((e)=>e.data);
30738
+ timeout: 5000
30739
+ }).catch((e)=>{
30740
+ const clientTimestamp = Date.now();
30741
+ const serverDate = e?.extra?.serverDate;
30742
+ const serverTimestamp = serverDate ? new Date(serverDate).getTime() : null;
30743
+ const timeDriftMs = serverTimestamp ? clientTimestamp - serverTimestamp : null;
30744
+ _task.logger?.warn("[XhsSessionCheck] creator base 接口请求失败", {
30745
+ accountId: params.accountId,
30746
+ duration: Date.now() - baseInfoStart,
30747
+ code: e?.code,
30748
+ message: e?.message,
30749
+ data: e?.data,
30750
+ extra: e?.extra,
30751
+ proxyInfo: http.proxyInfo,
30752
+ clientTimestamp,
30753
+ serverDate,
30754
+ serverTimestamp,
30755
+ timeDriftMs,
30756
+ isLikelyClockDrift: null !== timeDriftMs && Math.abs(timeDriftMs) > 300000
30757
+ });
30758
+ return e.data;
30759
+ });
30688
30760
  const _web_session = http.api({
30689
30761
  method: "get",
30690
30762
  url: "https://edith.xiaohongshu.com/api/sns/web/unread_count"
30691
30763
  }, {
30692
30764
  retries: 3,
30693
30765
  retryDelay: 20,
30694
- timeout: 3000
30766
+ timeout: 5000
30695
30767
  });
30696
30768
  const [baseInfo, web_session] = await Promise.all([
30697
30769
  _baseInfo,
30698
30770
  _web_session
30699
30771
  ]);
30700
30772
  if (baseInfo?.code === 0) check.isValidSession = true;
30701
- if (0 === web_session.code) check.isValidWebSession = true;
30702
- baseInfo?.code, web_session.code;
30773
+ if (web_session?.code === 0) check.isValidWebSession = true;
30774
+ baseInfo?.code, web_session?.code;
30703
30775
  const message = `小红书账号有效性检测成功${_task.debug ? ` ${http.proxyInfo}` : ""}`;
30704
30776
  return success(check, message);
30705
30777
  };
@@ -34635,9 +34707,7 @@ var __webpack_exports__ = {};
34635
34707
  msToken: params.cookies.find((e)=>"msToken" === e.name)?.value || "",
34636
34708
  a_bogus: ""
34637
34709
  };
34638
- task.logger.warn("publishParams", {
34639
- publishParams
34640
- });
34710
+ task.logger.info(`[douyinPublish] publishParams ${JSON.stringify(publishParams)}`);
34641
34711
  const publishData = {
34642
34712
  item: {
34643
34713
  common: {
@@ -34713,21 +34783,21 @@ var __webpack_exports__ = {};
34713
34783
  }
34714
34784
  publishData.item.common.creation_id = generateRandomString(8) + Date.now();
34715
34785
  let decision = null;
34716
- task.logger.info(`proxyHttp 代理信息: ${proxyHttp.proxyInfo} `);
34786
+ task.logger.info(`[douyinPublish] proxyHttp 代理信息: ${proxyHttp.proxyInfo} `);
34717
34787
  proxyHttp.addResponseInterceptor((response)=>{
34718
34788
  console.log("拦截器收到响应:", JSON.stringify(response.data));
34719
- task.logger.info(`拦截器收到响应response.headers: ${JSON.stringify(response.headers)} `);
34720
- task.logger.info(`拦截器收到响应response.data: ${JSON.stringify(response.data)} `);
34789
+ task.logger.warn(`[douyinPublish] 拦截器收到响应response.headers: ${JSON.stringify(response.headers)} `);
34790
+ task.logger.warn(`[douyinPublish] 拦截器收到响应response.data: ${JSON.stringify(response.data)} `);
34721
34791
  decision = parseVerifyPassportDecision(response.headers["x-tt-verify-passport-decision"]);
34722
34792
  if (needsVerification(decision)) {
34723
- task.logger.info(`需要验证: ${JSON.stringify(decision)}`);
34793
+ task.logger.warn(`[douyinPublish] 检测到需要验证: ${JSON.stringify(decision)}`);
34724
34794
  return;
34725
34795
  }
34726
34796
  if (!response || !response.data) return;
34727
34797
  const responseData = response.data;
34728
34798
  if (response && responseData?.status_code && 0 !== responseData.status_code) {
34729
34799
  const errorCode = 4 === responseData.status_code ? 500 : responseData.status_code;
34730
- if (4 === responseData.status_code) task.logger.warn(`抖音服务器错误 status_code: 4,映射为 500 触发重试。原始响应: ${JSON.stringify(responseData)}`);
34800
+ if (4 === responseData.status_code) task.logger.warn(`[douyinPublish] 抖音服务器错误 status_code: 4,映射为 500 触发重试。原始响应: ${JSON.stringify(responseData)}`);
34731
34801
  return {
34732
34802
  code: errorCode,
34733
34803
  message: responseData.status_msg || "文章发布异常,请稍后重试。",
@@ -34747,42 +34817,120 @@ var __webpack_exports__ = {};
34747
34817
  });
34748
34818
  return utils_response(0, message, data);
34749
34819
  }
34750
- const webProtectData = JSON.parse(JSON.parse(params.extraParam["security-sdk/s_sdk_sign_data_key/web_protect"] || "{}").data || "{}");
34751
- const ticket = webProtectData.ticket;
34752
- const ts_sign = webProtectData.ts_sign;
34753
- const ec_privateKey = JSON.parse(JSON.parse(params.extraParam["security-sdk/s_sdk_crypt_sdk"] || "{}").data || "{}").ec_privateKey;
34754
- const certificate = JSON.parse(params.extraParam["security-sdk/s_sdk_server_cert_key"] || "{}").cert;
34820
+ let webProtectData;
34821
+ try {
34822
+ webProtectData = JSON.parse(JSON.parse(params.extraParam["security-sdk/s_sdk_sign_data_key/web_protect"] || "{}").data || "{}");
34823
+ if (!webProtectData.ticket || !webProtectData.ts_sign || !webProtectData.client_cert) {
34824
+ task.logger.error(`webProtectData 关键字段缺失: ${JSON.stringify(webProtectData)}`);
34825
+ return utils_response(414, "安全参数 webProtectData 不完整,请重新获取后重试", "");
34826
+ }
34827
+ } catch (error) {
34828
+ task.logger.error(`解析 webProtectData 失败: ${error}`);
34829
+ return utils_response(414, "安全参数 webProtectData 解析失败,请重新获取后重试", "");
34830
+ }
34831
+ let ticket = webProtectData.ticket;
34832
+ let ts_sign = webProtectData.ts_sign;
34833
+ const serverDataCookie = params.cookies.find((it)=>"bd_ticket_guard_server_data" === it.name)?.value;
34834
+ if (serverDataCookie) try {
34835
+ const decoded = JSON.parse(Buffer.from(decodeURIComponent(serverDataCookie), "base64").toString("utf8"));
34836
+ if (decoded.ticket && decoded.ts_sign) {
34837
+ if (decoded.ticket !== ticket) task.logger.info("[douyinPublish] 使用 cookie 中的最新 ticket(web_protect 已过期)");
34838
+ ticket = decoded.ticket;
34839
+ ts_sign = decoded.ts_sign;
34840
+ }
34841
+ } catch (error) {
34842
+ task.logger.warn(`解析 bd_ticket_guard_server_data 失败,回退到 web_protect: ${error}`);
34843
+ }
34844
+ let ec_privateKey;
34845
+ try {
34846
+ ec_privateKey = JSON.parse(JSON.parse(params.extraParam["security-sdk/s_sdk_crypt_sdk"] || "{}").data || "{}").ec_privateKey;
34847
+ if (!ec_privateKey) {
34848
+ task.logger.error("ec_privateKey 为空");
34849
+ return utils_response(414, "安全参数 ec_privateKey 缺失,请重新获取后重试", "");
34850
+ }
34851
+ } catch (error) {
34852
+ task.logger.error(`解析 ec_privateKey 失败: ${error}`);
34853
+ return utils_response(414, "安全参数 ec_privateKey 解析失败,请重新获取后重试", "");
34854
+ }
34855
+ let certificate;
34856
+ try {
34857
+ certificate = JSON.parse(params.extraParam["security-sdk/s_sdk_server_cert_key"] || "{}").cert;
34858
+ if (!certificate) {
34859
+ task.logger.error("certificate 为空");
34860
+ return utils_response(414, "安全参数 certificate 缺失,请重新获取后重试", "");
34861
+ }
34862
+ } catch (error) {
34863
+ task.logger.error(`解析 certificate 失败: ${error}`);
34864
+ return utils_response(414, "安全参数 certificate 解析失败,请重新获取后重试", "");
34865
+ }
34755
34866
  const ree_public_key = webProtectData.client_cert.replace("pub.", "");
34756
- task.logger.info(`生成 bdTicketGuardClientData 的参数: ticket: ${ticket}, ts_sign: ${ts_sign}, ec_privateKey: ${ec_privateKey}, certificate: ${certificate}, ree_public_key: ${ree_public_key}`);
34757
- const bdTicketGuardClientData = getBdV2({
34758
- ticket,
34759
- ts_sign: ts_sign,
34760
- ec_privateKey: ec_privateKey,
34761
- certificate: certificate,
34762
- bd_ticket_guard_ree_public_key: ree_public_key
34763
- });
34764
- task.logger.info("bdTicketGuardClientData", {
34765
- bdTicketGuardClientData
34766
- });
34867
+ task.logger.info(`生成 bdTicketGuardClientData 的参数: ticket: ${ticket?.substring(0, 20)}..., ts_sign: ${ts_sign}, ree_public_key: ${ree_public_key?.substring(0, 20)}...`);
34868
+ let bdTicketGuardClientData;
34869
+ try {
34870
+ bdTicketGuardClientData = getBdV2({
34871
+ ticket,
34872
+ ts_sign: ts_sign,
34873
+ ec_privateKey: ec_privateKey,
34874
+ certificate: certificate,
34875
+ bd_ticket_guard_ree_public_key: ree_public_key
34876
+ });
34877
+ if (!bdTicketGuardClientData || !bdTicketGuardClientData["headers_bd_ticket_guard_client_data"]) {
34878
+ task.logger.error(`bdTicketGuardClientData 生成失败或不完整: ${JSON.stringify(bdTicketGuardClientData)}`);
34879
+ return utils_response(414, "安全参数 bdTicketGuardClientData 生成失败,请重新获取后重试", "");
34880
+ }
34881
+ } catch (error) {
34882
+ task.logger.error(`生成 bdTicketGuardClientData 失败: ${error}`);
34883
+ return utils_response(414, "安全参数 bdTicketGuardClientData 生成异常,请重新获取后重试", "");
34884
+ }
34885
+ task.logger.info("bdTicketGuardClientData 生成成功");
34767
34886
  const publishQuery = {
34768
34887
  ...publishParams,
34769
34888
  a_bogus: ""
34770
34889
  };
34771
34890
  const queryString = new URLSearchParams(publishQuery).toString();
34772
- const aBogus = mock_getABogus(`https://creator.douyin.com/web/api/media/aweme/create_v2/?${queryString}`, publishData, userAgent);
34891
+ let aBogus;
34892
+ try {
34893
+ aBogus = mock_getABogus(`https://creator.douyin.com/web/api/media/aweme/create_v2/?${queryString}`, publishData, userAgent);
34894
+ if (!aBogus || aBogus.length < 10) {
34895
+ task.logger.error(`a_bogus 生成异常,长度过短: ${aBogus}`);
34896
+ return utils_response(414, "安全参数 a_bogus 生成失败,请重试", "");
34897
+ }
34898
+ task.logger.info(`a_bogus 生成成功: ${aBogus.substring(0, 20)}...`);
34899
+ } catch (error) {
34900
+ task.logger.error(`生成 a_bogus 失败: ${error}`);
34901
+ return utils_response(414, "安全参数 a_bogus 生成异常,请重试", "");
34902
+ }
34773
34903
  publishQuery.a_bogus = aBogus;
34774
34904
  const publishQueryParams = new URLSearchParams(publishQuery).toString();
34775
- const csrfToken = mock_generateCsrfTokenAdvanced({
34776
- cookies: params.cookies,
34777
- url: "https://creator.douyin.com/web/api/media/aweme/create_v2/",
34778
- method: "POST",
34779
- userAgent
34780
- });
34781
- const sessionDtrait = mock_generateDtrait("/web/api/media/aweme/create_v2/");
34782
- task.logger.info("发布数据", {
34905
+ let csrfToken;
34906
+ try {
34907
+ csrfToken = mock_generateCsrfTokenAdvanced({
34908
+ cookies: params.cookies,
34909
+ url: "https://creator.douyin.com/web/api/media/aweme/create_v2/",
34910
+ method: "POST",
34911
+ userAgent
34912
+ });
34913
+ if (!csrfToken || csrfToken.length < 10) {
34914
+ task.logger.error(`csrfToken 生成异常,长度过短: ${csrfToken}`);
34915
+ return utils_response(414, "安全参数 csrfToken 生成失败,请重试", "");
34916
+ }
34917
+ task.logger.info(`csrfToken 生成成功: ${csrfToken.substring(0, 20)}...`);
34918
+ } catch (error) {
34919
+ task.logger.error(`生成 csrfToken 失败: ${error}`);
34920
+ return utils_response(414, "安全参数 csrfToken 生成异常,请重试", "");
34921
+ }
34922
+ let sessionDtrait;
34923
+ try {
34924
+ sessionDtrait = mock_generateDtrait("/web/api/media/aweme/create_v2/");
34925
+ task.logger.info(`sessionDtrait 生成成功: ${sessionDtrait || "(空)"}`);
34926
+ } catch (error) {
34927
+ task.logger.error(`生成 sessionDtrait 失败: ${error}`);
34928
+ return utils_response(414, "安全参数 sessionDtrait 生成异常,请重试", "");
34929
+ }
34930
+ task.logger.info("[douyinPublish] 发布数据", {
34783
34931
  data: JSON.stringify(publishData)
34784
34932
  });
34785
- task.logger.info(`headers: ${JSON.stringify({
34933
+ task.logger.info(`[douyinPublish] headers: ${JSON.stringify({
34786
34934
  ...headers,
34787
34935
  Referer: "https://creator.douyin.com/creator-micro/content/post/image?default-tab=3&enter_from=publish_page&media_type=image&type=new",
34788
34936
  "Content-Type": "application/json",
@@ -34795,8 +34943,7 @@ var __webpack_exports__ = {};
34795
34943
  "x-secsdk-csrf-token": csrfToken,
34796
34944
  "x-tt-session-dtrait": sessionDtrait || ""
34797
34945
  })}`);
34798
- task.logger.info(`publishData: ${JSON.stringify(publishData)}`);
34799
- task.logger.info(`url: https://creator.douyin.com/web/api/media/aweme/create_v2/?${publishQueryParams}`);
34946
+ task.logger.info(`[douyinPublish] url: https://creator.douyin.com/web/api/media/aweme/create_v2/?${publishQueryParams}`);
34800
34947
  const publishResult = await proxyHttp.api({
34801
34948
  method: "post",
34802
34949
  url: `https://creator.douyin.com/web/api/media/aweme/create_v2/?${publishQueryParams}`,
@@ -34820,8 +34967,7 @@ var __webpack_exports__ = {};
34820
34967
  retries: 3,
34821
34968
  retryDelay: 2000
34822
34969
  });
34823
- task.logger.info("========== api调用完成 ==========");
34824
- task.logger.info(`decision值: ${JSON.stringify(decision)}, needsVerification(decision): ${needsVerification(decision)}`);
34970
+ task.logger.info(`[douyinPublish] decision值: ${JSON.stringify(decision)}, needsVerification(decision): ${needsVerification(decision)}`);
34825
34971
  if (needsVerification(decision)) {
34826
34972
  const details = [
34827
34973
  publishResult.status_msg,
@@ -34829,7 +34975,6 @@ var __webpack_exports__ = {};
34829
34975
  decision?.verify_desc
34830
34976
  ].filter(Boolean).join(" ");
34831
34977
  const message = `图文发布失败,原因:${details}${task.debug ? ` ${http.proxyInfo}` : ""}`;
34832
- task.logger.warn(`TaskId:${task.taskId},检测到需要验证,准备返回验证信息`);
34833
34978
  let decisionObj = {};
34834
34979
  if (decision) decisionObj = decision;
34835
34980
  const mockData = {
@@ -34848,7 +34993,6 @@ var __webpack_exports__ = {};
34848
34993
  message: "操作成功"
34849
34994
  };
34850
34995
  }
34851
- task.logger.info("不需要验证,继续正常流程");
34852
34996
  reportLogger({
34853
34997
  token: params.huiwenToken || "",
34854
34998
  enverionment: task.enverionment || "development",
@@ -34860,8 +35004,7 @@ var __webpack_exports__ = {};
34860
35004
  platform: "douyin",
34861
35005
  publishParams: publishData
34862
35006
  });
34863
- task.logger.warn("发布结果");
34864
- task.logger.warn(JSON.stringify(publishResult));
35007
+ task.logger.info(`[douyinPublish] 发布结果 ${JSON.stringify(publishResult)}`);
34865
35008
  const isSuccess = 0 === publishResult.status_code;
34866
35009
  const message = `图文发布${isSuccess ? "成功" : `失败,原因:${publishResult.status_msg} ${decision?.verify_title} ${decision?.verify_desc}`}${task.debug ? ` ${http.proxyInfo}` : ""}`;
34867
35010
  const data = isSuccess ? publishResult.item_id || "" : "";
@@ -35702,6 +35845,7 @@ var __webpack_exports__ = {};
35702
35845
  uploadedImgList: classic_schemas_string().optional()
35703
35846
  });
35704
35847
  const douyinPublish = async (task, params)=>{
35848
+ task.logger.info(`douyinPublish actionType: ${params.actionType}`);
35705
35849
  if ("rpa" === params.actionType) return douyinPublish_rpa_rpaAction(task, params);
35706
35850
  if ("mockApi" === params.actionType) return mock_mockAction(task, params);
35707
35851
  if ("server" === params.actionType) return rpaAction_Server(task, params);
@@ -39991,7 +40135,7 @@ var __webpack_exports__ = {};
39991
40135
  ]).optional()
39992
40136
  });
39993
40137
  const shipinhaoPublish = async (task, params)=>{
39994
- console.log("shipinhaoPublish params:", params);
40138
+ task.logger.info(`shipinhaoPublish actionType: ${params.actionType}`);
39995
40139
  if ("rpa" === params.actionType) return shipinhaoPublish_rpa_rpaAction(task, params);
39996
40140
  if ("mockApi" === params.actionType) return shipinhaoPublish_mock_mockAction(task, params);
39997
40141
  if ("server" === params.actionType) return rpa_server_rpaAction_Server(task, params);
@@ -41049,6 +41193,7 @@ var __webpack_exports__ = {};
41049
41193
  };
41050
41194
  const getAddTypeValue = (toutiaoAd)=>"yes" === toutiaoAd ? 3 : 2;
41051
41195
  const toutiaoPublish = async (task, params)=>{
41196
+ task.logger.info(`toutiaoPublish actionType: ${params.actionType}`);
41052
41197
  params.content = formatSectionHtml(params.content);
41053
41198
  if ("rpa" === params.actionType) return toutiaoPublish_rpa_rpaAction(task, params);
41054
41199
  if ("mockApi" === params.actionType) return toutiaoPublish_mock_mockAction(task, params);
@@ -43385,6 +43530,33 @@ var __webpack_exports__ = {};
43385
43530
  const encode_mnsv2 = __webpack_require__("./src/utils/xhs_ob/x_s.encoder.js");
43386
43531
  const xiaohongshuLogin_rpa_server_scanRetryMaxCount = 60;
43387
43532
  const xiaohongshuLogin_rpa_server_waitQrcodeResultMaxTime = 2000 * xiaohongshuLogin_rpa_server_scanRetryMaxCount;
43533
+ async function collectCookiesWithA1(task) {
43534
+ const hasA1 = (cookies)=>cookies.some((c)=>"a1" === c.name && !!c.value);
43535
+ let cookies = await task.steelBrowserContext?.cookies() ?? [];
43536
+ if (hasA1(cookies)) return cookies;
43537
+ task.logger?.warn("[XhsLogin] 首次抓取缺失 a1,尝试补救……");
43538
+ try {
43539
+ const page = task.steelBrowserContext?.pages?.()[0];
43540
+ if (page) {
43541
+ await page.goto("https://www.xiaohongshu.com", {
43542
+ waitUntil: "domcontentloaded",
43543
+ timeout: 15000
43544
+ });
43545
+ for(let i = 0; i < 10; i++){
43546
+ cookies = await task.steelBrowserContext?.cookies() ?? [];
43547
+ if (hasA1(cookies)) {
43548
+ task.logger?.info(`[XhsLogin] a1 补救成功,第 ${i + 1} 次轮询命中`);
43549
+ return cookies;
43550
+ }
43551
+ await new Promise((resolve)=>setTimeout(resolve, 500));
43552
+ }
43553
+ }
43554
+ } catch (err) {
43555
+ task.logger?.warn("[XhsLogin] a1 补救访问主站失败", err);
43556
+ }
43557
+ cookies = await task.steelBrowserContext?.cookies() ?? [];
43558
+ return cookies;
43559
+ }
43388
43560
  const xiaohongshuLogin_rpa_server_rpaServer = async (task, params)=>{
43389
43561
  const updateTaskState = task.taskStageStore?.update?.bind(task.taskStageStore, task.taskId || "");
43390
43562
  const reporter = task.reportService?.reportLoginStatus ?? (()=>Promise.resolve());
@@ -43585,21 +43757,29 @@ var __webpack_exports__ = {};
43585
43757
  };
43586
43758
  }
43587
43759
  case types_ExecutionState.SUCCESS:
43588
- await updateTaskState?.({
43589
- state: types_TaskState.SUCCESS,
43590
- result: {
43591
- cookie: JSON.stringify(await task.steelBrowserContext?.cookies()),
43592
- userInfo: userInfo
43593
- }
43594
- });
43595
- return {
43596
- code: 0,
43597
- message: "成功",
43598
- data: {
43599
- cookie: JSON.stringify(await task.steelBrowserContext?.cookies()),
43600
- userInfo
43601
- }
43602
- };
43760
+ {
43761
+ const cookies = await collectCookiesWithA1(task);
43762
+ const hasA1 = cookies.some((c)=>"a1" === c.name && !!c.value);
43763
+ if (!hasA1) task.logger?.warn("[XhsLogin] 登录成功但缺失关键 cookie a1,后续检测可能失败", {
43764
+ cookieNames: cookies.map((c)=>c.name)
43765
+ });
43766
+ const cookieStr = JSON.stringify(cookies);
43767
+ await updateTaskState?.({
43768
+ state: types_TaskState.SUCCESS,
43769
+ result: {
43770
+ cookie: cookieStr,
43771
+ userInfo: userInfo
43772
+ }
43773
+ });
43774
+ return {
43775
+ code: 0,
43776
+ message: "成功",
43777
+ data: {
43778
+ cookie: cookieStr,
43779
+ userInfo
43780
+ }
43781
+ };
43782
+ }
43603
43783
  default:
43604
43784
  return {
43605
43785
  code: 500,
@@ -43800,6 +43980,24 @@ var __webpack_exports__ = {};
43800
43980
  const fileName = getFilenameFromUrl(url);
43801
43981
  const localUrl = await downloadImage(url, external_node_path_default().join(tmpCachePath, fileName));
43802
43982
  const fileBuffer = external_node_fs_default().readFileSync(localUrl);
43983
+ let width = 0;
43984
+ let height = 0;
43985
+ try {
43986
+ const dimensions = imageSize(fileBuffer);
43987
+ width = dimensions.width ?? 0;
43988
+ height = dimensions.height ?? 0;
43989
+ const orientation = dimensions.orientation ?? 1;
43990
+ if ([
43991
+ 5,
43992
+ 6,
43993
+ 7,
43994
+ 8
43995
+ ].includes(orientation)) [width, height] = [
43996
+ height,
43997
+ width
43998
+ ];
43999
+ } catch {}
44000
+ const originSize = fileBuffer.byteLength / 1024;
43803
44001
  const MAX_RETRIES = uploadInfos.length;
43804
44002
  let attempt = 0;
43805
44003
  while(attempt < MAX_RETRIES){
@@ -43821,7 +44019,10 @@ var __webpack_exports__ = {};
43821
44019
  });
43822
44020
  return {
43823
44021
  ossFileId,
43824
- ossToken
44022
+ ossToken,
44023
+ width,
44024
+ height,
44025
+ originSize
43825
44026
  };
43826
44027
  } catch (error) {
43827
44028
  attempt++;
@@ -43829,7 +44030,10 @@ var __webpack_exports__ = {};
43829
44030
  }
43830
44031
  return {
43831
44032
  ossFileId: "",
43832
- ossToken: ""
44033
+ ossToken: "",
44034
+ width,
44035
+ height,
44036
+ originSize
43833
44037
  };
43834
44038
  };
43835
44039
  const coverInfos = await Promise.all(params.banners.map((it, idx)=>uploadFile(it, idx)));
@@ -43894,8 +44098,16 @@ var __webpack_exports__ = {};
43894
44098
  },
43895
44099
  image_info: {
43896
44100
  images: coverInfos.map((it)=>({
43897
- extra_info_json: '{"mimeType":"image/png"}',
44101
+ extra_info_json: JSON.stringify({
44102
+ mimeType: "image/png",
44103
+ image_metadata: {
44104
+ bg_color: "",
44105
+ origin_size: it.originSize
44106
+ }
44107
+ }),
43898
44108
  file_id: it.ossFileId,
44109
+ width: it.width,
44110
+ height: it.height,
43899
44111
  metadata: {
43900
44112
  source: -1
43901
44113
  },
@@ -44002,6 +44214,7 @@ var __webpack_exports__ = {};
44002
44214
  });
44003
44215
  return success(data, message);
44004
44216
  }
44217
+ task.logger.info(`[xiaohongshuPublish] publishData: ${JSON.stringify(publishData)} `);
44005
44218
  const publishResult = await proxyHttp.api({
44006
44219
  method: "post",
44007
44220
  url: "https://edith.xiaohongshu.com/web_api/sns/v2/note",
@@ -45111,6 +45324,7 @@ var __webpack_exports__ = {};
45111
45324
  originalBind: classic_schemas_boolean().optional()
45112
45325
  });
45113
45326
  const xiaohongshuPublish = async (task, params)=>{
45327
+ task.logger.info(`xiaohongshuPublish actionType: ${params.actionType}`);
45114
45328
  if (DisabledReq) return {
45115
45329
  code: 414,
45116
45330
  data: "",