@7365admin1/core 3.133.0 → 3.134.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/index.mjs CHANGED
@@ -63571,6 +63571,17 @@ var ROBOT_CLOUD_PATHS = {
63571
63571
  workHours: "/portal/workhours/get-work-hours",
63572
63572
  haltPlans: "/portal/halt-plan/get",
63573
63573
  stationState: "/portal/detailstate/get-station-detail-state",
63574
+ // Read-only map layers and logs (2026-09-30: every read in the document is used).
63575
+ wallList: "/portal/maps/get-wall-list",
63576
+ safeZoneList: "/portal/maps/get-safezone-list",
63577
+ slowZoneList: "/portal/maps/get-slowzone-list",
63578
+ obstacleLayer: "/portal/obstacles/get-obstacle-layer",
63579
+ teachTrack: "/portal/teach/get-teach-track",
63580
+ mapVersions: "/portal/maps/get-map-version-list",
63581
+ floorMapHistory: "/portal/maps/v2405/get-floor-maplist",
63582
+ robotLog: "/portal/report/get-robot-log-list",
63583
+ userLog: "/portal/userlog/get-user-logs",
63584
+ cleaningSetting: "/portal/setting/get-cleaning-setting",
63574
63585
  mapList: "/portal/maps/get-map-list",
63575
63586
  fileUrl: "/portal/maps/get-file-url",
63576
63587
  tracking: "/portal/robots/tracking",
@@ -63871,7 +63882,17 @@ var STEP_NAMES = {
63871
63882
  [ROBOT_CLOUD_PATHS.haltPlans]: "the power schedule",
63872
63883
  [ROBOT_CLOUD_PATHS.stationState]: "the base station state",
63873
63884
  [ROBOT_CLOUD_PATHS.alertList]: "the alert history",
63874
- [ROBOT_CLOUD_PATHS.liftList]: "the lift list"
63885
+ [ROBOT_CLOUD_PATHS.liftList]: "the lift list",
63886
+ [ROBOT_CLOUD_PATHS.wallList]: "the virtual walls",
63887
+ [ROBOT_CLOUD_PATHS.safeZoneList]: "the safe zones",
63888
+ [ROBOT_CLOUD_PATHS.slowZoneList]: "the slow zones",
63889
+ [ROBOT_CLOUD_PATHS.obstacleLayer]: "the obstacle layer",
63890
+ [ROBOT_CLOUD_PATHS.teachTrack]: "the taught route",
63891
+ [ROBOT_CLOUD_PATHS.mapVersions]: "the map versions",
63892
+ [ROBOT_CLOUD_PATHS.floorMapHistory]: "the floor's map history",
63893
+ [ROBOT_CLOUD_PATHS.robotLog]: "the robot status log",
63894
+ [ROBOT_CLOUD_PATHS.userLog]: "the app action log",
63895
+ [ROBOT_CLOUD_PATHS.cleaningSetting]: "the robot settings"
63875
63896
  };
63876
63897
  var robotCloudStepName = (path5) => STEP_NAMES[path5] ?? path5;
63877
63898
  var SUCCESS_CODES = /* @__PURE__ */ new Set(["0", "200"]);
@@ -64091,6 +64112,40 @@ function useRobotCloudService(credentials, options = {}) {
64091
64112
  );
64092
64113
  return data.state ?? null;
64093
64114
  }
64115
+ async function getMapShapes(kind, mapId) {
64116
+ const [path5, list] = kind === "walls" ? [ROBOT_CLOUD_PATHS.wallList, "wallList"] : kind === "safe" ? [ROBOT_CLOUD_PATHS.safeZoneList, "safeZoneList"] : [ROBOT_CLOUD_PATHS.slowZoneList, "slowZoneList"];
64117
+ const data = await post(path5, { mapId }, list);
64118
+ return Array.isArray(data[list]) ? data[list] : [];
64119
+ }
64120
+ async function getObstacleLayer(robotId) {
64121
+ return post(ROBOT_CLOUD_PATHS.obstacleLayer, { robotId, version: 0 });
64122
+ }
64123
+ async function getTeachTrack(robotId, offset) {
64124
+ return post(ROBOT_CLOUD_PATHS.teachTrack, { robotId, offset }, "trackList");
64125
+ }
64126
+ async function getMapVersions(mapId) {
64127
+ return post(ROBOT_CLOUD_PATHS.mapVersions, { mapId }, "versionList");
64128
+ }
64129
+ async function getFloorMapHistory(sceneId, floorNo2) {
64130
+ return post(ROBOT_CLOUD_PATHS.floorMapHistory, { sceneId, floorNo: floorNo2 }, "mapList");
64131
+ }
64132
+ async function getRobotLog(robotId, sceneId, timeFrom, timeTo) {
64133
+ return post(
64134
+ ROBOT_CLOUD_PATHS.robotLog,
64135
+ { robotId: String(robotId), sceneId: String(sceneId), timeFrom, timeTo, key: "", pageNo: 1, pageSize: 50 },
64136
+ "logList"
64137
+ );
64138
+ }
64139
+ async function getUserLogs(robotId, startTime, endTime) {
64140
+ return post(
64141
+ ROBOT_CLOUD_PATHS.userLog,
64142
+ { robotId, pageNo: 1, pageSize: 50, startTime, endTime, keyword: "" },
64143
+ "actionList"
64144
+ );
64145
+ }
64146
+ async function getCleaningSetting(robotId) {
64147
+ return post(ROBOT_CLOUD_PATHS.cleaningSetting, { robotId });
64148
+ }
64094
64149
  async function getMaps(robotSn) {
64095
64150
  const data = await post(
64096
64151
  ROBOT_CLOUD_PATHS.mapList,
@@ -64176,6 +64231,14 @@ function useRobotCloudService(credentials, options = {}) {
64176
64231
  getHaltPlans,
64177
64232
  getStationState,
64178
64233
  getLiftList,
64234
+ getMapShapes,
64235
+ getObstacleLayer,
64236
+ getTeachTrack,
64237
+ getMapVersions,
64238
+ getFloorMapHistory,
64239
+ getRobotLog,
64240
+ getUserLogs,
64241
+ getCleaningSetting,
64179
64242
  getMaps,
64180
64243
  getFileUrls,
64181
64244
  getPlans,
@@ -64370,22 +64433,48 @@ function ounitechFault(list) {
64370
64433
  return { code: "error", message: String(list[0]).slice(0, 200) };
64371
64434
  return { code: "error", message: "The robot reports an error" };
64372
64435
  }
64373
- function ounitechMapShare(map, x, y) {
64436
+ function ounitechMapShare(map, x, y, clamp4 = false) {
64374
64437
  const w = map?.width, h = map?.height, r = map?.resolution;
64375
64438
  const wx = num(x), wy = num(y);
64376
64439
  if (!finite(w) || !finite(h) || !finite(r) || w <= 0 || h <= 0 || r <= 0 || wx === void 0 || wy === void 0)
64377
64440
  return null;
64378
- const sx = (wx - (num(map?.originX) ?? 0)) / r / w * 100;
64379
- const sy = 100 - (wy - (num(map?.originY) ?? 0)) / r / h * 100;
64441
+ let sx = (wx - (num(map?.originX) ?? 0)) / r / w * 100;
64442
+ let sy = 100 - (wy - (num(map?.originY) ?? 0)) / r / h * 100;
64443
+ if (clamp4)
64444
+ sx = Math.min(100, Math.max(0, sx)), sy = Math.min(100, Math.max(0, sy));
64380
64445
  if (sx < 0 || sx > 100 || sy < 0 || sy > 100)
64381
64446
  return null;
64382
64447
  return { x: Math.round(sx * 100) / 100, y: Math.round(sy * 100) / 100 };
64383
64448
  }
64384
- function ounitechMapView(m, imageUrl, partitionImageUrl, size) {
64449
+ var SHAPE_WORDS = { wall: "Virtual wall", safe: "Safe zone", slow: "Slow zone" };
64450
+ function ounitechShapes(map, kind, list) {
64451
+ return (Array.isArray(list) ? list : []).flatMap((z5, i) => {
64452
+ const points = (Array.isArray(z5?.pointList) ? z5.pointList : []).flatMap((p) => {
64453
+ const at2 = Array.isArray(p) ? ounitechMapShare(map, p[0], p[1], true) : null;
64454
+ return at2 ? [at2] : [];
64455
+ });
64456
+ const name = String(z5?.wallName ?? z5?.zoneName ?? "").trim();
64457
+ return points.length >= 2 ? [{ kind, name: name || `${SHAPE_WORDS[kind]} ${i + 1}`, points }] : [];
64458
+ });
64459
+ }
64460
+ function ounitechTrack(map, list) {
64461
+ const on = (Array.isArray(list) ? list : []).filter((p) => p && (p.mapid == null || String(p.mapid) === map?.mapId));
64462
+ const step = Math.max(1, Math.ceil(on.length / 500));
64463
+ return on.filter((_, i) => i % step === 0).flatMap((p) => {
64464
+ const at2 = ounitechMapShare(map, p.x, p.y, true);
64465
+ return at2 ? [at2] : [];
64466
+ });
64467
+ }
64468
+ function ounitechMapView(m, imageUrl, partitionImageUrl, size, shapes = {}) {
64385
64469
  const floorNo2 = Number.isInteger(m.floorNo) ? m.floorNo : null;
64386
64470
  const width = size?.width ?? null;
64387
64471
  const height = size?.height ?? null;
64388
64472
  const frame2 = { width, height, resolution: m.resolution, originX: m.originX, originY: m.originY };
64473
+ const zones = [
64474
+ ...ounitechShapes(frame2, "wall", Array.isArray(shapes.walls) && shapes.walls.length ? shapes.walls : m.wallList),
64475
+ ...ounitechShapes(frame2, "safe", shapes.safe),
64476
+ ...ounitechShapes(frame2, "slow", shapes.slow)
64477
+ ];
64389
64478
  const areas = (Array.isArray(m.areaList) ? m.areaList : []).filter((a) => typeof a?.areaName === "string" && a.areaName.trim()).map((a) => {
64390
64479
  const px = num(a.x), py = num(a.y);
64391
64480
  const at2 = width && height && px !== void 0 && py !== void 0 && (px > 0 || py > 0) && px <= width && py <= height ? { x: Math.round(px / width * 1e4) / 100, y: Math.round(py / height * 1e4) / 100 } : null;
@@ -64415,7 +64504,11 @@ function ounitechMapView(m, imageUrl, partitionImageUrl, size) {
64415
64504
  positionApproximate: true,
64416
64505
  // The raw areas, kept for older screens.
64417
64506
  areaList: areas.map(({ at: _at, ...a }) => a),
64418
- areas: areas.map((a) => ({ name: a.areaName, at: a.at }))
64507
+ areas: areas.map((a) => ({ name: a.areaName, at: a.at })),
64508
+ /** Virtual walls (the robot never crosses), safe zones and slow zones, drawn on the map. */
64509
+ zones,
64510
+ /** The route the robot was taught (get-teach-track), set per robot by getMaps. */
64511
+ taughtRoute: []
64419
64512
  };
64420
64513
  }
64421
64514
  function ounitechCurrentMap(maps, taskMapId, floorNo2) {
@@ -64487,7 +64580,12 @@ function ounitechTaskRecord(t, maps = [], tz = 480) {
64487
64580
  };
64488
64581
  }
64489
64582
  var ALERT_WORDS = {
64583
+ "205": "Side brush driver offline",
64584
+ "206": "Button panel offline",
64490
64585
  "540": "Floor check: cliff sensor switched on",
64586
+ "588": "Switched off with the power button",
64587
+ "589": "Switched off by the timed power schedule",
64588
+ "593": "Still finding its position - try again shortly",
64491
64589
  "601": "Left wheel driver reset",
64492
64590
  "620": "Right wheel driver offline",
64493
64591
  "621": "Right wheel driver reset",
@@ -64508,7 +64606,8 @@ function ounitechAlertRecord(a, tz = 480) {
64508
64606
  return {
64509
64607
  code,
64510
64608
  level: lv ? ALERT_LEVEL_WORDS[lv[1].trim()] ?? lv[1].trim() : null,
64511
- message: ALERT_WORDS[code] ?? (rest || raw),
64609
+ // An untranslated Chinese text keeps its code up front, so the row is never only Chinese.
64610
+ message: ALERT_WORDS[code] ?? (/[㐀-鿿]/.test(rest || raw) && code ? `Robot alert ${code}: ${rest || raw}` : rest || raw),
64512
64611
  vendorText: rest || raw,
64513
64612
  resolved,
64514
64613
  at: ounitechTime(a.createTime, tz)
@@ -64618,11 +64717,12 @@ var PART_WORDS = {
64618
64717
  floor_brush_double_roller_structure: "Floor brush rollers",
64619
64718
  floor_mop_double_roller_structure: "Mop rollers"
64620
64719
  };
64720
+ var upFirst = (t) => t.charAt(0).toUpperCase() + t.slice(1);
64621
64721
  function ounitechConsumable(u) {
64622
64722
  const code = String(u.unitcode ?? "").trim();
64623
64723
  const minutes = num(u.workminutes);
64624
64724
  return {
64625
- part: PART_WORDS[code] ?? (code.replace(/_/g, " ") || String(u.unitname ?? "").trim() || "Part"),
64725
+ part: PART_WORDS[code] ?? upFirst(code.replace(/_/g, " ") || String(u.unitname ?? "").trim() || "Part"),
64626
64726
  hours: minutes !== void 0 ? Math.round(minutes / 6) / 10 : null,
64627
64727
  days: num(u.workdays) ?? null
64628
64728
  };
@@ -64635,10 +64735,115 @@ function ounitechPowerPlan(p) {
64635
64735
  enabled: p.enableFlag !== false
64636
64736
  };
64637
64737
  }
64738
+ function ounitechStatusLog(l, tz = 480) {
64739
+ const code = num(l.typeFlag);
64740
+ const words = code !== void 0 ? ROBOT_STATUS_NAMES[code] : void 0;
64741
+ return {
64742
+ at: ounitechTime(l.timeFrom, tz),
64743
+ status: words ? code === 15 || code === 16 ? `${words} (mid-job)` : words : String(l.typeName ?? "").trim() || `Status ${l.typeFlag ?? "?"}`
64744
+ };
64745
+ }
64746
+ var ACTION_WORDS = {
64747
+ \u539F\u5730\u505C\u6B62: "Stopped in place",
64748
+ \u4E0B\u53D1\u6E05\u6D01: "Started a cleaning job",
64749
+ \u793A\u6559\u8DEF\u5F84\u63A7\u5236: "Controlled a taught route",
64750
+ \u6682\u505C: "Paused",
64751
+ \u7EE7\u7EED: "Resumed",
64752
+ \u56DE\u5145: "Sent back to charge",
64753
+ \u7ED3\u675F\u6E05\u6D01: "Ended the cleaning job",
64754
+ \u5F00\u673A: "Switched on",
64755
+ \u5173\u673A: "Switched off"
64756
+ };
64757
+ function ounitechAppAction(a, tz = 480) {
64758
+ const raw = String(a.actionName ?? "").trim();
64759
+ return {
64760
+ at: ounitechTime(a.createTime, tz),
64761
+ action: ACTION_WORDS[raw] ?? (raw ? /[㐀-鿿]/.test(raw) ? `App action: ${raw}` : raw : "App action"),
64762
+ by: String(a.userName ?? "").trim() || null
64763
+ };
64764
+ }
64765
+ function ounitechMapVersion(v, tz = 480) {
64766
+ return { version: num(v.versionNo) ?? null, latest: v.latestFlag === true, createdAt: ounitechTime(v.createTime, tz) };
64767
+ }
64768
+ function ounitechFloorMapHistory(m, tz = 480) {
64769
+ const area = num(m.totalArea);
64770
+ return {
64771
+ name: String(m.mapName ?? "").trim() || `Map ${m.mapId ?? ""}`.trim(),
64772
+ areaM2: area !== void 0 ? Math.round(area * 10) / 10 : null,
64773
+ latest: m.latestFlag === true,
64774
+ inUse: m.enableFlag === true,
64775
+ createdAt: ounitechTime(m.createTime, tz),
64776
+ updatedAt: ounitechTime(m.updateTime, tz)
64777
+ };
64778
+ }
64779
+ var SETTINGS = {
64780
+ soundLevel: { group: "Sound", label: "Sound level", unit: "%" },
64781
+ enableWorkSound: { group: "Sound", label: "Sounds while working" },
64782
+ clean_speed_mode: { group: "Cleaning", label: "Cleaning speed" },
64783
+ fanLevel: { group: "Cleaning", label: "Suction level" },
64784
+ waterGear: { group: "Cleaning", label: "Water level" },
64785
+ planningWidth: { group: "Cleaning", label: "Cleaning path width" },
64786
+ alongWallFlag: { group: "Cleaning", label: "Edge cleaning" },
64787
+ alongWallDistance: { group: "Cleaning", label: "Edge distance" },
64788
+ enablePlanFlag: { group: "Cleaning", label: "Schedules switched on" },
64789
+ slowZoneSpeed: { group: "Cleaning", label: "Speed in slow zones", unit: "m/s" },
64790
+ minCleanBatteryPerc: { group: "Battery", label: "Lowest battery to start cleaning", unit: "%" },
64791
+ normalCleanBatteryPerc: { group: "Battery", label: "Normal cleaning battery", unit: "%" },
64792
+ backChargeThreshold: { group: "Battery", label: "Return-to-charge battery level", unit: "%" },
64793
+ chargeCompIntervalDay: { group: "Battery", label: "Full charge every", unit: "days" },
64794
+ obsAvoidSens: { group: "Safety", label: "Obstacle avoidance sensitivity" },
64795
+ obsDetectionHeight: { group: "Safety", label: "Obstacle detection height" },
64796
+ enableCliffDetect: { group: "Safety", label: "Cliff (drop) detection" },
64797
+ ultrasonicSwitch: { group: "Safety", label: "Ultrasonic sensors" },
64798
+ panicButtonMode: { group: "Safety", label: "Emergency button mode" },
64799
+ autoUpdateMap: { group: "Maps", label: "Update the map automatically" },
64800
+ autoUpdateVirtualWall: { group: "Maps", label: "Update virtual walls automatically" },
64801
+ autoUpdateZoneMap: { group: "Maps", label: "Update the area map automatically" },
64802
+ stationAutoDrain: { group: "Base station", label: "Station drains automatically" },
64803
+ language: { group: "Robot", label: "Robot language" },
64804
+ timeZone: { group: "Robot", label: "Robot time zone" }
64805
+ };
64806
+ var SECRET_SETTING = /wifi|pwd|password|secret|token/i;
64807
+ var LANG_WORDS = { zh: "Chinese", en: "English" };
64808
+ function ounitechSettings(s) {
64809
+ const out = [];
64810
+ for (const [key, v] of Object.entries(s ?? {})) {
64811
+ if (key === "ok" || key === "msg" || SECRET_SETTING.test(key) || v == null || typeof v === "object")
64812
+ continue;
64813
+ const raw = String(v).trim();
64814
+ if (raw === "")
64815
+ continue;
64816
+ const d = SETTINGS[key] ?? { group: "Other settings", label: key };
64817
+ let value;
64818
+ if (typeof v === "boolean")
64819
+ value = v ? "On" : "Off";
64820
+ else if (key === "language")
64821
+ value = LANG_WORDS[raw] ?? raw;
64822
+ else if (key === "timeZone" && num(raw) !== void 0)
64823
+ value = `UTC${num(raw) >= 0 ? "+" : ""}${raw}`;
64824
+ else
64825
+ value = d.unit ? `${raw} ${d.unit}` : raw;
64826
+ out.push({ key, group: d.group, label: d.label, value, attention: false });
64827
+ }
64828
+ const order = ["Cleaning", "Battery", "Safety", "Maps", "Sound", "Base station", "Robot", "Other settings"];
64829
+ return out.sort((a, b) => order.indexOf(a.group) - order.indexOf(b.group));
64830
+ }
64831
+ function ounitechObstacleImage(o) {
64832
+ const b64 = typeof o?.image === "string" ? o.image.replace(/^data:image\/\w+;base64,/, "").trim() : "";
64833
+ if (!b64 || !/^[A-Za-z0-9+/=\s]+$/.test(b64.slice(0, 200)))
64834
+ return null;
64835
+ if (b64.length > 15e5)
64836
+ return { version: num(o?.version) ?? null, image: null, tooLarge: true };
64837
+ const type = b64.startsWith("/9j/") ? "jpeg" : "png";
64838
+ return { version: num(o?.version) ?? null, image: `data:image/${type};base64,${b64}`, tooLarge: false };
64839
+ }
64638
64840
  var MAP_TTL_MS = 10 * 6e4;
64639
64841
  var RECORDS_TTL_MS = 2 * 6e4;
64640
64842
  var mapCache = /* @__PURE__ */ new Map();
64641
64843
  var recordsCache = /* @__PURE__ */ new Map();
64844
+ var SLOW_TTL_MS = 10 * 6e4;
64845
+ var slowCache = /* @__PURE__ */ new Map();
64846
+ var trackCache = /* @__PURE__ */ new Map();
64642
64847
  function cached2(cache3, field, key, ttl, load) {
64643
64848
  const hit = cache3.get(key);
64644
64849
  if (hit && Date.now() - hit.at < ttl)
@@ -64651,6 +64856,8 @@ function cached2(cache3, field, key, ttl, load) {
64651
64856
  function clearOunitechCaches() {
64652
64857
  mapCache.clear();
64653
64858
  recordsCache.clear();
64859
+ slowCache.clear();
64860
+ trackCache.clear();
64654
64861
  }
64655
64862
  var robotTime = (d) => robotCloudTimestamp(d, "yyyy-MM-dd HH:mm:ss", "Asia/Shanghai");
64656
64863
  function createOunitechAdapter(credentials, options) {
@@ -64664,12 +64871,15 @@ function createOunitechAdapter(credentials, options) {
64664
64871
  const keys = list.flatMap((m) => [m.backgroundFileKey, m.partitionFileKey]).filter((k) => typeof k === "string" && !!k);
64665
64872
  const files = keys.length ? await cloud.previewFiles(keys).catch(() => []) : [];
64666
64873
  const url2 = (k) => files.find((f) => f.fileKey === k)?.url || null;
64667
- return Promise.all(
64668
- list.map(async (m) => {
64669
- const imageUrl = url2(m.backgroundFileKey);
64670
- return ounitechMapView(m, imageUrl, url2(m.partitionFileKey), imageUrl ? await fetchPngSize(imageUrl) : null);
64671
- })
64672
- );
64874
+ const views = [];
64875
+ for (const m of list) {
64876
+ const imageUrl = url2(m.backgroundFileKey);
64877
+ const id = num(m.mapId);
64878
+ const layer = (kind) => id !== void 0 ? cloud.getMapShapes(kind, id).catch(() => []) : Promise.resolve([]);
64879
+ const shapes = { walls: await layer("walls"), safe: await layer("safe"), slow: await layer("slow") };
64880
+ views.push(ounitechMapView(m, imageUrl, url2(m.partitionFileKey), imageUrl ? await fetchPngSize(imageUrl) : null, shapes));
64881
+ }
64882
+ return views;
64673
64883
  });
64674
64884
  }
64675
64885
  async function placed(row, robot) {
@@ -64683,6 +64893,40 @@ function createOunitechAdapter(credentials, options) {
64683
64893
  robot.planPosition = robot.position ? ounitechMapShare(map, robot.position.x, robot.position.y) : null;
64684
64894
  return robot;
64685
64895
  }
64896
+ async function slowRecords(robotSn) {
64897
+ const row = await rowFor(robotSn);
64898
+ if (!row || !finite(row.robotId))
64899
+ return {};
64900
+ const robotId = row.robotId;
64901
+ const tz = finite(row.timezone) ? row.timezone : 480;
64902
+ const now = /* @__PURE__ */ new Date();
64903
+ const since = (days) => robotTime(new Date(now.getTime() - days * 864e5));
64904
+ const part = async (read2) => {
64905
+ try {
64906
+ return { items: await read2() };
64907
+ } catch (e) {
64908
+ return { items: [], error: String(e?.message ?? e).slice(0, 300) };
64909
+ }
64910
+ };
64911
+ const maps = finite(row.sceneId) ? await floorMaps(row.sceneId).catch(() => []) : [];
64912
+ const map = ounitechCurrentMap(maps, row.taskState?.mapId, Number.isInteger(row.floorNo) ? row.floorNo : null);
64913
+ const mapId = map ? num(map.mapId) : void 0;
64914
+ const floorNo2 = map?.floorNo ?? (Number.isInteger(row.floorNo) ? row.floorNo : null);
64915
+ const sceneId = finite(row.sceneId) ? row.sceneId : null;
64916
+ const statusLog = sceneId !== null ? await part(async () => ((await cloud.getRobotLog(robotId, sceneId, since(7), robotTime(now))).logList ?? []).map((l) => ounitechStatusLog(l, tz))) : { items: [] };
64917
+ const appActions = await part(async () => ((await cloud.getUserLogs(robotId, since(30), robotTime(now))).actionList ?? []).map((a) => ounitechAppAction(a, tz)));
64918
+ const settings = await part(async () => ounitechSettings(await cloud.getCleaningSetting(robotId)));
64919
+ const obstacles = await part(async () => {
64920
+ const o = ounitechObstacleImage(await cloud.getObstacleLayer(robotId));
64921
+ return o ? [o] : [];
64922
+ });
64923
+ const mapVersions = mapId !== void 0 ? await part(async () => ((await cloud.getMapVersions(mapId)).versionList ?? []).map((v) => ounitechMapVersion(v, tz))) : { items: [] };
64924
+ const mapHistory = sceneId !== null && floorNo2 !== null ? await part(async () => ((await cloud.getFloorMapHistory(sceneId, floorNo2)).mapList ?? []).map((m) => ounitechFloorMapHistory(m, tz))) : { items: [] };
64925
+ const mapLayers = {
64926
+ items: map ? [{ map: map.mapDisplayName || null, zones: map.zones.map((z5) => ({ kind: z5.kind, name: z5.name })) }] : []
64927
+ };
64928
+ return { statusLog, appActions, settings, obstacles, mapVersions, mapHistory, mapLayers };
64929
+ }
64686
64930
  async function rowFor(robotSn) {
64687
64931
  return (await cloud.getHomeRobots()).find((r) => r.robotSn === robotSn) ?? null;
64688
64932
  }
@@ -64746,7 +64990,18 @@ function createOunitechAdapter(credentials, options) {
64746
64990
  const row = await rowFor(robotSn);
64747
64991
  if (!row || !finite(row.sceneId))
64748
64992
  return [];
64749
- return floorMaps(row.sceneId);
64993
+ const maps = await floorMaps(row.sceneId);
64994
+ const robotId = row.robotId;
64995
+ if (!finite(robotId))
64996
+ return maps;
64997
+ const track = await cached2(
64998
+ trackCache,
64999
+ "value",
65000
+ `${options?.baseUrl ?? ""}|${credentials.appid}|${robotId}`,
65001
+ SLOW_TTL_MS,
65002
+ async () => (await cloud.getTeachTrack(robotId, robotTime(new Date(Date.now() - 365 * 864e5)))).trackList ?? []
65003
+ ).catch(() => []);
65004
+ return maps.map((m) => ({ ...m, taughtRoute: ounitechTrack(m, track) }));
64750
65005
  },
64751
65006
  async getMapImages(_robotSn, fileKeys) {
64752
65007
  return cloud.previewFiles(fileKeys);
@@ -64772,7 +65027,7 @@ function createOunitechAdapter(credentials, options) {
64772
65027
  * after another (gentler on the rate limit); each part carries its own error.
64773
65028
  */
64774
65029
  async getRecords(robotSn) {
64775
- return cached2(recordsCache, "value", `${options?.baseUrl ?? ""}|${credentials.appid}|${robotSn}`, RECORDS_TTL_MS, async () => {
65030
+ const fast = cached2(recordsCache, "value", `${options?.baseUrl ?? ""}|${credentials.appid}|${robotSn}`, RECORDS_TTL_MS, async () => {
64776
65031
  const row = await rowFor(robotSn);
64777
65032
  if (!row || !finite(row.robotId))
64778
65033
  return { supported: true, error: `Serial ${robotSn} is not on this Ounitech account.` };
@@ -64806,11 +65061,17 @@ function createOunitechAdapter(credentials, options) {
64806
65061
  ) : { items: [] };
64807
65062
  const readings = await part(async () => ounitechReadings((await cloud.getRobotState(robotId)).properties));
64808
65063
  const station = await part(async () => {
64809
- const st = await cloud.getStationState(robotId);
65064
+ const st = await cloud.getStationState(robotId).catch((e) => {
65065
+ if (/no station bound|e=59/i.test(String(e?.message ?? "")))
65066
+ return null;
65067
+ throw e;
65068
+ });
64810
65069
  return st ? [{ status: String(st.statusName ?? "").trim() || null, readings: ounitechReadings(st.properties, true) }] : [];
64811
65070
  });
64812
65071
  return { supported: true, readAt: now.toISOString(), tasks, alerts, consumables, power, lifts, readings, station };
64813
65072
  });
65073
+ const slow = await cached2(slowCache, "value", `${options?.baseUrl ?? ""}|${credentials.appid}|${robotSn}`, SLOW_TTL_MS, () => slowRecords(robotSn));
65074
+ return { ...slow, ...await fast };
64814
65075
  },
64815
65076
  /**
64816
65077
  * Staff Diagnose: every other read-only chapter-6 call, with the vendor's
@@ -64842,8 +65103,8 @@ function createOunitechAdapter(credentials, options) {
64842
65103
  return { count: list.length, robots: list.slice(0, 3).map((r) => ({ robotSn: r.robotSn, statusName: r.statusName })) };
64843
65104
  });
64844
65105
  await run("serial-based map list (chapter 2)", ROBOT_CLOUD_PATHS.mapList, { robotSn }, async () => {
64845
- const maps = await cloud.getMaps(robotSn);
64846
- return { count: maps.length, floors: maps.map((m) => m.floorNo) };
65106
+ const maps2 = await cloud.getMaps(robotSn);
65107
+ return { count: maps2.length, floors: maps2.map((m) => m.floorNo) };
64847
65108
  });
64848
65109
  const row = await rowFor(robotSn).catch(() => null);
64849
65110
  if (!row || !finite(row.robotId)) {
@@ -64895,6 +65156,50 @@ function createOunitechAdapter(credentials, options) {
64895
65156
  return (r.liftlist ?? []).map((l) => ({ liftno: l.liftno, liftname: l.liftname, floorno: l.floorno, onlineflag: l.onlineflag, enableflag: l.enableflag }));
64896
65157
  });
64897
65158
  }
65159
+ const maps = finite(row.sceneId) ? await floorMaps(row.sceneId).catch(() => []) : [];
65160
+ const map = ounitechCurrentMap(maps, row.taskState?.mapId, Number.isInteger(row.floorNo) ? row.floorNo : null);
65161
+ const mapId = map ? num(map.mapId) : void 0;
65162
+ if (mapId !== void 0) {
65163
+ await run("virtual walls (get-wall-list)", ROBOT_CLOUD_PATHS.wallList, { mapId }, async () => cut(await cloud.getMapShapes("walls", mapId)));
65164
+ await run("safe zones (get-safezone-list)", ROBOT_CLOUD_PATHS.safeZoneList, { mapId }, async () => cut(await cloud.getMapShapes("safe", mapId)));
65165
+ await run("slow zones (get-slowzone-list)", ROBOT_CLOUD_PATHS.slowZoneList, { mapId }, async () => cut(await cloud.getMapShapes("slow", mapId)));
65166
+ await run("map versions (get-map-version-list)", ROBOT_CLOUD_PATHS.mapVersions, { mapId }, async () => cut((await cloud.getMapVersions(mapId)).versionList ?? []));
65167
+ }
65168
+ if (finite(row.sceneId) && map?.floorNo != null) {
65169
+ const sceneId = row.sceneId;
65170
+ const floorNo2 = map.floorNo;
65171
+ await run(
65172
+ "floor map history (v2405/get-floor-maplist)",
65173
+ ROBOT_CLOUD_PATHS.floorMapHistory,
65174
+ { sceneId, floorNo: floorNo2 },
65175
+ async () => cut((await cloud.getFloorMapHistory(sceneId, floorNo2)).mapList ?? [])
65176
+ );
65177
+ }
65178
+ await run("obstacle layer (get-obstacle-layer)", ROBOT_CLOUD_PATHS.obstacleLayer, { robotId, version: 0 }, async () => {
65179
+ const o = await cloud.getObstacleLayer(robotId);
65180
+ return { version: o.version ?? null, imageChars: typeof o.image === "string" ? o.image.length : 0 };
65181
+ });
65182
+ await run("taught route (get-teach-track)", ROBOT_CLOUD_PATHS.teachTrack, { robotId, offset: window.timeFrom }, async () => {
65183
+ const r = await cloud.getTeachTrack(robotId, window.timeFrom);
65184
+ return { points: r.trackList?.length ?? 0, since: r.since ?? null, first: cut(r.trackList ?? []) };
65185
+ });
65186
+ if (finite(row.sceneId)) {
65187
+ const sceneId = row.sceneId;
65188
+ await run("robot status log, last 7 days (get-robot-log-list)", ROBOT_CLOUD_PATHS.robotLog, { robotId, sceneId, ...window }, async () => {
65189
+ const r = await cloud.getRobotLog(robotId, sceneId, window.timeFrom, window.timeTo);
65190
+ return { total: r.total ?? r.logList?.length ?? 0, latest: cut(r.logList ?? []) };
65191
+ });
65192
+ }
65193
+ await run("app action log, last 7 days (get-user-logs)", ROBOT_CLOUD_PATHS.userLog, { robotId, startTime: window.timeFrom, endTime: window.timeTo }, async () => {
65194
+ const r = await cloud.getUserLogs(robotId, window.timeFrom, window.timeTo);
65195
+ return { total: r.total ?? r.actionList?.length ?? 0, latest: cut((r.actionList ?? []).map(({ userPhone: _p, ...a }) => a)) };
65196
+ });
65197
+ await run(
65198
+ "robot settings (get-cleaning-setting)",
65199
+ ROBOT_CLOUD_PATHS.cleaningSetting,
65200
+ { robotId },
65201
+ async () => Object.fromEntries(Object.entries(await cloud.getCleaningSetting(robotId)).filter(([k]) => !SECRET_SETTING.test(k) && k !== "ok" && k !== "msg"))
65202
+ );
64898
65203
  steps.push({
64899
65204
  step: "current job (robot list taskState)",
64900
65205
  path: ROBOT_CLOUD_PATHS.homeRobotList,
@@ -107318,6 +107623,7 @@ export {
107318
107623
  ROBOT_TYPES,
107319
107624
  RobotCloudError,
107320
107625
  RobotCredentialsError,
107626
+ SECRET_SETTING,
107321
107627
  SELF_SERVICE_RESEND_COOLDOWN_MS,
107322
107628
  SELF_SIGNUP_PLATFORM,
107323
107629
  SELF_SIGNUP_STATUS,
@@ -107614,18 +107920,26 @@ export {
107614
107920
  orgRoleSets,
107615
107921
  orgSchema,
107616
107922
  ounitechAlertRecord,
107923
+ ounitechAppAction,
107617
107924
  ounitechCleaning,
107618
107925
  ounitechConsumable,
107619
107926
  ounitechCurrentMap,
107620
107927
  ounitechFault,
107928
+ ounitechFloorMapHistory,
107621
107929
  ounitechJobWords,
107622
107930
  ounitechMapShare,
107931
+ ounitechMapVersion,
107623
107932
  ounitechMapView,
107933
+ ounitechObstacleImage,
107624
107934
  ounitechPowerPlan,
107625
107935
  ounitechReadings,
107626
107936
  ounitechRobotFromHomeRow,
107937
+ ounitechSettings,
107938
+ ounitechShapes,
107939
+ ounitechStatusLog,
107627
107940
  ounitechTaskRecord,
107628
107941
  ounitechTime,
107942
+ ounitechTrack,
107629
107943
  overnight_parking_requests_namespace_collection,
107630
107944
  padbotAccountKey,
107631
107945
  padbotAlarmFault,