@7365admin1/core 3.132.0 → 3.133.1

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
@@ -2237,10 +2237,10 @@ function useOccurrenceEntryRepo() {
2237
2237
  const cacheKey = makeCacheKey3(namespace_collection3, {
2238
2238
  dailyOccurrenceBookId
2239
2239
  });
2240
- const cached3 = await getCache(cacheKey);
2241
- if (cached3) {
2240
+ const cached4 = await getCache(cacheKey);
2241
+ if (cached4) {
2242
2242
  logger5.info(`Cache hit for key: ${cacheKey}`);
2243
- return cached3;
2243
+ return cached4;
2244
2244
  }
2245
2245
  const bookId = typeof dailyOccurrenceBookId === "string" ? new ObjectId9(dailyOccurrenceBookId) : dailyOccurrenceBookId;
2246
2246
  const data = await collection.findOne(
@@ -17963,13 +17963,13 @@ function useFileRepo() {
17963
17963
  }
17964
17964
  const cacheKey = makeCacheKey14(namespace_collection3, { _id: String(_id) });
17965
17965
  try {
17966
- const cached3 = await getCache(cacheKey);
17967
- if (cached3) {
17966
+ const cached4 = await getCache(cacheKey);
17967
+ if (cached4) {
17968
17968
  logger30.log({
17969
17969
  level: "info",
17970
17970
  message: `Cache hit for getById file: ${cacheKey}`
17971
17971
  });
17972
- return cached3;
17972
+ return cached4;
17973
17973
  }
17974
17974
  const result = await collection.findOne({
17975
17975
  _id
@@ -22065,9 +22065,9 @@ function useCameraViewService() {
22065
22065
  async function refreshProbe(target, channel) {
22066
22066
  if (!target?.enabled)
22067
22067
  return null;
22068
- const cached3 = await cachedProbe(target, channel);
22069
- if (cached3)
22070
- return cached3;
22068
+ const cached4 = await cachedProbe(target, channel);
22069
+ if (cached4)
22070
+ return cached4;
22071
22071
  const probe = await probeDeviceCapabilities({
22072
22072
  adapter: createDeviceHttpAdapter({ target, budget: authBudget }),
22073
22073
  channel
@@ -22438,9 +22438,9 @@ function useCameraViewService() {
22438
22438
  };
22439
22439
  }
22440
22440
  const cacheKey = `device:${resolved.device.host}:${resolved.device.port}`;
22441
- const cached3 = await getCache(cacheKey);
22442
- const reachable = typeof cached3 === "boolean" ? cached3 : await probeDevice(resolved.device);
22443
- if (typeof cached3 !== "boolean") {
22441
+ const cached4 = await getCache(cacheKey);
22442
+ const reachable = typeof cached4 === "boolean" ? cached4 : await probeDevice(resolved.device);
22443
+ if (typeof cached4 !== "boolean") {
22444
22444
  setCache(cacheKey, reachable, cacheSeconds).catch(
22445
22445
  (error) => logger33.info(`Camera device health cache write failed: ${error?.message}`)
22446
22446
  );
@@ -22473,10 +22473,10 @@ function useCameraViewService() {
22473
22473
  const subtype = knownNoSubStream ? 0 : wanted;
22474
22474
  const fellBackFromCache = subtype !== wanted;
22475
22475
  const cacheKey = `snapshot:${params.cameraId}:${subtype}`;
22476
- const cached3 = await getCache(cacheKey);
22477
- if (cached3) {
22476
+ const cached4 = await getCache(cacheKey);
22477
+ if (cached4) {
22478
22478
  return {
22479
- buffer: Buffer.from(cached3, "base64"),
22479
+ buffer: Buffer.from(cached4, "base64"),
22480
22480
  cached: true,
22481
22481
  stream: subtype === 0 ? "main" : "sub",
22482
22482
  fellBackToMain: fellBackFromCache
@@ -22566,9 +22566,9 @@ function useCameraViewService() {
22566
22566
  };
22567
22567
  }
22568
22568
  const cacheKey = `device:${resolved.device.host}:${resolved.device.port}`;
22569
- const cached3 = await getCache(cacheKey);
22570
- const reachable = typeof cached3 === "boolean" ? cached3 : await probeDevice(resolved.device);
22571
- if (typeof cached3 !== "boolean") {
22569
+ const cached4 = await getCache(cacheKey);
22570
+ const reachable = typeof cached4 === "boolean" ? cached4 : await probeDevice(resolved.device);
22571
+ if (typeof cached4 !== "boolean") {
22572
22572
  setCache(cacheKey, reachable, DEVICE_HEALTH_CACHE_SECONDS).catch(
22573
22573
  (error) => logger33.info(`Camera device health cache write failed: ${error?.message}`)
22574
22574
  );
@@ -25839,13 +25839,13 @@ function usePersonRepo() {
25839
25839
  _id: String(_id)
25840
25840
  });
25841
25841
  try {
25842
- const cached3 = await getCache(cacheKey);
25843
- if (cached3) {
25842
+ const cached4 = await getCache(cacheKey);
25843
+ if (cached4) {
25844
25844
  logger39.log({
25845
25845
  level: "info",
25846
25846
  message: `Cache hit for getById person: ${cacheKey}`
25847
25847
  });
25848
- return cached3;
25848
+ return cached4;
25849
25849
  }
25850
25850
  const result = await collection.findOne({
25851
25851
  _id
@@ -26271,13 +26271,13 @@ function usePersonRepo() {
26271
26271
  user: userId
26272
26272
  });
26273
26273
  try {
26274
- const cached3 = await getCache(cacheKey);
26275
- if (cached3) {
26274
+ const cached4 = await getCache(cacheKey);
26275
+ if (cached4) {
26276
26276
  logger39.log({
26277
26277
  level: "info",
26278
26278
  message: `Cache hit for getByUserId person: ${cacheKey}`
26279
26279
  });
26280
- return cached3;
26280
+ return cached4;
26281
26281
  }
26282
26282
  const result = await collection.findOne({
26283
26283
  user
@@ -36966,13 +36966,13 @@ function useBuildingUnitRepo() {
36966
36966
  message: `Cache key for getAll building units: ${cacheKey}`
36967
36967
  });
36968
36968
  try {
36969
- const cached3 = await getCache(cacheKey);
36970
- if (cached3) {
36969
+ const cached4 = await getCache(cacheKey);
36970
+ if (cached4) {
36971
36971
  logger69.log({
36972
36972
  level: "info",
36973
36973
  message: `Cache hit for getAll building units: ${cacheKey}`
36974
36974
  });
36975
- return cached3;
36975
+ return cached4;
36976
36976
  }
36977
36977
  const pipeline = [
36978
36978
  { $match: query2 },
@@ -37107,13 +37107,13 @@ function useBuildingUnitRepo() {
37107
37107
  message: `Cache key for getAll building units: ${cacheKey}`
37108
37108
  });
37109
37109
  try {
37110
- const cached3 = await getCache(cacheKey);
37111
- if (cached3) {
37110
+ const cached4 = await getCache(cacheKey);
37111
+ if (cached4) {
37112
37112
  logger69.log({
37113
37113
  level: "info",
37114
37114
  message: `Cache hit for getAll building units: ${cacheKey}`
37115
37115
  });
37116
- return cached3;
37116
+ return cached4;
37117
37117
  }
37118
37118
  const items = await collection.aggregate(
37119
37119
  [
@@ -37202,13 +37202,13 @@ function useBuildingUnitRepo() {
37202
37202
  level: level2
37203
37203
  });
37204
37204
  try {
37205
- const cached3 = await getCache(cacheKey);
37206
- if (cached3) {
37205
+ const cached4 = await getCache(cacheKey);
37206
+ if (cached4) {
37207
37207
  logger69.log({
37208
37208
  level: "info",
37209
37209
  message: `Cache hit for getById building unit: ${cacheKey}`
37210
37210
  });
37211
- return cached3;
37211
+ return cached4;
37212
37212
  }
37213
37213
  const result = await collection.findOne({
37214
37214
  building,
@@ -37275,13 +37275,13 @@ function useBuildingUnitRepo() {
37275
37275
  building: String(building)
37276
37276
  });
37277
37277
  try {
37278
- const cached3 = await getCache(cacheKey);
37279
- if (cached3) {
37278
+ const cached4 = await getCache(cacheKey);
37279
+ if (cached4) {
37280
37280
  logger69.log({
37281
37281
  level: "info",
37282
37282
  message: `Cache hit for getById building unit: ${cacheKey}`
37283
37283
  });
37284
- return cached3;
37284
+ return cached4;
37285
37285
  }
37286
37286
  const result = await collection.findOne({
37287
37287
  building,
@@ -37487,13 +37487,13 @@ function useBuildingUnitRepo() {
37487
37487
  cacheOptions
37488
37488
  );
37489
37489
  try {
37490
- const cached3 = await getCache(cacheKey);
37491
- if (cached3) {
37490
+ const cached4 = await getCache(cacheKey);
37491
+ if (cached4) {
37492
37492
  logger69.log({
37493
37493
  level: "info",
37494
37494
  message: `Cache hit for getById building unit: ${cacheKey}`
37495
37495
  });
37496
- return cached3;
37496
+ return cached4;
37497
37497
  }
37498
37498
  const result = await collection.findOne(query2, {
37499
37499
  session
@@ -37533,13 +37533,13 @@ function useBuildingUnitRepo() {
37533
37533
  level: level2
37534
37534
  });
37535
37535
  try {
37536
- const cached3 = await getCache(cacheKey);
37537
- if (cached3) {
37536
+ const cached4 = await getCache(cacheKey);
37537
+ if (cached4) {
37538
37538
  logger69.log({
37539
37539
  level: "info",
37540
37540
  message: `Cache hit for getById building unit: ${cacheKey}`
37541
37541
  });
37542
- return cached3;
37542
+ return cached4;
37543
37543
  }
37544
37544
  const query2 = {
37545
37545
  site,
@@ -37905,9 +37905,9 @@ function useVehicleService() {
37905
37905
  const siteZones = /* @__PURE__ */ new Map();
37906
37906
  async function siteTimezone(site) {
37907
37907
  const key = String(site ?? "");
37908
- const cached3 = siteZones.get(key);
37909
- if (cached3 && Date.now() - cached3.at < 5 * 6e4)
37910
- return cached3.zone;
37908
+ const cached4 = siteZones.get(key);
37909
+ if (cached4 && Date.now() - cached4.at < 5 * 6e4)
37910
+ return cached4.zone;
37911
37911
  let zone = resolveSiteTimezone(null);
37912
37912
  if (key) {
37913
37913
  try {
@@ -40801,13 +40801,13 @@ function useBuildingRepo() {
40801
40801
  message: `Cache key for getAll buildings: ${cacheKey}`
40802
40802
  });
40803
40803
  try {
40804
- const cached3 = await getCache(cacheKey);
40805
- if (cached3) {
40804
+ const cached4 = await getCache(cacheKey);
40805
+ if (cached4) {
40806
40806
  logger76.log({
40807
40807
  level: "info",
40808
40808
  message: `Cache hit for getAll buildings: ${cacheKey}`
40809
40809
  });
40810
- return cached3;
40810
+ return cached4;
40811
40811
  }
40812
40812
  const items = await collection.aggregate(
40813
40813
  [
@@ -40936,13 +40936,13 @@ function useBuildingRepo() {
40936
40936
  _id: String(_id)
40937
40937
  });
40938
40938
  try {
40939
- const cached3 = await getCache(cacheKey);
40940
- if (cached3) {
40939
+ const cached4 = await getCache(cacheKey);
40940
+ if (cached4) {
40941
40941
  logger76.log({
40942
40942
  level: "info",
40943
40943
  message: `Cache hit for getById building: ${cacheKey}`
40944
40944
  });
40945
- return cached3;
40945
+ return cached4;
40946
40946
  }
40947
40947
  const result = await collection.findOne({
40948
40948
  _id
@@ -41006,13 +41006,13 @@ function useBuildingRepo() {
41006
41006
  const cacheOptions = { ...query2 };
41007
41007
  const cacheKey = makeCacheKey28(buildings_namespace_collection, cacheOptions);
41008
41008
  try {
41009
- const cached3 = await getCache(cacheKey);
41010
- if (cached3) {
41009
+ const cached4 = await getCache(cacheKey);
41010
+ if (cached4) {
41011
41011
  logger76.log({
41012
41012
  level: "info",
41013
41013
  message: `Cache hit for getById building: ${cacheKey}`
41014
41014
  });
41015
- return cached3;
41015
+ return cached4;
41016
41016
  }
41017
41017
  const result = await collection.findOne(query2);
41018
41018
  setCache(cacheKey, result, 300).then(() => {
@@ -41510,13 +41510,13 @@ function useBuildingLevelRepo() {
41510
41510
  message: `Cache key for getAll building levels: ${cacheKey}`
41511
41511
  });
41512
41512
  try {
41513
- const cached3 = await getCache(cacheKey);
41514
- if (cached3) {
41513
+ const cached4 = await getCache(cacheKey);
41514
+ if (cached4) {
41515
41515
  logger78.log({
41516
41516
  level: "info",
41517
41517
  message: `Cache hit for getAll building levels: ${cacheKey}`
41518
41518
  });
41519
- return cached3;
41519
+ return cached4;
41520
41520
  }
41521
41521
  const sortStage = Object.keys(sort).length > 0 ? { $sort: sort } : { $sort: { name: 1 } };
41522
41522
  const items = await collection.aggregate(
@@ -41561,13 +41561,13 @@ function useBuildingLevelRepo() {
41561
41561
  const cacheKey = makeCacheKey29(building_level_namespace_collection, {
41562
41562
  _id
41563
41563
  });
41564
- const cached3 = await getCache(cacheKey);
41565
- if (cached3) {
41564
+ const cached4 = await getCache(cacheKey);
41565
+ if (cached4) {
41566
41566
  logger78.log({
41567
41567
  level: "info",
41568
41568
  message: `Cache hit for getById building level: ${cacheKey}`
41569
41569
  });
41570
- return cached3;
41570
+ return cached4;
41571
41571
  }
41572
41572
  try {
41573
41573
  _id = new ObjectId88(_id);
@@ -45241,7 +45241,7 @@ function useCameraViewController() {
45241
45241
  }
45242
45242
  async function snapshot2(req, res, next) {
45243
45243
  try {
45244
- const { buffer, cached: cached3, stream, fellBackToMain } = await getSnapshot({
45244
+ const { buffer, cached: cached4, stream, fellBackToMain } = await getSnapshot({
45245
45245
  cameraId: String(req.params.id ?? ""),
45246
45246
  userId: callerId5(req)
45247
45247
  });
@@ -45250,7 +45250,7 @@ function useCameraViewController() {
45250
45250
  "Cache-Control",
45251
45251
  `private, max-age=${CAMERA_SNAPSHOT_CACHE_SECONDS}`
45252
45252
  );
45253
- res.setHeader("X-Camera-Snapshot-Cached", cached3 ? "1" : "0");
45253
+ res.setHeader("X-Camera-Snapshot-Cached", cached4 ? "1" : "0");
45254
45254
  res.setHeader("X-Camera-Stream", stream);
45255
45255
  res.setHeader("X-Camera-Stream-Fallback", fellBackToMain ? "1" : "0");
45256
45256
  res.status(200).end(buffer);
@@ -63568,6 +63568,9 @@ var ROBOT_CLOUD_PATHS = {
63568
63568
  taskList: "/portal/cleaning/get-task-list",
63569
63569
  alertList: "/portal/alert/get-alert-list",
63570
63570
  liftList: "/portal/lift/get-lift-list",
63571
+ workHours: "/portal/workhours/get-work-hours",
63572
+ haltPlans: "/portal/halt-plan/get",
63573
+ stationState: "/portal/detailstate/get-station-detail-state",
63571
63574
  mapList: "/portal/maps/get-map-list",
63572
63575
  fileUrl: "/portal/maps/get-file-url",
63573
63576
  tracking: "/portal/robots/tracking",
@@ -63864,6 +63867,9 @@ var STEP_NAMES = {
63864
63867
  [ROBOT_CLOUD_PATHS.filePreview]: "the map images",
63865
63868
  [ROBOT_CLOUD_PATHS.plansV2]: "the cleaning schedule",
63866
63869
  [ROBOT_CLOUD_PATHS.taskList]: "the cleaning records",
63870
+ [ROBOT_CLOUD_PATHS.workHours]: "the consumable hours",
63871
+ [ROBOT_CLOUD_PATHS.haltPlans]: "the power schedule",
63872
+ [ROBOT_CLOUD_PATHS.stationState]: "the base station state",
63867
63873
  [ROBOT_CLOUD_PATHS.alertList]: "the alert history",
63868
63874
  [ROBOT_CLOUD_PATHS.liftList]: "the lift list"
63869
63875
  };
@@ -64068,6 +64074,23 @@ function useRobotCloudService(credentials, options = {}) {
64068
64074
  async function getLiftList(sceneId) {
64069
64075
  return post(ROBOT_CLOUD_PATHS.liftList, { sceneid: sceneId }, "liftlist");
64070
64076
  }
64077
+ async function getWorkHours(robotId) {
64078
+ return post(ROBOT_CLOUD_PATHS.workHours, { robotId }, "unitlist");
64079
+ }
64080
+ async function getHaltPlans(robotId) {
64081
+ return post(
64082
+ ROBOT_CLOUD_PATHS.haltPlans,
64083
+ { planId: 0, robotId, pageNo: 1, pageSize: 20 },
64084
+ "planList"
64085
+ );
64086
+ }
64087
+ async function getStationState(robotId) {
64088
+ const data = await post(
64089
+ ROBOT_CLOUD_PATHS.stationState,
64090
+ { robotId, options: "state" }
64091
+ );
64092
+ return data.state ?? null;
64093
+ }
64071
64094
  async function getMaps(robotSn) {
64072
64095
  const data = await post(
64073
64096
  ROBOT_CLOUD_PATHS.mapList,
@@ -64149,6 +64172,9 @@ function useRobotCloudService(credentials, options = {}) {
64149
64172
  getPlansV2,
64150
64173
  getTaskList,
64151
64174
  getAlerts,
64175
+ getWorkHours,
64176
+ getHaltPlans,
64177
+ getStationState,
64152
64178
  getLiftList,
64153
64179
  getMaps,
64154
64180
  getFileUrls,
@@ -64162,6 +64188,7 @@ function useRobotCloudService(credentials, options = {}) {
64162
64188
  }
64163
64189
 
64164
64190
  // src/services/ounitech.adapter.ts
64191
+ import axios4 from "axios";
64165
64192
  var OUNITECH_BRAND = "ounitech";
64166
64193
  var OUNITECH_CAPABILITIES = {
64167
64194
  // Pose in the chapter-6 robot list (metres) and the tracking stream.
@@ -64343,12 +64370,326 @@ function ounitechFault(list) {
64343
64370
  return { code: "error", message: String(list[0]).slice(0, 200) };
64344
64371
  return { code: "error", message: "The robot reports an error" };
64345
64372
  }
64373
+ function ounitechMapShare(map, x, y) {
64374
+ const w = map?.width, h = map?.height, r = map?.resolution;
64375
+ const wx = num(x), wy = num(y);
64376
+ if (!finite(w) || !finite(h) || !finite(r) || w <= 0 || h <= 0 || r <= 0 || wx === void 0 || wy === void 0)
64377
+ 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;
64380
+ if (sx < 0 || sx > 100 || sy < 0 || sy > 100)
64381
+ return null;
64382
+ return { x: Math.round(sx * 100) / 100, y: Math.round(sy * 100) / 100 };
64383
+ }
64384
+ function ounitechMapView(m, imageUrl, partitionImageUrl, size) {
64385
+ const floorNo2 = Number.isInteger(m.floorNo) ? m.floorNo : null;
64386
+ const width = size?.width ?? null;
64387
+ const height = size?.height ?? null;
64388
+ const frame2 = { width, height, resolution: m.resolution, originX: m.originX, originY: m.originY };
64389
+ const areas = (Array.isArray(m.areaList) ? m.areaList : []).filter((a) => typeof a?.areaName === "string" && a.areaName.trim()).map((a) => {
64390
+ const px = num(a.x), py = num(a.y);
64391
+ 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;
64392
+ return { ...a.areaId != null ? { areaId: a.areaId } : {}, areaName: a.areaName.trim(), rgba: a.rgba, x: a.x, y: a.y, at: at2 };
64393
+ });
64394
+ return {
64395
+ mapId: String(m.mapId ?? `floor-${floorNo2 ?? 0}`),
64396
+ floor: floorNo2,
64397
+ floorNo: floorNo2,
64398
+ mapDisplayName: String(m.mapName ?? "").trim(),
64399
+ mapName: m.mapName,
64400
+ imageUrl,
64401
+ partitionImageUrl,
64402
+ width,
64403
+ height,
64404
+ resolution: m.resolution,
64405
+ originX: m.originX,
64406
+ originY: m.originY,
64407
+ backgroundFileKey: m.backgroundFileKey,
64408
+ partitionFileKey: m.partitionFileKey,
64409
+ totalArea: m.totalArea,
64410
+ baseX: m.baseX,
64411
+ baseY: m.baseY,
64412
+ baseTheta: m.baseTheta,
64413
+ createTime: m.createTime,
64414
+ dock: ounitechMapShare(frame2, m.baseX ?? 0, m.baseY ?? 0),
64415
+ positionApproximate: true,
64416
+ // The raw areas, kept for older screens.
64417
+ areaList: areas.map(({ at: _at, ...a }) => a),
64418
+ areas: areas.map((a) => ({ name: a.areaName, at: a.at }))
64419
+ };
64420
+ }
64421
+ function ounitechCurrentMap(maps, taskMapId, floorNo2) {
64422
+ const byTask = taskMapId != null ? maps.find((m) => m.mapId === String(taskMapId)) : void 0;
64423
+ if (byTask)
64424
+ return byTask;
64425
+ if (Number.isInteger(floorNo2))
64426
+ return maps.find((m) => m.floorNo === floorNo2) ?? null;
64427
+ return maps.length === 1 ? maps[0] : null;
64428
+ }
64429
+ function pngSize(bytes) {
64430
+ if (!bytes || bytes.length < 24)
64431
+ return null;
64432
+ const ihdr = String.fromCharCode(bytes[12], bytes[13], bytes[14], bytes[15]);
64433
+ if (bytes[1] !== 80 || ihdr !== "IHDR")
64434
+ return null;
64435
+ const dv = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
64436
+ const width = dv.getUint32(16), height = dv.getUint32(20);
64437
+ return width > 0 && height > 0 && width < 2e4 && height < 2e4 ? { width, height } : null;
64438
+ }
64439
+ async function fetchPngSize(url2) {
64440
+ try {
64441
+ const res = await axios4.get(url2, { responseType: "arraybuffer", headers: { Range: "bytes=0-63" }, timeout: 8e3 });
64442
+ return pngSize(new Uint8Array(res.data));
64443
+ } catch {
64444
+ return null;
64445
+ }
64446
+ }
64447
+ function ounitechTime(v, tzMinutes = 480) {
64448
+ const m = typeof v === "string" ? /^(\d{4}-\d{2}-\d{2})[ T](\d{2}:\d{2}(?::\d{2})?)/.exec(v.trim()) : null;
64449
+ if (!m)
64450
+ return null;
64451
+ const t = Date.parse(`${m[1]}T${m[2].length === 5 ? `${m[2]}:00` : m[2]}Z`) - tzMinutes * 6e4;
64452
+ return Number.isFinite(t) ? new Date(t).toISOString() : null;
64453
+ }
64454
+ var MODE_WORDS = { \u5438\u5C18: "Vacuum", \u6D17\u5730: "Wash floor", \u5C18\u63A8: "Dust mop", \u62D6\u5730: "Mop" };
64455
+ var TYPE_WORDS = {
64456
+ \u51C6\u5907\u6E05\u6D01: "Getting ready",
64457
+ \u8131\u79BB\u57FA\u7AD9\u4E2D: "Leaving the charger",
64458
+ \u5168\u5C40\u6E05\u626B: "Clean all",
64459
+ \u5206\u533A\u6E05\u626B: "Area clean",
64460
+ \u5B9A\u70B9\u6E05\u626B: "Spot clean",
64461
+ \u56DE\u5145: "Returning to charge",
64462
+ \u6CBF\u8FB9\u6E05\u626B: "Edge clean"
64463
+ };
64464
+ var SOURCE_WORDS = { plan: "Schedule", app: "Ounitech app", btn: "Button on the robot" };
64465
+ var round1 = (v) => v !== void 0 ? Math.round(v * 10) / 10 : null;
64466
+ function ounitechTaskRecord(t, maps = [], tz = 480) {
64467
+ const map = maps.find((m) => m.mapId === String(t.mapId));
64468
+ const kind = String(t.typeName ?? "").trim();
64469
+ const mode = String(t.subTypeName ?? "").trim();
64470
+ const src = String(t.source ?? "").split(",")[0].trim();
64471
+ const mileage = num(t.cleanedMileage);
64472
+ return {
64473
+ id: String(t.taskId ?? ""),
64474
+ start: ounitechTime(t.timeFrom, tz),
64475
+ end: ounitechTime(t.timeTo, tz),
64476
+ durationSec: num(t.durationSeconds) ?? num(t.accTime) ?? null,
64477
+ areaM2: round1(num(t.cleanedArea) ?? num(t.accArea)),
64478
+ plannedM2: round1(num(t.countArea)),
64479
+ percent: num(t.accPercent) ?? null,
64480
+ distanceM: mileage !== void 0 ? Math.round(mileage) : null,
64481
+ result: String(t.statusName ?? "").trim() || null,
64482
+ job: TYPE_WORDS[kind] ?? (kind || null),
64483
+ mode: MODE_WORDS[mode] ?? (mode || null),
64484
+ source: SOURCE_WORDS[src] ?? (src || null),
64485
+ map: map ? map.mapDisplayName || (map.floorNo !== null ? `Floor ${map.floorNo}` : null) : null,
64486
+ floorNo: Number.isInteger(t.floorNo) ? t.floorNo : map?.floorNo ?? null
64487
+ };
64488
+ }
64489
+ var ALERT_WORDS = {
64490
+ "205": "Side brush driver offline",
64491
+ "206": "Button panel offline",
64492
+ "540": "Floor check: cliff sensor switched on",
64493
+ "588": "Switched off with the power button",
64494
+ "589": "Switched off by the timed power schedule",
64495
+ "593": "Still finding its position - try again shortly",
64496
+ "601": "Left wheel driver reset",
64497
+ "620": "Right wheel driver offline",
64498
+ "621": "Right wheel driver reset",
64499
+ "734": "IMU zero offset too large",
64500
+ "785": "Localisation ready"
64501
+ };
64502
+ var ALERT_LEVEL_WORDS = { \u63D0\u793A: "Notice", \u8B66\u544A: "Warning", \u6545\u969C: "Fault", \u9519\u8BEF: "Error", \u4E25\u91CD: "Critical" };
64503
+ function ounitechAlertRecord(a, tz = 480) {
64504
+ const raw = String(a.errMsg ?? a.errCode ?? "").trim();
64505
+ const m = /^\s*(\d+)\s*-\s*(.*)$/.exec(raw);
64506
+ const code = m?.[1] ?? "";
64507
+ let rest = (m?.[2] ?? raw).trim();
64508
+ const resolved = /\(Resolved\)\s*$/i.test(rest);
64509
+ rest = rest.replace(/\(Resolved\)\s*$/i, "").replace(/\(\s*\d+\s*\)\s*$/, "").trim();
64510
+ const lv = /^\(([^)]*)\)/.exec(rest);
64511
+ if (lv)
64512
+ rest = rest.slice(lv[0].length).trim();
64513
+ return {
64514
+ code,
64515
+ level: lv ? ALERT_LEVEL_WORDS[lv[1].trim()] ?? lv[1].trim() : null,
64516
+ // An untranslated Chinese text keeps its code up front, so the row is never only Chinese.
64517
+ message: ALERT_WORDS[code] ?? (/[㐀-鿿]/.test(rest || raw) && code ? `Robot alert ${code}: ${rest || raw}` : rest || raw),
64518
+ vendorText: rest || raw,
64519
+ resolved,
64520
+ at: ounitechTime(a.createTime, tz)
64521
+ };
64522
+ }
64523
+ var READINGS = {
64524
+ "battery-percent": { group: "Battery", label: "Battery", unit: "%" },
64525
+ "left-battery-percent": { group: "Battery", label: "Left battery", unit: "%" },
64526
+ "right-battery-percent": { group: "Battery", label: "Right battery", unit: "%" },
64527
+ "bat-vol-left": { group: "Battery", label: "Left battery voltage", unit: "V" },
64528
+ "bat-vol-right": { group: "Battery", label: "Right battery voltage", unit: "V" },
64529
+ BatteryOffline: { group: "Battery", label: "Battery disconnected", bad: "true" },
64530
+ BatteryClosed: { group: "Battery", label: "Battery switched off", bad: "true" },
64531
+ "clean-water": { group: "Water", label: "Clean water", unit: "%" },
64532
+ "dirty-water": { group: "Water", label: "Dirty water", unit: "%" },
64533
+ "clean-water-level": { group: "Water", label: "Clean water level" },
64534
+ "dirty-water-level": { group: "Water", label: "Dirty water level" },
64535
+ "ctank-full": { group: "Water", label: "Clean water tank full" },
64536
+ "cmop-pump-low": { group: "Water", label: "Mop water running low", bad: "true" },
64537
+ "top-cover": { group: "Parts in place", label: "Top cover closed", bad: "false" },
64538
+ "hand-push-rod": { group: "Parts in place", label: "Push handle in place", bad: "false" },
64539
+ "clean-water-tank": { group: "Parts in place", label: "Clean water tank fitted", bad: "false" },
64540
+ "waste-water-tank": { group: "Parts in place", label: "Dirty water tank fitted", bad: "false" },
64541
+ "dust-box": { group: "Parts in place", label: "Dust box fitted", bad: "false" },
64542
+ "collision-left": { group: "Sensors", label: "Left bumper pressed", bad: "true" },
64543
+ "collision-right": { group: "Sensors", label: "Right bumper pressed", bad: "true" },
64544
+ "wfan-brake-flag": { group: "Sensors", label: "Water suction fan blocked", bad: "true" },
64545
+ "sfan-brake-flag": { group: "Sensors", label: "Dust suction fan blocked", bad: "true" },
64546
+ "wfan-brake-percent": { group: "Sensors", label: "Water suction fan blockage", unit: "%" },
64547
+ "sfan-brake-percent": { group: "Sensors", label: "Dust suction fan blockage", unit: "%" },
64548
+ job: { group: "Current job", label: "Job" },
64549
+ status: { group: "Current job", label: "Work status" },
64550
+ "acc-percent": { group: "Current job", label: "Job done", unit: "%" },
64551
+ "acc-area": { group: "Current job", label: "Area cleaned", unit: "m\xB2" },
64552
+ "count-area": { group: "Current job", label: "Area planned", unit: "m\xB2" },
64553
+ "acc-mile": { group: "Current job", label: "Distance driven", unit: "m" },
64554
+ "acc-time": { group: "Current job", label: "Cleaning time" },
64555
+ "acc-task": { group: "Current job", label: "Jobs counted" },
64556
+ "avg-speed": { group: "Current job", label: "Average speed", unit: "m\xB2/s" },
64557
+ x: { group: "Position", label: "Position x", unit: "m" },
64558
+ y: { group: "Position", label: "Position y", unit: "m" },
64559
+ theta: { group: "Position", label: "Heading", unit: "rad" },
64560
+ "mcu-state": { group: "Connection", label: "Main board connected", bad: "false" },
64561
+ bslink: { group: "Connection", label: "Linked to the base station" },
64562
+ RouterSignalStrength: { group: "Connection", label: "Mobile signal" },
64563
+ IsOfflineMode: { group: "Connection", label: "Offline mode", bad: "true" },
64564
+ OfflineVersion: { group: "Software", label: "Offline map version" },
64565
+ McuSW: { group: "Software", label: "Main board software" },
64566
+ FaceH7SW: { group: "Software", label: "Front panel software" },
64567
+ SlamType: { group: "Software", label: "Mapping type" },
64568
+ LockType: { group: "Software", label: "Lock type" }
64569
+ };
64570
+ var STATION_READINGS = {
64571
+ "clean-water": { group: "Base station", label: "Station clean water", unit: "L" },
64572
+ "dirty-water": { group: "Base station", label: "Station dirty water", unit: "L" },
64573
+ "clean-percent": { group: "Base station", label: "Station clean water", unit: "%" },
64574
+ "dirty-percent": { group: "Base station", label: "Station dirty water", unit: "%" },
64575
+ temperature: { group: "Base station", label: "Station temperature", unit: "\xB0C" },
64576
+ "bluetooth-err": { group: "Base station", label: "Bluetooth fault", bad: "true" },
64577
+ "charge-err": { group: "Base station", label: "Charging fault", bad: "true" },
64578
+ "clean-box-err": { group: "Base station", label: "Clean water box fault", bad: "true" },
64579
+ "clean-pump-err": { group: "Base station", label: "Clean water pump fault", bad: "true" },
64580
+ "dirty-box-err": { group: "Base station", label: "Dirty water box fault", bad: "true" },
64581
+ "dirty-pump-err": { group: "Base station", label: "Dirty water pump fault", bad: "true" },
64582
+ "dust-box-err": { group: "Base station", label: "Dust box fault", bad: "true" },
64583
+ "dust-fan-err": { group: "Base station", label: "Dust fan fault", bad: "true" },
64584
+ "ir-err": { group: "Base station", label: "Docking sensor fault", bad: "true" },
64585
+ "solenoid-err": { group: "Base station", label: "Water valve fault", bad: "true" },
64586
+ "temperature-err": { group: "Base station", label: "Temperature fault", bad: "true" },
64587
+ "water-sensor-err": { group: "Base station", label: "Water sensor fault", bad: "true" }
64588
+ };
64589
+ var HIDDEN_READINGS = /* @__PURE__ */ new Set(["RobotIP", "RouterIccid"]);
64590
+ var LEVEL_READING = { \u4F4E: "Low", \u4E2D: "Medium", \u9AD8: "High", \u7A7A: "Empty", \u6EE1: "Full" };
64591
+ function ounitechReadings(props, station = false) {
64592
+ const defs = station ? STATION_READINGS : READINGS;
64593
+ const out = [];
64594
+ for (const p of Array.isArray(props) ? props : []) {
64595
+ const key = String(p?.key ?? "").trim();
64596
+ if (!key || HIDDEN_READINGS.has(key))
64597
+ continue;
64598
+ const raw = p?.value == null ? "" : String(p.value).trim();
64599
+ if (raw === "" || raw === "-")
64600
+ continue;
64601
+ const d = defs[key] ?? { group: station ? "Base station" : "Other readings", label: key };
64602
+ let value;
64603
+ if (raw === "true" || raw === "false")
64604
+ value = raw === "true" ? "Yes" : "No";
64605
+ else if (key === "job")
64606
+ value = JOB_WORDS[raw] ?? raw;
64607
+ else if (key === "status")
64608
+ value = ROBOT_STATUS_NAMES[STATUS_CODE_BY_READING[raw] ?? -1] ?? raw;
64609
+ else if (LEVEL_READING[raw])
64610
+ value = LEVEL_READING[raw];
64611
+ else if (key === "acc-time" && num(raw) !== void 0)
64612
+ value = `${Math.round(num(raw) / 60)} min`;
64613
+ else
64614
+ value = d.unit === "%" ? `${raw}%` : d.unit ? `${raw} ${d.unit}` : raw;
64615
+ out.push({ key, group: d.group, label: d.label, value, attention: !!d.bad && raw === d.bad });
64616
+ }
64617
+ return out;
64618
+ }
64619
+ var PART_WORDS = {
64620
+ left_side_brush_plastic: "Left side brush",
64621
+ right_side_brush_plastic: "Right side brush",
64622
+ dust_bag: "Dust bag",
64623
+ single_suction_mouth_rubber: "Suction rubber",
64624
+ floor_brush_double_roller_structure: "Floor brush rollers",
64625
+ floor_mop_double_roller_structure: "Mop rollers"
64626
+ };
64627
+ var upFirst = (t) => t.charAt(0).toUpperCase() + t.slice(1);
64628
+ function ounitechConsumable(u) {
64629
+ const code = String(u.unitcode ?? "").trim();
64630
+ const minutes = num(u.workminutes);
64631
+ return {
64632
+ part: PART_WORDS[code] ?? upFirst(code.replace(/_/g, " ") || String(u.unitname ?? "").trim() || "Part"),
64633
+ hours: minutes !== void 0 ? Math.round(minutes / 6) / 10 : null,
64634
+ days: num(u.workdays) ?? null
64635
+ };
64636
+ }
64637
+ function ounitechPowerPlan(p) {
64638
+ return {
64639
+ days: (Array.isArray(p.dateList) ? p.dateList : []).map(Number).filter((d) => d >= 1 && d <= 7),
64640
+ time: String(p.actionTime ?? "").trim(),
64641
+ action: Number(p.actionFlag) === 1 ? "on" : "off",
64642
+ enabled: p.enableFlag !== false
64643
+ };
64644
+ }
64645
+ var MAP_TTL_MS = 10 * 6e4;
64646
+ var RECORDS_TTL_MS = 2 * 6e4;
64647
+ var mapCache = /* @__PURE__ */ new Map();
64648
+ var recordsCache = /* @__PURE__ */ new Map();
64649
+ function cached2(cache3, field, key, ttl, load) {
64650
+ const hit = cache3.get(key);
64651
+ if (hit && Date.now() - hit.at < ttl)
64652
+ return hit[field];
64653
+ const p = load();
64654
+ cache3.set(key, { at: Date.now(), [field]: p });
64655
+ p.catch(() => cache3.delete(key));
64656
+ return p;
64657
+ }
64658
+ function clearOunitechCaches() {
64659
+ mapCache.clear();
64660
+ recordsCache.clear();
64661
+ }
64346
64662
  var robotTime = (d) => robotCloudTimestamp(d, "yyyy-MM-dd HH:mm:ss", "Asia/Shanghai");
64347
64663
  function createOunitechAdapter(credentials, options) {
64348
64664
  const cloud = useRobotCloudService(credentials, options);
64349
64665
  async function liveFor(row) {
64350
64666
  return needsLiveState(row) ? cloud.getRobotState(row.robotId).catch(() => null) : null;
64351
64667
  }
64668
+ function floorMaps(sceneId) {
64669
+ return cached2(mapCache, "maps", `${options?.baseUrl ?? ""}|${credentials.appid}|${sceneId}`, MAP_TTL_MS, async () => {
64670
+ const list = (await cloud.getFloorMaps(sceneId)).filter((m) => m.latestFlag !== false);
64671
+ const keys = list.flatMap((m) => [m.backgroundFileKey, m.partitionFileKey]).filter((k) => typeof k === "string" && !!k);
64672
+ const files = keys.length ? await cloud.previewFiles(keys).catch(() => []) : [];
64673
+ const url2 = (k) => files.find((f) => f.fileKey === k)?.url || null;
64674
+ return Promise.all(
64675
+ list.map(async (m) => {
64676
+ const imageUrl = url2(m.backgroundFileKey);
64677
+ return ounitechMapView(m, imageUrl, url2(m.partitionFileKey), imageUrl ? await fetchPngSize(imageUrl) : null);
64678
+ })
64679
+ );
64680
+ });
64681
+ }
64682
+ async function placed(row, robot) {
64683
+ if (!robot.online || !finite(row.sceneId))
64684
+ return robot;
64685
+ const maps = await floorMaps(row.sceneId).catch(() => []);
64686
+ const map = ounitechCurrentMap(maps, row.taskState?.mapId, robot.floorNo);
64687
+ if (!map)
64688
+ return robot;
64689
+ robot.mapId = map.mapId;
64690
+ robot.planPosition = robot.position ? ounitechMapShare(map, robot.position.x, robot.position.y) : null;
64691
+ return robot;
64692
+ }
64352
64693
  async function rowFor(robotSn) {
64353
64694
  return (await cloud.getHomeRobots()).find((r) => r.robotSn === robotSn) ?? null;
64354
64695
  }
@@ -64357,7 +64698,9 @@ function createOunitechAdapter(credentials, options) {
64357
64698
  displayName: "Ounitech (Q3-G / Q3-W)",
64358
64699
  capabilities: OUNITECH_CAPABILITIES,
64359
64700
  async listRobots() {
64360
- return Promise.all((await cloud.getHomeRobots()).map(async (row) => ounitechRobotFromHomeRow(row, await liveFor(row))));
64701
+ return Promise.all(
64702
+ (await cloud.getHomeRobots()).map(async (row) => placed(row, ounitechRobotFromHomeRow(row, await liveFor(row))))
64703
+ );
64361
64704
  },
64362
64705
  async getRobot(robotSn) {
64363
64706
  const row = await rowFor(robotSn);
@@ -64373,7 +64716,7 @@ function createOunitechAdapter(credentials, options) {
64373
64716
  position: null
64374
64717
  };
64375
64718
  }
64376
- return ounitechRobotFromHomeRow(row, await liveFor(row));
64719
+ return placed(row, ounitechRobotFromHomeRow(row, await liveFor(row)));
64377
64720
  },
64378
64721
  async sendCommand(robotSn, command) {
64379
64722
  const options2 = {
@@ -64401,31 +64744,16 @@ function createOunitechAdapter(credentials, options) {
64401
64744
  );
64402
64745
  }
64403
64746
  },
64404
- /** Chapter 6 floor maps, in the chapter-2 shape the screens read (walls left out - they are large). */
64747
+ /**
64748
+ * Chapter 6 floor maps (walls left out - they are large): the chapter-2
64749
+ * fields plus `mapId`, `imageUrl`, `width` / `height` (from the PNG) and
64750
+ * the areas' centres, so robot detail draws the real map with the robot on it.
64751
+ */
64405
64752
  async getMaps(robotSn) {
64406
64753
  const row = await rowFor(robotSn);
64407
64754
  if (!row || !finite(row.sceneId))
64408
64755
  return [];
64409
- return (await cloud.getFloorMaps(row.sceneId)).filter((m) => m.latestFlag !== false).map((m) => ({
64410
- floorNo: m.floorNo,
64411
- mapName: m.mapName,
64412
- backgroundFileKey: m.backgroundFileKey,
64413
- partitionFileKey: m.partitionFileKey,
64414
- originX: m.originX,
64415
- originY: m.originY,
64416
- resolution: m.resolution,
64417
- totalArea: m.totalArea,
64418
- baseX: m.baseX,
64419
- baseY: m.baseY,
64420
- baseTheta: m.baseTheta,
64421
- createTime: m.createTime,
64422
- areaList: (Array.isArray(m.areaList) ? m.areaList : []).map((a) => ({
64423
- areaName: a.areaName,
64424
- rgba: a.rgba,
64425
- x: a.x,
64426
- y: a.y
64427
- }))
64428
- }));
64756
+ return floorMaps(row.sceneId);
64429
64757
  },
64430
64758
  async getMapImages(_robotSn, fileKeys) {
64431
64759
  return cloud.previewFiles(fileKeys);
@@ -64444,6 +64772,57 @@ function createOunitechAdapter(credentials, options) {
64444
64772
  jobList: p.cleanList ?? p.jobList ?? []
64445
64773
  }));
64446
64774
  },
64775
+ /**
64776
+ * Robot detail's records (read-only, cached 2 min - the vendor rate-limits):
64777
+ * cleaning jobs (14 days), alert history (30 days), consumable hours, power
64778
+ * schedule, lifts, every live reading and the base station. Reads run one
64779
+ * after another (gentler on the rate limit); each part carries its own error.
64780
+ */
64781
+ async getRecords(robotSn) {
64782
+ return cached2(recordsCache, "value", `${options?.baseUrl ?? ""}|${credentials.appid}|${robotSn}`, RECORDS_TTL_MS, async () => {
64783
+ const row = await rowFor(robotSn);
64784
+ if (!row || !finite(row.robotId))
64785
+ return { supported: true, error: `Serial ${robotSn} is not on this Ounitech account.` };
64786
+ const robotId = row.robotId;
64787
+ const tz = finite(row.timezone) ? row.timezone : 480;
64788
+ const now = /* @__PURE__ */ new Date();
64789
+ const since = (days) => robotTime(new Date(now.getTime() - days * 864e5));
64790
+ const part = async (read2) => {
64791
+ try {
64792
+ return { items: await read2() };
64793
+ } catch (e) {
64794
+ return { items: [], error: String(e?.message ?? e).slice(0, 300) };
64795
+ }
64796
+ };
64797
+ const maps = finite(row.sceneId) ? await floorMaps(row.sceneId).catch(() => []) : [];
64798
+ const tasks = await part(
64799
+ async () => ((await cloud.getTaskList(robotId, since(14), robotTime(now))).taskList ?? []).map((t) => ounitechTaskRecord(t, maps, tz)).sort((a, b) => String(b.start ?? "").localeCompare(String(a.start ?? ""))).slice(0, 50)
64800
+ );
64801
+ const alerts = await part(
64802
+ async () => ((await cloud.getAlerts(robotId, since(30), robotTime(now))).alertList ?? []).map((a) => ounitechAlertRecord(a, tz))
64803
+ );
64804
+ const consumables = await part(async () => ((await cloud.getWorkHours(robotId)).unitlist ?? []).map(ounitechConsumable));
64805
+ const power = await part(async () => ((await cloud.getHaltPlans(robotId)).planList ?? []).map(ounitechPowerPlan));
64806
+ const lifts = finite(row.sceneId) ? await part(
64807
+ async () => ((await cloud.getLiftList(row.sceneId)).liftlist ?? []).map((l) => ({
64808
+ name: String(l.liftname ?? "").trim() || `Lift ${l.liftno ?? ""}`.trim(),
64809
+ floorNo: Number.isInteger(l.floorno) ? l.floorno : null,
64810
+ online: Number(l.onlineflag) === 1,
64811
+ enabled: l.enableflag !== false
64812
+ }))
64813
+ ) : { items: [] };
64814
+ const readings = await part(async () => ounitechReadings((await cloud.getRobotState(robotId)).properties));
64815
+ const station = await part(async () => {
64816
+ const st = await cloud.getStationState(robotId).catch((e) => {
64817
+ if (/no station bound|e=59/i.test(String(e?.message ?? "")))
64818
+ return null;
64819
+ throw e;
64820
+ });
64821
+ return st ? [{ status: String(st.statusName ?? "").trim() || null, readings: ounitechReadings(st.properties, true) }] : [];
64822
+ });
64823
+ return { supported: true, readAt: now.toISOString(), tasks, alerts, consumables, power, lifts, readings, station };
64824
+ });
64825
+ },
64447
64826
  /**
64448
64827
  * Staff Diagnose: every other read-only chapter-6 call, with the vendor's
64449
64828
  * answer (lists cut to 3). Never a command, never the signed envelope.
@@ -64517,6 +64896,9 @@ function createOunitechAdapter(credentials, options) {
64517
64896
  const r = await cloud.getAlerts(robotId, window.timeFrom, window.timeTo);
64518
64897
  return { total: r.total ?? r.alertList?.length ?? 0, latest: cut(r.alertList ?? []) };
64519
64898
  });
64899
+ await run("consumable hours (get-work-hours)", ROBOT_CLOUD_PATHS.workHours, { robotId }, async () => cut((await cloud.getWorkHours(robotId)).unitlist ?? []));
64900
+ await run("power schedule (halt-plan/get)", ROBOT_CLOUD_PATHS.haltPlans, { robotId }, async () => cut((await cloud.getHaltPlans(robotId)).planList ?? []));
64901
+ await run("base station (get-station-detail-state)", ROBOT_CLOUD_PATHS.stationState, { robotId, options: "state" }, async () => cloud.getStationState(robotId));
64520
64902
  if (finite(row.sceneId)) {
64521
64903
  const sceneId = row.sceneId;
64522
64904
  await run("lifts (get-lift-list)", ROBOT_CLOUD_PATHS.liftList, { sceneid: sceneId }, async () => {
@@ -64550,7 +64932,7 @@ var OUNITECH_BRAND_DEFINITION = {
64550
64932
  { name: "Q3-G", codes: ["Q3G", "Q3-G"] },
64551
64933
  { name: "Q3-W", codes: ["Q3W", "Q3-W"] }
64552
64934
  ],
64553
- info: { makerApp: "the Ounitech app", makerAppOnly: ["pausing or stopping a job", "cleaning across floors"] },
64935
+ info: { makerApp: "the Ounitech app", makerAppOnly: ["pausing or stopping a job", "cleaning across floors", "changing maps, areas and schedules"] },
64554
64936
  create: (credentials) => createOunitechAdapter(credentials)
64555
64937
  };
64556
64938
  function registerOunitechBrand() {
@@ -65349,7 +65731,7 @@ function createOpenRmfClient(config2, deps) {
65349
65731
  throw new OpenRmfError("The fleet server sent a reply that is not JSON.");
65350
65732
  }
65351
65733
  }
65352
- function cached3(key, ttlMs, load) {
65734
+ function cached4(key, ttlMs, load) {
65353
65735
  const k = `${config2?.baseUrl}|${key}`;
65354
65736
  const hit = cache.get(k);
65355
65737
  if (hit && now() - hit.at < ttlMs)
@@ -65361,8 +65743,8 @@ function createOpenRmfClient(config2, deps) {
65361
65743
  }
65362
65744
  const enc2 = encodeURIComponent;
65363
65745
  return {
65364
- fleets: () => cached3("fleets", 1500, () => call("GET", "/fleets")),
65365
- buildingMap: () => cached3("building_map", 6e4, () => call("GET", "/building_map")),
65746
+ fleets: () => cached4("fleets", 1500, () => call("GET", "/fleets")),
65747
+ buildingMap: () => cached4("building_map", 6e4, () => call("GET", "/building_map")),
65366
65748
  doors: () => call("GET", "/doors"),
65367
65749
  doorState: (name) => call("GET", `/doors/${enc2(name)}/state`),
65368
65750
  doorRequest: (name, mode) => call("POST", `/doors/${enc2(name)}/request`, { mode }),
@@ -66806,7 +67188,7 @@ function mapSummary(m) {
66806
67188
  }
66807
67189
  var CACHE_TTL_MS = 5 * 6e4;
66808
67190
  var cache2 = /* @__PURE__ */ new Map();
66809
- function cached2(key, load) {
67191
+ function cached3(key, load) {
66810
67192
  const hit = cache2.get(key);
66811
67193
  if (hit && Date.now() - hit.at < CACHE_TTL_MS)
66812
67194
  return hit.value;
@@ -66892,8 +67274,8 @@ function createPadbotAdapter(credentials, options = {}) {
66892
67274
  const ns = `${credentials.appid}@${options.baseUrl ?? padbotBaseUrl()}`;
66893
67275
  const account = padbotAccountKey(credentials);
66894
67276
  const callRaw = call;
66895
- const roster = () => cached2(`${ns}:robots`, () => call(PADBOT_PATHS.robots, { robotTypes: ["PATROL"] }));
66896
- const maps = (sn) => cached2(`${ns}:maps:${sn}`, () => call(PADBOT_PATHS.maps, { serialNumber: sn }).then(asList));
67277
+ const roster = () => cached3(`${ns}:robots`, () => call(PADBOT_PATHS.robots, { robotTypes: ["PATROL"] }));
67278
+ const maps = (sn) => cached3(`${ns}:maps:${sn}`, () => call(PADBOT_PATHS.maps, { serialNumber: sn }).then(asList));
66897
67279
  const states = async (sn) => {
66898
67280
  const list = await call(PADBOT_PATHS.states, { serialNumbers: [sn] });
66899
67281
  const entry = (list ?? []).find((e) => e?.serialNumber === sn);
@@ -67461,6 +67843,12 @@ function useRobotFleetService(deps) {
67461
67843
  return [];
67462
67844
  return adapter.getMapImages(await resolveRobotSn(robot), fileKeys);
67463
67845
  }
67846
+ async function getRecords(robot) {
67847
+ const adapter = adapterFor(robot);
67848
+ if (!adapter.getRecords)
67849
+ return null;
67850
+ return adapter.getRecords(await resolveRobotSn(robot));
67851
+ }
67464
67852
  async function getPlans(robot) {
67465
67853
  const adapter = adapterFor(robot);
67466
67854
  if (!adapter.getPlans)
@@ -67830,6 +68218,7 @@ function useRobotFleetService(deps) {
67830
68218
  getMaps,
67831
68219
  getMapImages,
67832
68220
  getPlans,
68221
+ getRecords,
67833
68222
  getPatrolRoutes,
67834
68223
  dispatch: dispatch2
67835
68224
  };
@@ -70423,9 +70812,9 @@ function rmfSummary(rmf) {
70423
70812
  }
70424
70813
 
70425
70814
  // src/services/robot-tracking.service.ts
70426
- import axios4 from "axios";
70815
+ import axios5 from "axios";
70427
70816
  async function openWithAxios(url2, body) {
70428
- const response = await axios4.post(url2, body, {
70817
+ const response = await axios5.post(url2, body, {
70429
70818
  responseType: "stream",
70430
70819
  // No read timeout: this connection is SUPPOSED to stay open and mostly
70431
70820
  // silent. A request timeout here would sever a healthy stream on a quiet
@@ -70638,6 +71027,14 @@ function useRobotFleetController(deps) {
70638
71027
  fail(next, error);
70639
71028
  }
70640
71029
  }
71030
+ async function getRecords(req, res, next) {
71031
+ try {
71032
+ const robot = await entitleRobot(req, req.params.id);
71033
+ res.json(await getFleet2().getRecords(robot) ?? { supported: false });
71034
+ } catch (error) {
71035
+ fail(next, error);
71036
+ }
71037
+ }
70641
71038
  async function getPatrolRoutes(req, res, next) {
70642
71039
  try {
70643
71040
  const robot = await entitleRobot(req, req.params.id);
@@ -70931,6 +71328,7 @@ function useRobotFleetController(deps) {
70931
71328
  getMaps,
70932
71329
  getMapImages,
70933
71330
  getPlans,
71331
+ getRecords,
70934
71332
  getPatrolRoutes,
70935
71333
  sendCommand: sendCommand2,
70936
71334
  trackRobot,
@@ -79699,13 +80097,13 @@ function useSiteBillingItemRepo() {
79699
80097
  }
79700
80098
  const cacheKey = makeCacheKey44(namespace_collection3, { _id: String(_id) });
79701
80099
  try {
79702
- const cached3 = await getCache(cacheKey);
79703
- if (cached3) {
80100
+ const cached4 = await getCache(cacheKey);
80101
+ if (cached4) {
79704
80102
  logger142.log({
79705
80103
  level: "info",
79706
80104
  message: `Cache hit for getById site billing items: ${cacheKey}`
79707
80105
  });
79708
- return cached3;
80106
+ return cached4;
79709
80107
  }
79710
80108
  const result = await collection.findOne({
79711
80109
  _id
@@ -80073,13 +80471,13 @@ function useSiteBillingConfigurationRepo() {
80073
80471
  }
80074
80472
  const cacheKey = makeCacheKey45(namespace_collection3, { _id: String(_id) });
80075
80473
  try {
80076
- const cached3 = await getCache(cacheKey);
80077
- if (cached3) {
80474
+ const cached4 = await getCache(cacheKey);
80475
+ if (cached4) {
80078
80476
  logger144.log({
80079
80477
  level: "info",
80080
80478
  message: `Cache hit for getById site billing configuration: ${cacheKey}`
80081
80479
  });
80082
- return cached3;
80480
+ return cached4;
80083
80481
  }
80084
80482
  const result = await collection.findOne({
80085
80483
  _id
@@ -81750,13 +82148,13 @@ function useSiteUnitBillingRepo() {
81750
82148
  }
81751
82149
  const cacheKey = makeCacheKey47(namespace_collection3, { _id: String(_id) });
81752
82150
  try {
81753
- const cached3 = await getCache(cacheKey);
81754
- if (cached3) {
82151
+ const cached4 = await getCache(cacheKey);
82152
+ if (cached4) {
81755
82153
  logger152.log({
81756
82154
  level: "info",
81757
82155
  message: `Cache hit for getById site unit billing: ${cacheKey}`
81758
82156
  });
81759
- return cached3;
82157
+ return cached4;
81760
82158
  }
81761
82159
  const result = await collection.findOne({
81762
82160
  _id
@@ -84581,13 +84979,13 @@ function useNfcPatrolRouteRepo() {
84581
84979
  }
84582
84980
  const cacheKey = makeCacheKey49(namespace_collection3, cacheParams);
84583
84981
  try {
84584
- const cached3 = await getCache(cacheKey);
84585
- if (cached3) {
84982
+ const cached4 = await getCache(cacheKey);
84983
+ if (cached4) {
84586
84984
  logger157.log({
84587
84985
  level: "info",
84588
84986
  message: `Cache hit for getById ${namespace_collection3}: ${cacheKey}`
84589
84987
  });
84590
- return cached3;
84988
+ return cached4;
84591
84989
  }
84592
84990
  let result;
84593
84991
  if (isStart === true) {
@@ -86057,13 +86455,13 @@ function useStatementOfAccountRepo() {
86057
86455
  }
86058
86456
  const cacheKey = makeCacheKey51(namespace_collection3, { _id: String(_id) });
86059
86457
  try {
86060
- const cached3 = await getCache(cacheKey);
86061
- if (cached3) {
86458
+ const cached4 = await getCache(cacheKey);
86459
+ if (cached4) {
86062
86460
  logger163.log({
86063
86461
  level: "info",
86064
86462
  message: `Cache hit for getById soa: ${cacheKey}`
86065
86463
  });
86066
- return cached3;
86464
+ return cached4;
86067
86465
  }
86068
86466
  const result = await collection.findOne({
86069
86467
  _id
@@ -93237,7 +93635,7 @@ import {
93237
93635
  } from "@7365admin1/node-server-utils";
93238
93636
 
93239
93637
  // src/utils/hrmlabs-attendance.util.ts
93240
- import axios5 from "axios";
93638
+ import axios6 from "axios";
93241
93639
  import moment8 from "moment-timezone";
93242
93640
  var default_early_checkIn = 4;
93243
93641
  async function hrmLabsAuthentication({
@@ -93246,7 +93644,7 @@ async function hrmLabsAuthentication({
93246
93644
  password,
93247
93645
  domain
93248
93646
  }) {
93249
- const res = await axios5.post(
93647
+ const res = await axios6.post(
93250
93648
  authUrl,
93251
93649
  {
93252
93650
  grant_type: "password",
@@ -93276,7 +93674,7 @@ async function fetchAttendanceData({
93276
93674
  search
93277
93675
  }) {
93278
93676
  try {
93279
- const res = await axios5.post(
93677
+ const res = await axios6.post(
93280
93678
  attendanceUrl,
93281
93679
  {
93282
93680
  start: startDate,
@@ -93476,7 +93874,7 @@ async function fetchSites({ siteUrl, token }) {
93476
93874
  do {
93477
93875
  try {
93478
93876
  attempt++;
93479
- const res = await axios5.get(siteUrl, {
93877
+ const res = await axios6.get(siteUrl, {
93480
93878
  headers: { Authorization: `Bearer ${token}` },
93481
93879
  timeout: 15e3
93482
93880
  });
@@ -97077,7 +97475,7 @@ async function manpowerEvents(io) {
97077
97475
  }
97078
97476
 
97079
97477
  // src/services/reddot-payment.service.ts
97080
- import axios6 from "axios";
97478
+ import axios7 from "axios";
97081
97479
 
97082
97480
  // src/utils/payment-signature.util.ts
97083
97481
  import * as crypto11 from "crypto";
@@ -97719,7 +98117,7 @@ var useRedDotPaymentSvc = () => {
97719
98117
  );
97720
98118
  }
97721
98119
  const url2 = process.env.MERCHANT_PAYMENT;
97722
- const response = await axios6.post(url2, dataString, { headers });
98120
+ const response = await axios7.post(url2, dataString, { headers });
97723
98121
  const result = response.data;
97724
98122
  return result;
97725
98123
  } catch (error) {
@@ -97753,7 +98151,7 @@ var useRedDotPaymentSvc = () => {
97753
98151
  );
97754
98152
  }
97755
98153
  const url2 = process.env.MERCHANT_ENQUIRY;
97756
- const response = await axios6.post(url2, dataString, { headers });
98154
+ const response = await axios7.post(url2, dataString, { headers });
97757
98155
  const result = response.data;
97758
98156
  const transactionId = result.transaction_id;
97759
98157
  const amount = result.request_amount || 0;
@@ -107032,6 +107430,7 @@ export {
107032
107430
  claimReadsAsStale,
107033
107431
  clampChassis,
107034
107432
  clampPtzSpeed,
107433
+ clearOunitechCaches,
107035
107434
  clearPadbotCache,
107036
107435
  clearRobotBrands,
107037
107436
  clockDriftSeconds,
@@ -107225,10 +107624,19 @@ export {
107225
107624
  orgQualifiesForOwnerRepair,
107226
107625
  orgRoleSets,
107227
107626
  orgSchema,
107627
+ ounitechAlertRecord,
107228
107628
  ounitechCleaning,
107629
+ ounitechConsumable,
107630
+ ounitechCurrentMap,
107229
107631
  ounitechFault,
107230
107632
  ounitechJobWords,
107633
+ ounitechMapShare,
107634
+ ounitechMapView,
107635
+ ounitechPowerPlan,
107636
+ ounitechReadings,
107231
107637
  ounitechRobotFromHomeRow,
107638
+ ounitechTaskRecord,
107639
+ ounitechTime,
107232
107640
  overnight_parking_requests_namespace_collection,
107233
107641
  padbotAccountKey,
107234
107642
  padbotAlarmFault,
@@ -107281,6 +107689,7 @@ export {
107281
107689
  platform_terms_namespace_collection,
107282
107690
  playbackRelays,
107283
107691
  playbackWindowRefusal,
107692
+ pngSize,
107284
107693
  promoCodeRefusal,
107285
107694
  promoCodeSchema,
107286
107695
  promoCodeStatusSchema,