@mduan/paseo-cli 0.11.0-fork.30 → 0.11.0-fork.31

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.
Files changed (31) hide show
  1. package/node_modules/@getpaseo/client/dist/daemon-client.d.ts +3 -0
  2. package/node_modules/@getpaseo/client/dist/daemon-client.js +7 -0
  3. package/node_modules/@getpaseo/client/package.json +3 -3
  4. package/node_modules/@getpaseo/highlight/package.json +1 -1
  5. package/node_modules/@getpaseo/plugin/package.json +3 -3
  6. package/node_modules/@getpaseo/protocol/dist/generated/validation/ws-outbound.aot.js +9979 -9947
  7. package/node_modules/@getpaseo/protocol/dist/messages.d.ts +53 -0
  8. package/node_modules/@getpaseo/protocol/dist/messages.js +18 -0
  9. package/node_modules/@getpaseo/protocol/dist/validation/ws-outbound-schema-metadata.d.ts +8 -0
  10. package/node_modules/@getpaseo/protocol/package.json +1 -1
  11. package/node_modules/@getpaseo/relay/package.json +1 -1
  12. package/node_modules/@getpaseo/server/dist/server/builtin-plugins/package.json +1 -1
  13. package/node_modules/@getpaseo/server/dist/server/server/authorization/operation-permissions.js +2 -0
  14. package/node_modules/@getpaseo/server/dist/server/server/session.d.ts +1 -0
  15. package/node_modules/@getpaseo/server/dist/server/server/session.js +38 -0
  16. package/node_modules/@getpaseo/server/dist/server/server/websocket-server.js +1 -0
  17. package/node_modules/@getpaseo/server/dist/server/server/workspace-git-service.d.ts +1 -0
  18. package/node_modules/@getpaseo/server/dist/server/server/workspace-git-service.js +2 -2
  19. package/node_modules/@getpaseo/server/dist/server/server/workspace-ports/service.d.ts +5 -2
  20. package/node_modules/@getpaseo/server/dist/server/server/workspace-ports/service.js +24 -7
  21. package/node_modules/@getpaseo/server/dist/server/services/linear-integration.d.ts +5 -2
  22. package/node_modules/@getpaseo/server/dist/server/services/linear-integration.js +8 -4
  23. package/node_modules/@getpaseo/server/dist/server/web-ui/_expo/static/js/web/{index-d073261c6c171ec5910a051220471a65.js → index-1c2f6e52d2d7067032060f5f520417a8.js} +22 -22
  24. package/node_modules/@getpaseo/server/dist/server/web-ui/_expo/static/js/web/index-1c2f6e52d2d7067032060f5f520417a8.js.br +0 -0
  25. package/node_modules/@getpaseo/server/dist/server/web-ui/_expo/static/js/web/{index-d073261c6c171ec5910a051220471a65.js.gz → index-1c2f6e52d2d7067032060f5f520417a8.js.gz} +0 -0
  26. package/node_modules/@getpaseo/server/dist/server/web-ui/index.html +1 -1
  27. package/node_modules/@getpaseo/server/dist/server/web-ui/index.html.br +0 -0
  28. package/node_modules/@getpaseo/server/dist/server/web-ui/index.html.gz +0 -0
  29. package/node_modules/@getpaseo/server/package.json +6 -6
  30. package/package.json +7 -7
  31. package/node_modules/@getpaseo/server/dist/server/web-ui/_expo/static/js/web/index-d073261c6c171ec5910a051220471a65.js.br +0 -0
@@ -718,6 +718,20 @@ export declare const WorkspaceLinearIssuesUpdateRequestSchema: z.ZodObject<{
718
718
  remove: z.ZodOptional<z.ZodArray<z.ZodString>>;
719
719
  requestId: z.ZodString;
720
720
  }, z.core.$strip>;
721
+ export declare const WorkspaceRefreshMetadataRequestSchema: z.ZodObject<{
722
+ type: z.ZodLiteral<"workspace.refresh_metadata.request">;
723
+ workspaceId: z.ZodString;
724
+ requestId: z.ZodString;
725
+ }, z.core.$strip>;
726
+ export declare const WorkspaceRefreshMetadataResponseSchema: z.ZodObject<{
727
+ type: z.ZodLiteral<"workspace.refresh_metadata.response">;
728
+ payload: z.ZodObject<{
729
+ requestId: z.ZodString;
730
+ workspaceId: z.ZodString;
731
+ success: z.ZodBoolean;
732
+ error: z.ZodOptional<z.ZodString>;
733
+ }, z.core.$strip>;
734
+ }, z.core.$strip>;
721
735
  export declare const WorkspaceLinearIssuesUpdateResponseSchema: z.ZodObject<{
722
736
  type: z.ZodLiteral<"workspace.linear_issues.update.response">;
723
737
  payload: z.ZodObject<{
@@ -5362,6 +5376,10 @@ export declare const SessionInboundMessageSchema: z.ZodDiscriminatedUnion<[z.Zod
5362
5376
  add: z.ZodOptional<z.ZodArray<z.ZodString>>;
5363
5377
  remove: z.ZodOptional<z.ZodArray<z.ZodString>>;
5364
5378
  requestId: z.ZodString;
5379
+ }, z.core.$strip>, z.ZodObject<{
5380
+ type: z.ZodLiteral<"workspace.refresh_metadata.request">;
5381
+ workspaceId: z.ZodString;
5382
+ requestId: z.ZodString;
5365
5383
  }, z.core.$strip>, z.ZodObject<{
5366
5384
  type: z.ZodLiteral<"integrations.linear.get_connection.request">;
5367
5385
  requestId: z.ZodString;
@@ -7950,6 +7968,7 @@ export declare const ServerInfoStatusPayloadSchema: z.ZodPipe<z.ZodObject<{
7950
7968
  directorySync: z.ZodOptional<z.ZodBoolean>;
7951
7969
  workspaceLabels: z.ZodOptional<z.ZodBoolean>;
7952
7970
  workspaceLinearIssues: z.ZodOptional<z.ZodBoolean>;
7971
+ workspaceMetadataRefresh: z.ZodOptional<z.ZodBoolean>;
7953
7972
  linearIntegration: z.ZodOptional<z.ZodBoolean>;
7954
7973
  workspaceSetupRun: z.ZodOptional<z.ZodBoolean>;
7955
7974
  turnDiffs: z.ZodOptional<z.ZodBoolean>;
@@ -8070,6 +8089,7 @@ export declare const ServerInfoStatusPayloadSchema: z.ZodPipe<z.ZodObject<{
8070
8089
  directorySync?: boolean | undefined;
8071
8090
  workspaceLabels?: boolean | undefined;
8072
8091
  workspaceLinearIssues?: boolean | undefined;
8092
+ workspaceMetadataRefresh?: boolean | undefined;
8073
8093
  linearIntegration?: boolean | undefined;
8074
8094
  workspaceSetupRun?: boolean | undefined;
8075
8095
  turnDiffs?: boolean | undefined;
@@ -8191,6 +8211,7 @@ export declare const ServerInfoStatusPayloadSchema: z.ZodPipe<z.ZodObject<{
8191
8211
  directorySync?: boolean | undefined;
8192
8212
  workspaceLabels?: boolean | undefined;
8193
8213
  workspaceLinearIssues?: boolean | undefined;
8214
+ workspaceMetadataRefresh?: boolean | undefined;
8194
8215
  linearIntegration?: boolean | undefined;
8195
8216
  workspaceSetupRun?: boolean | undefined;
8196
8217
  turnDiffs?: boolean | undefined;
@@ -34037,6 +34058,14 @@ export declare const SessionOutboundMessageSchema: z.ZodDiscriminatedUnion<[z.Zo
34037
34058
  }, z.core.$strip>>;
34038
34059
  error: z.ZodNullable<z.ZodString>;
34039
34060
  }, z.core.$strip>;
34061
+ }, z.core.$strip>, z.ZodObject<{
34062
+ type: z.ZodLiteral<"workspace.refresh_metadata.response">;
34063
+ payload: z.ZodObject<{
34064
+ requestId: z.ZodString;
34065
+ workspaceId: z.ZodString;
34066
+ success: z.ZodBoolean;
34067
+ error: z.ZodOptional<z.ZodString>;
34068
+ }, z.core.$strip>;
34040
34069
  }, z.core.$strip>, z.ZodObject<{
34041
34070
  type: z.ZodLiteral<"integrations.linear.get_connection.response">;
34042
34071
  payload: z.ZodObject<{
@@ -38718,6 +38747,10 @@ export declare const WSSessionInboundSchema: z.ZodObject<{
38718
38747
  add: z.ZodOptional<z.ZodArray<z.ZodString>>;
38719
38748
  remove: z.ZodOptional<z.ZodArray<z.ZodString>>;
38720
38749
  requestId: z.ZodString;
38750
+ }, z.core.$strip>, z.ZodObject<{
38751
+ type: z.ZodLiteral<"workspace.refresh_metadata.request">;
38752
+ workspaceId: z.ZodString;
38753
+ requestId: z.ZodString;
38721
38754
  }, z.core.$strip>, z.ZodObject<{
38722
38755
  type: z.ZodLiteral<"integrations.linear.get_connection.request">;
38723
38756
  requestId: z.ZodString;
@@ -50995,6 +51028,14 @@ export declare const WSSessionOutboundSchema: z.ZodObject<{
50995
51028
  }, z.core.$strip>>;
50996
51029
  error: z.ZodNullable<z.ZodString>;
50997
51030
  }, z.core.$strip>;
51031
+ }, z.core.$strip>, z.ZodObject<{
51032
+ type: z.ZodLiteral<"workspace.refresh_metadata.response">;
51033
+ payload: z.ZodObject<{
51034
+ requestId: z.ZodString;
51035
+ workspaceId: z.ZodString;
51036
+ success: z.ZodBoolean;
51037
+ error: z.ZodOptional<z.ZodString>;
51038
+ }, z.core.$strip>;
50998
51039
  }, z.core.$strip>, z.ZodObject<{
50999
51040
  type: z.ZodLiteral<"integrations.linear.get_connection.response">;
51000
51041
  payload: z.ZodObject<{
@@ -55315,6 +55356,10 @@ export declare const WSInboundMessageSchema: z.ZodDiscriminatedUnion<[z.ZodObjec
55315
55356
  add: z.ZodOptional<z.ZodArray<z.ZodString>>;
55316
55357
  remove: z.ZodOptional<z.ZodArray<z.ZodString>>;
55317
55358
  requestId: z.ZodString;
55359
+ }, z.core.$strip>, z.ZodObject<{
55360
+ type: z.ZodLiteral<"workspace.refresh_metadata.request">;
55361
+ workspaceId: z.ZodString;
55362
+ requestId: z.ZodString;
55318
55363
  }, z.core.$strip>, z.ZodObject<{
55319
55364
  type: z.ZodLiteral<"integrations.linear.get_connection.request">;
55320
55365
  requestId: z.ZodString;
@@ -67594,6 +67639,14 @@ export declare const WSOutboundMessageSchema: z.ZodDiscriminatedUnion<[z.ZodObje
67594
67639
  }, z.core.$strip>>;
67595
67640
  error: z.ZodNullable<z.ZodString>;
67596
67641
  }, z.core.$strip>;
67642
+ }, z.core.$strip>, z.ZodObject<{
67643
+ type: z.ZodLiteral<"workspace.refresh_metadata.response">;
67644
+ payload: z.ZodObject<{
67645
+ requestId: z.ZodString;
67646
+ workspaceId: z.ZodString;
67647
+ success: z.ZodBoolean;
67648
+ error: z.ZodOptional<z.ZodString>;
67649
+ }, z.core.$strip>;
67597
67650
  }, z.core.$strip>, z.ZodObject<{
67598
67651
  type: z.ZodLiteral<"integrations.linear.get_connection.response">;
67599
67652
  payload: z.ZodObject<{
@@ -874,6 +874,20 @@ export const WorkspaceLinearIssuesUpdateRequestSchema = z.object({
874
874
  remove: z.array(z.string()).optional(),
875
875
  requestId: z.string(),
876
876
  });
877
+ export const WorkspaceRefreshMetadataRequestSchema = z.object({
878
+ type: z.literal("workspace.refresh_metadata.request"),
879
+ workspaceId: z.string(),
880
+ requestId: z.string(),
881
+ });
882
+ export const WorkspaceRefreshMetadataResponseSchema = z.object({
883
+ type: z.literal("workspace.refresh_metadata.response"),
884
+ payload: z.object({
885
+ requestId: z.string(),
886
+ workspaceId: z.string(),
887
+ success: z.boolean(),
888
+ error: z.string().optional(),
889
+ }),
890
+ });
877
891
  export const WorkspaceLinearIssuesUpdateResponseSchema = z.object({
878
892
  type: z.literal("workspace.linear_issues.update.response"),
879
893
  payload: z.object({
@@ -2929,6 +2943,7 @@ export const SessionInboundMessageSchema = z.discriminatedUnion("type", [
2929
2943
  ProjectIconColorSetRequestSchema,
2930
2944
  ProjectRemoveRequestSchema,
2931
2945
  WorkspaceLinearIssuesUpdateRequestSchema,
2946
+ WorkspaceRefreshMetadataRequestSchema,
2932
2947
  LinearGetConnectionRequestSchema,
2933
2948
  LinearSetKeyRequestSchema,
2934
2949
  LinearDisconnectRequestSchema,
@@ -3290,6 +3305,8 @@ export const ServerInfoStatusPayloadSchema = z
3290
3305
  workspaceLabels: z.boolean().optional(),
3291
3306
  // COMPAT(workspaceLinearIssues): added in v0.11.0-fork.27, remove gate after 2027-04-21.
3292
3307
  workspaceLinearIssues: z.boolean().optional(),
3308
+ // COMPAT(workspaceMetadataRefresh): added in v0.11.0-fork.30, remove gate after 2027-04-21.
3309
+ workspaceMetadataRefresh: z.boolean().optional(),
3293
3310
  // COMPAT(linearIntegration): added in v0.11.0-fork.28, remove gate after 2027-04-21.
3294
3311
  linearIntegration: z.boolean().optional(),
3295
3312
  // COMPAT(workspaceSetupRun): added in v0.8.0, remove gate after 2027-09-02.
@@ -6466,6 +6483,7 @@ export const SessionOutboundMessageSchema = z.discriminatedUnion("type", [
6466
6483
  ProjectIconColorSetResponseSchema,
6467
6484
  ProjectRemoveResponseSchema,
6468
6485
  WorkspaceLinearIssuesUpdateResponseSchema,
6486
+ WorkspaceRefreshMetadataResponseSchema,
6469
6487
  LinearGetConnectionResponseSchema,
6470
6488
  LinearSetKeyResponseSchema,
6471
6489
  LinearDisconnectResponseSchema,
@@ -9869,6 +9869,14 @@ export declare const WSOutboundMessageSchema: {
9869
9869
  }, import("zod/v4/core").$strip>>;
9870
9870
  error: import("zod").ZodNullable<import("zod").ZodString>;
9871
9871
  }, import("zod/v4/core").$strip>;
9872
+ }, import("zod/v4/core").$strip>, import("zod").ZodObject<{
9873
+ type: import("zod").ZodLiteral<"workspace.refresh_metadata.response">;
9874
+ payload: import("zod").ZodObject<{
9875
+ requestId: import("zod").ZodString;
9876
+ workspaceId: import("zod").ZodString;
9877
+ success: import("zod").ZodBoolean;
9878
+ error: import("zod").ZodOptional<import("zod").ZodString>;
9879
+ }, import("zod/v4/core").$strip>;
9872
9880
  }, import("zod/v4/core").$strip>, import("zod").ZodObject<{
9873
9881
  type: import("zod").ZodLiteral<"integrations.linear.get_connection.response">;
9874
9882
  payload: import("zod").ZodObject<{
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@getpaseo/protocol",
3
- "version": "0.11.0-fork.30",
3
+ "version": "0.11.0-fork.31",
4
4
  "description": "Paseo shared protocol schemas and wire types",
5
5
  "files": [
6
6
  "dist",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@getpaseo/relay",
3
- "version": "0.11.0-fork.30",
3
+ "version": "0.11.0-fork.31",
4
4
  "description": "Paseo relay for bridging daemon and client connections",
5
5
  "files": [
6
6
  "dist",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@getpaseo/builtin-plugins",
3
- "version": "0.11.0-fork.30",
3
+ "version": "0.11.0-fork.31",
4
4
  "private": true,
5
5
  "type": "module",
6
6
  "scripts": {
@@ -212,6 +212,7 @@ const INBOUND_PERMISSION = {
212
212
  "workspace.script.start.request": "workspace.write",
213
213
  "workspace.script.stop.request": "workspace.write",
214
214
  "workspace.linear_issues.update.request": ["workspace.manage", "hub.execute"],
215
+ "workspace.refresh_metadata.request": "workspace.read",
215
216
  "integrations.linear.get_connection.request": "daemon.read",
216
217
  "integrations.linear.set_key.request": "daemon.manage",
217
218
  "integrations.linear.disconnect.request": "daemon.manage",
@@ -449,6 +450,7 @@ const OUTBOUND_PERMISSION = {
449
450
  "workspace.script.start.response": "workspace.write",
450
451
  "workspace.script.stop.response": "workspace.write",
451
452
  "workspace.linear_issues.update.response": ["workspace.manage", "hub.execute"],
453
+ "workspace.refresh_metadata.response": "workspace.read",
452
454
  "integrations.linear.get_connection.response": "daemon.read",
453
455
  "integrations.linear.set_key.response": "daemon.manage",
454
456
  "integrations.linear.disconnect.response": "daemon.manage",
@@ -414,6 +414,7 @@ export declare class Session {
414
414
  private handleProjectRemoveRequest;
415
415
  private dispatchLinearIntegrationMessage;
416
416
  private handleLinearIntegrationRequest;
417
+ private handleWorkspaceMetadataRefresh;
417
418
  private handleWorkspaceLinearIssuesUpdate;
418
419
  private handleWorkspaceTitleSetRequest;
419
420
  private handleWorkspacePinSetRequest;
@@ -2074,6 +2074,8 @@ export class Session {
2074
2074
  return this.handleProjectIconColorSetRequest(msg);
2075
2075
  case "workspace.linear_issues.update.request":
2076
2076
  return this.handleWorkspaceLinearIssuesUpdate(msg);
2077
+ case "workspace.refresh_metadata.request":
2078
+ return this.handleWorkspaceMetadataRefresh(msg);
2077
2079
  case "workspace.title.set.request":
2078
2080
  return this.handleWorkspaceTitleSetRequest(msg.workspaceId, msg.title, msg.requestId);
2079
2081
  case "workspace.pin.set.request":
@@ -2799,6 +2801,42 @@ export class Session {
2799
2801
  });
2800
2802
  }
2801
2803
  }
2804
+ async handleWorkspaceMetadataRefresh(request) {
2805
+ const { workspaceId, requestId } = request;
2806
+ try {
2807
+ const workspace = await this.workspaceRegistry.get(workspaceId);
2808
+ if (!workspace)
2809
+ throw new Error("Workspace not found");
2810
+ await Promise.all([
2811
+ this.workspacePorts?.refresh(),
2812
+ this.workspaceGitService
2813
+ .getSnapshot(workspace.cwd, {
2814
+ force: true,
2815
+ includeForge: true,
2816
+ refreshGit: false,
2817
+ queueIfBusy: false,
2818
+ reason: "workspace-hover",
2819
+ })
2820
+ .then((snapshot) => this.linearIntegration.getPullRequestIssues(snapshot.forge.pullRequest?.url, {
2821
+ force: true,
2822
+ }))
2823
+ .then((prIssues) => this.linearIntegration.resolve(mergeLinearIssues(workspace.linearIssues, prIssues), {
2824
+ force: true,
2825
+ })),
2826
+ ]);
2827
+ await this.emitWorkspaceUpdatesForWorkspaceIds([workspaceId]);
2828
+ this.emit({
2829
+ type: "workspace.refresh_metadata.response",
2830
+ payload: { workspaceId, requestId, success: true },
2831
+ });
2832
+ }
2833
+ catch (error) {
2834
+ this.emit({
2835
+ type: "workspace.refresh_metadata.response",
2836
+ payload: { workspaceId, requestId, success: false, error: getErrorMessage(error) },
2837
+ });
2838
+ }
2839
+ }
2802
2840
  async handleWorkspaceLinearIssuesUpdate(request) {
2803
2841
  const { workspaceId, requestId, add, remove } = request;
2804
2842
  let updated;
@@ -1310,6 +1310,7 @@ export class VoiceAssistantWebSocketServer {
1310
1310
  // COMPAT(workspaceSetupRun): added in v0.7.3, remove gate after 2027-09-02.
1311
1311
  workspaceSetupRun: true,
1312
1312
  workspaceLinearIssues: true,
1313
+ workspaceMetadataRefresh: true,
1313
1314
  linearIntegration: true,
1314
1315
  // COMPAT(turnDiffs): added in v0.11.0, remove gate after 2027-10-03.
1315
1316
  turnDiffs: true,
@@ -155,6 +155,7 @@ export type WorkspaceGitBranchSuggestion = BranchSuggestion;
155
155
  export type WorkspaceGitWorktreeInfo = PaseoWorktreeInfo;
156
156
  export type WorkspaceGitSnapshotOptions = WorkspaceGitReadOptions & {
157
157
  includeForge?: boolean;
158
+ refreshGit?: boolean;
158
159
  queueIfBusy?: boolean;
159
160
  };
160
161
  interface WorkspaceGitServiceDependencies {
@@ -2167,8 +2167,8 @@ export class WorkspaceGitServiceImpl {
2167
2167
  const force = options?.force === true;
2168
2168
  return {
2169
2169
  force,
2170
- refreshStructure: true,
2171
- refreshWorktree: true,
2170
+ refreshStructure: options?.refreshGit !== false,
2171
+ refreshWorktree: options?.refreshGit !== false,
2172
2172
  includeForge: options?.includeForge ?? true,
2173
2173
  reason: options?.reason ?? defaultReason,
2174
2174
  notify,
@@ -11,7 +11,8 @@ export declare class WorkspacePortsService {
11
11
  private readonly options;
12
12
  private active;
13
13
  private disposed;
14
- private running;
14
+ private pending?;
15
+ private lastScanAt?;
15
16
  private timer?;
16
17
  private readonly details;
17
18
  private ports;
@@ -20,7 +21,9 @@ export declare class WorkspacePortsService {
20
21
  getPorts(workspaceId: string): WorkspacePort[];
21
22
  setConnected(connected: boolean): void;
22
23
  dispose(): void;
23
- private refresh;
24
+ refresh(): Promise<void>;
25
+ private startRefresh;
26
+ private scan;
24
27
  }
25
28
  export {};
26
29
  //# sourceMappingURL=service.d.ts.map
@@ -5,7 +5,6 @@ export class WorkspacePortsService {
5
5
  this.options = options;
6
6
  this.active = false;
7
7
  this.disposed = false;
8
- this.running = false;
9
8
  this.details = new Map();
10
9
  this.ports = [];
11
10
  this.byWorkspace = new Map();
@@ -20,16 +19,34 @@ export class WorkspacePortsService {
20
19
  if (this.timer)
21
20
  clearTimeout(this.timer);
22
21
  this.timer = undefined;
23
- if (connected && !this.running)
24
- void this.refresh();
22
+ if (connected && !this.pending)
23
+ void this.startRefresh();
25
24
  }
26
25
  dispose() {
27
26
  this.setConnected(false);
28
27
  this.disposed = true;
29
28
  this.details.clear();
30
29
  }
31
- async refresh() {
32
- this.running = true;
30
+ refresh() {
31
+ if (this.disposed)
32
+ return Promise.resolve();
33
+ if (this.pending)
34
+ return this.pending;
35
+ // Hovering across rows must not launch a host-wide process scan for every row.
36
+ if (this.lastScanAt !== undefined && Date.now() - this.lastScanAt < 5000)
37
+ return Promise.resolve();
38
+ return this.startRefresh();
39
+ }
40
+ startRefresh() {
41
+ if (this.timer)
42
+ clearTimeout(this.timer);
43
+ this.timer = undefined;
44
+ this.pending = this.scan().finally(() => {
45
+ this.pending = undefined;
46
+ });
47
+ return this.pending;
48
+ }
49
+ async scan() {
33
50
  try {
34
51
  const scan = this.options.scan ??
35
52
  ((details) => scanListeningPorts({ details, logger: this.options.logger }));
@@ -55,9 +72,9 @@ export class WorkspacePortsService {
55
72
  this.options.logger.warn({ err: error }, "Failed to publish workspace ports");
56
73
  }
57
74
  finally {
58
- this.running = false;
75
+ this.lastScanAt = Date.now();
59
76
  if (this.active) {
60
- this.timer = setTimeout(() => void this.refresh(), 30000);
77
+ this.timer = setTimeout(() => void this.startRefresh(), 30000);
61
78
  this.timer.unref();
62
79
  }
63
80
  }
@@ -1,11 +1,14 @@
1
1
  import type { Logger } from "pino";
2
2
  import { type LinearConnection, type LinearIssue } from "@getpaseo/protocol/messages";
3
+ type LookupOptions = {
4
+ force?: boolean;
5
+ };
3
6
  export type LinearIntegrationService = {
4
7
  getConnection(): Promise<LinearConnection>;
5
8
  setKey(apiKey: string): Promise<LinearConnection>;
6
9
  disconnect(): Promise<LinearConnection>;
7
- getPullRequestIssues(url?: string): Promise<LinearIssue[]>;
8
- resolve(issues?: readonly LinearIssue[]): Promise<LinearIssue[] | undefined>;
10
+ getPullRequestIssues(url?: string, options?: LookupOptions): Promise<LinearIssue[]>;
11
+ resolve(issues?: readonly LinearIssue[], options?: LookupOptions): Promise<LinearIssue[] | undefined>;
9
12
  };
10
13
  type Options = {
11
14
  paseoHome: string;
@@ -212,7 +212,7 @@ export function createLinearIntegrationService({ paseoHome, logger, request = fe
212
212
  return describe(undefined);
213
213
  });
214
214
  },
215
- async getPullRequestIssues(url) {
215
+ async getPullRequestIssues(url, options) {
216
216
  if (!url)
217
217
  return [];
218
218
  try {
@@ -220,7 +220,9 @@ export function createLinearIntegrationService({ paseoHome, logger, request = fe
220
220
  if (!connection)
221
221
  return [];
222
222
  let entry = pullRequestCache.get(url);
223
- if (!entry || entry.expiresAt <= now()) {
223
+ if (!entry ||
224
+ entry.expiresAt <= now() ||
225
+ (options?.force && Number.isFinite(entry.expiresAt))) {
224
226
  const pending = limitRequests(() => loadPullRequestIssues({ url, apiKey: connection.apiKey }));
225
227
  entry = { pending, expiresAt: Number.POSITIVE_INFINITY };
226
228
  const current = entry;
@@ -242,7 +244,7 @@ export function createLinearIntegrationService({ paseoHome, logger, request = fe
242
244
  return [];
243
245
  }
244
246
  },
245
- async resolve(issues) {
247
+ async resolve(issues, options) {
246
248
  if (!issues?.length)
247
249
  return issues ? [...issues] : undefined;
248
250
  let connection;
@@ -261,7 +263,9 @@ export function createLinearIntegrationService({ paseoHome, logger, request = fe
261
263
  if (!normalized)
262
264
  return issue;
263
265
  let entry = cache.get(normalized.url);
264
- if (!entry || entry.expiresAt <= now()) {
266
+ if (!entry ||
267
+ entry.expiresAt <= now() ||
268
+ (options?.force && Number.isFinite(entry.expiresAt))) {
265
269
  const pending = limitRequests(() => loadIssue({ issue: normalized, apiKey }));
266
270
  entry = { pending, expiresAt: Number.POSITIVE_INFINITY };
267
271
  cache.set(normalized.url, entry);