@openforge-app/plugin-sdk 0.2.7 → 0.2.9

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.
@@ -1,4 +1,4 @@
1
- import { BrowserSurfaceError, isAllowedBrowserSurfaceUrl, } from './browserSurfaces';
1
+ import { BrowserSurfaceError, isAllowedBrowserSurfaceUrl, } from './browserSurfaces.js';
2
2
  function disposable(dispose) {
3
3
  let disposed = false;
4
4
  return {
@@ -1,5 +1,5 @@
1
1
  import type { BrowserSurfaceCapture, BrowserDevToolsPanel, BrowserSurfaceFeedbackSelection, BrowserSurfaceVisualFeedback, BrowserSurfaceRegion, BrowserSurfaceErrorCode, BrowserSurfaceNavigationError, BrowserSurfacesAPI, GetOrCreateBrowserSurfaceRequest, TaskBrowserSurfaceController, TaskBrowserSurfaceState } from './browserSurfaces';
2
- import type { CommandDescriptor, CommandRegistry, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ComposeTaskResult, Disposable, FrontendBackendBridge, FrontendOpenForgeAPI, FrontendPlugin, FrontendPluginContext, FrontendSettingsRegistry, FrontendTaskPaneRegistry, FrontendInjectionPointRegistry, FrontendTaskStartRegistry, FrontendTaskUIRegistry, FrontendViewRegistry, InjectionPointLocation, NavigationAPI, OpenForgeContextChangeHandler, OpenForgeContextSnapshot, OpenForgeNavigationRequest, OpenForgeNavigationSnapshot, TaskLinkHandler, TaskLinkHandlerResult, TaskLinkOpenRequest, TaskLinksAPI, PluginIcon, PluginSidebarNavigationProps, PluginSidebarViewIdentity, PluginInjectionPointProps, PluginInjectionPointRegistration, PluginSettingsSectionProps, PluginSettingsSectionRegistration, PluginSettingsSectionScope, PluginStorageScope, PluginSvgIcon, PluginTaskPaneProps, PluginTaskPaneTabRegistration, PluginTaskUISectionProps, PluginTaskUISectionRegistration, PluginViewProps, PluginViewRegistration, TaskStartPrefixContext, TaskStartPrefixProviderRegistration, PtyBufferState, TerminalImageProtocol } from './types';
2
+ import type { CommandDescriptor, CommandRegistry, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ComposeTaskResult, Disposable, FrontendBackendBridge, FrontendOpenForgeAPI, FrontendPlugin, FrontendPluginContext, FrontendSettingsRegistry, FrontendTaskPaneRegistry, FrontendInjectionPointRegistry, FrontendTaskStartRegistry, FrontendReviewUIRegistry, FrontendTaskUIRegistry, FrontendViewRegistry, InjectionPointLocation, NavigationAPI, OpenForgeContextChangeHandler, OpenForgeContextSnapshot, OpenForgeNavigationRequest, OpenForgeNavigationSnapshot, TaskLinkHandler, TaskLinkHandlerResult, TaskLinkOpenRequest, TaskLinksAPI, PluginIcon, PluginSidebarNavigationProps, PluginSidebarViewIdentity, PluginInjectionPointProps, PluginInjectionPointRegistration, PluginSettingsSectionProps, PluginSettingsSectionRegistration, PluginSettingsSectionScope, PluginStorageScope, PluginSvgIcon, PluginTaskPaneProps, PluginTaskPaneTabRegistration, PluginReviewRowActionProps, PluginReviewRowActionRegistration, PluginTaskUISectionProps, PluginTaskUISectionRegistration, PluginViewProps, PluginViewRegistration, TaskStartPrefixContext, TaskStartPrefixProviderRegistration, PtyBufferState, TerminalImageProtocol, TerminalViewSnapshot } from './types';
3
3
  export declare const OPENFORGE_FRONTEND_PLUGIN_MARKER = "__openforgeFrontendPlugin";
4
4
  export type MarkedFrontendPlugin<TPlugin extends FrontendPlugin = FrontendPlugin> = TPlugin & {
5
5
  readonly [OPENFORGE_FRONTEND_PLUGIN_MARKER]: true;
@@ -7,4 +7,4 @@ export type MarkedFrontendPlugin<TPlugin extends FrontendPlugin = FrontendPlugin
7
7
  export declare function defineFrontendPlugin<const TPlugin extends FrontendPlugin>(plugin: TPlugin): MarkedFrontendPlugin<TPlugin>;
8
8
  export { BrowserSurfaceError, isAllowedBrowserSurfaceUrl } from './browserSurfaces';
9
9
  export type { BrowserSurfaceCapture, BrowserDevToolsPanel, BrowserSurfaceFeedbackSelection, BrowserSurfaceVisualFeedback, BrowserSurfaceRegion, BrowserSurfaceErrorCode, BrowserSurfaceNavigationError, BrowserSurfacesAPI, GetOrCreateBrowserSurfaceRequest, TaskBrowserSurfaceController, TaskBrowserSurfaceState, };
10
- export type { CommandDescriptor, CommandRegistry, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ComposeTaskResult, Disposable, FrontendBackendBridge, FrontendOpenForgeAPI, FrontendPlugin, FrontendPluginContext, FrontendSettingsRegistry, FrontendTaskPaneRegistry, FrontendInjectionPointRegistry, FrontendTaskStartRegistry, FrontendTaskUIRegistry, FrontendViewRegistry, InjectionPointLocation, NavigationAPI, OpenForgeContextChangeHandler, OpenForgeContextSnapshot, OpenForgeNavigationRequest, OpenForgeNavigationSnapshot, TaskLinkHandler, TaskLinkHandlerResult, TaskLinkOpenRequest, TaskLinksAPI, PluginIcon, PluginSidebarNavigationProps, PluginSidebarViewIdentity, PluginInjectionPointProps, PluginInjectionPointRegistration, PluginSettingsSectionProps, PluginSettingsSectionRegistration, PluginSettingsSectionScope, PluginStorageScope, PluginSvgIcon, PluginTaskPaneProps, PluginTaskPaneTabRegistration, PluginTaskUISectionProps, PluginTaskUISectionRegistration, PluginViewProps, PluginViewRegistration, TaskStartPrefixContext, TaskStartPrefixProviderRegistration, PtyBufferState, TerminalImageProtocol, };
10
+ export type { CommandDescriptor, CommandRegistry, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ComposeTaskResult, Disposable, FrontendBackendBridge, FrontendOpenForgeAPI, FrontendPlugin, FrontendPluginContext, FrontendSettingsRegistry, FrontendTaskPaneRegistry, FrontendInjectionPointRegistry, FrontendTaskStartRegistry, FrontendReviewUIRegistry, FrontendTaskUIRegistry, FrontendViewRegistry, InjectionPointLocation, NavigationAPI, OpenForgeContextChangeHandler, OpenForgeContextSnapshot, OpenForgeNavigationRequest, OpenForgeNavigationSnapshot, TaskLinkHandler, TaskLinkHandlerResult, TaskLinkOpenRequest, TaskLinksAPI, PluginIcon, PluginSidebarNavigationProps, PluginSidebarViewIdentity, PluginInjectionPointProps, PluginInjectionPointRegistration, PluginSettingsSectionProps, PluginSettingsSectionRegistration, PluginSettingsSectionScope, PluginStorageScope, PluginSvgIcon, PluginTaskPaneProps, PluginTaskPaneTabRegistration, PluginReviewRowActionProps, PluginReviewRowActionRegistration, PluginTaskUISectionProps, PluginTaskUISectionRegistration, PluginViewProps, PluginViewRegistration, TaskStartPrefixContext, TaskStartPrefixProviderRegistration, PtyBufferState, TerminalImageProtocol, TerminalViewSnapshot, };
package/dist/index.d.ts CHANGED
@@ -3,7 +3,7 @@ export type { BrowserSurfaceCapture, BrowserSurfaceFeedbackSelection, BrowserSur
3
3
  export { OPENFORGE_PACKAGE_METADATA_SCHEMA, OPENFORGE_PLUGIN_CAPABILITIES, isOpenForgePackageMetadata, isPluginPackageMetadata, isSupportedOpenForgeApiVersion, validateOpenForgePackageMetadata, validatePluginPackageMetadata, } from './manifest';
4
4
  export { createMemoryPluginStorage, createMockBackendOpenForgeApi, createMockFrontendOpenForgeApi, createMockOpenForgeApi, createMockPluginContext, createOpenForgeRegistryFake, createTestingCalls, TestingOpenForgeRegistryFake, TestingSubscriptionSink, } from './testing';
5
5
  export { DEFAULT_EXTERNAL_TEXT_FILE_CHUNK_SIZE_BYTES, MAX_EXTERNAL_TEXT_FILE_CHUNK_SIZE_BYTES, MIN_EXTERNAL_TEXT_FILE_CHUNK_SIZE_BYTES, TaskFollowUpError, MAX_SUPPORTED_API_VERSION, MIN_SUPPORTED_API_VERSION, OPENFORGE_PLUGIN_API_VERSION, SUPPORTED_OPENFORGE_API_VERSIONS, isPluginViewKey, resolveExternalTextFileChunkSize, makePluginViewKey, parsePluginViewKey, } from './types';
6
- export type { AgentCommandDescriptor, AgentCommandMetadata, AgentCommandRuntime, AttentionAPI, BackendReadyState, CommandDescriptor, CommandRegistry, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ComposeTaskResult, ConfigureStartPromptContributionRequest, CreateTaskRequest, Disposable, BackendFileSystemAPI, ExternalReadDirectoryRequest, ExternalReadFileRequest, ExternalReadTextFileChunksRequest, ExternalReadFileSystemAPI, FileSystemAPI, UserDataDirectoryRequest, UserDataFileRequest, UserDataFileSystemAPI, UserDataFileWriteRequest, ImplementationRun, InjectionPointLocation, JsonObject, JsonPrimitive, JsonSchema, JsonValue, MaybePromise, KeyValueConfigAPI, NotificationRequest, NavigationAPI, NotificationsAPI, OpenForgeCommonAPI, OpenForgeContextChangeHandler, OpenForgeContextSnapshot, OpenForgeNavigationRequest, OpenForgeNavigationSnapshot, OpenForgePackageMetadata, OpenForgePluginCapability, OpenForgePluginContext, OpenForgePluginPackageJson, PluginCommandInvocationContext, PluginCommandInvocationSource, PluginComponentLoader, PluginComponentModule, PluginEntry, PluginIcon, PluginSidebarNavigationProps, PluginSidebarViewIdentity, PluginInjectionPointProps, PluginSettingsSectionProps, PluginState, PluginSvgIcon, PluginTaskPaneProps, PluginTaskUISectionProps, PluginViewProps, PluginStorage, PluginStorageScope, PluginViewKey, ProjectsAPI, PtyBufferState, ShellAPI, ShellResizeRequest, TaskStartPrefixContext, TaskStartPrefixProviderRegistration, TerminalImageProtocol, ShellSessionRequest, ShellSpawnRequest, ShellTerminalQueryResponseRequest, ShellWriteRequest, StartPromptContribution, SendTaskFollowUpRequest, StartTaskImplementationRequest, TaskFollowUpDisposition, TaskFollowUpErrorCode, TaskFollowUpReceipt, SubscriptionSink, SupportedOpenForgeApiVersion, SystemAPI, TaskLinkHandler, TaskLinkHandlerResult, TaskLinkOpenRequest, TaskLinksAPI, TasksAPI, ValidationError, } from './types';
6
+ export type { AgentCommandDescriptor, AgentCommandMetadata, AgentCommandRuntime, AttentionAPI, BackendReadyState, CommandDescriptor, CommandRegistry, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ComposeTaskResult, ConfigureStartPromptContributionRequest, CreateTaskRequest, Disposable, BackendFileSystemAPI, ExternalReadDirectoryRequest, ExternalReadFileRequest, ExternalReadTextFileChunksRequest, ExternalReadFileSystemAPI, FileSystemAPI, UserDataDirectoryRequest, UserDataFileRequest, UserDataFileSystemAPI, UserDataFileWriteRequest, ImplementationRun, InjectionPointLocation, JsonObject, JsonPrimitive, JsonSchema, JsonValue, MaybePromise, KeyValueConfigAPI, NotificationRequest, NavigationAPI, NotificationsAPI, OpenForgeCommonAPI, OpenForgeContextChangeHandler, OpenForgeContextSnapshot, OpenForgeNavigationRequest, OpenForgeNavigationSnapshot, OpenForgePackageMetadata, OpenForgePluginCapability, OpenForgePluginContext, OpenForgePluginPackageJson, PluginCommandInvocationContext, PluginCommandInvocationSource, PluginComponentLoader, PluginComponentModule, PluginEntry, PluginIcon, PluginSidebarNavigationProps, PluginSidebarViewIdentity, PluginInjectionPointProps, PluginSettingsSectionProps, PluginState, PluginSvgIcon, PluginTaskPaneProps, PluginTaskUISectionProps, PluginViewProps, PluginStorage, PluginStorageScope, PluginViewKey, ProjectsAPI, PtyBufferState, ShellAPI, ShellResizeRequest, TaskStartPrefixContext, TaskStartPrefixProviderRegistration, TerminalImageProtocol, TerminalViewSnapshot, ShellSessionRequest, ShellSpawnRequest, ShellTerminalQueryResponseRequest, ShellWriteRequest, StartPromptContribution, SendTaskFollowUpRequest, StartTaskImplementationRequest, TaskFollowUpDisposition, TaskFollowUpErrorCode, TaskFollowUpReceipt, SubscriptionSink, SupportedOpenForgeApiVersion, SystemAPI, TaskLinkHandler, TaskLinkHandlerResult, TaskLinkOpenRequest, TaskLinksAPI, TasksAPI, ValidationError, } from './types';
7
7
  export type { MockBackendOpenForgeAPI, MockFrontendOpenForgeAPI, TestingBackgroundServiceContribution, TestingBackendMethodContribution, TestingCommandContribution, TestingContributionBase, TestingExternalTextFile, TestingExternalTextFileChunksCall, TestingEventListenerContribution, TestingOpenForgeApiCalls, TestingOpenForgeApiOptions, TestingOpenForgeRegistrySnapshot, TestingRuntimeKind, TestingRuntimeScope, TestingSettingsSectionContribution, TestingTaskPaneTabContribution, TestingTaskUISectionContribution, TestingViewContribution, } from './testing';
8
8
  export { parseStrictFiniteNumber } from './numberParsing';
9
9
  export { buildProjectFileTree, flattenVisibleProjectFileTree, formatProjectFileTreeSize, getProjectFileTreeDepth, getProjectFileTreeItemAccessibility, getProjectFileTreeKeyboardAction, getProjectFileTreeParentPath, hasProjectFileTreeShortcutModifier, projectFileTreePathToId, } from './projectFileTree';
@@ -138,7 +138,8 @@
138
138
  "browserSurfaces",
139
139
  "taskLinks",
140
140
  "appEnablement",
141
- "customSidebarNavigation"
141
+ "customSidebarNavigation",
142
+ "reviewUI"
142
143
  ]
143
144
  }
144
145
  }
@@ -1,5 +1,5 @@
1
1
  import type { BackendOpenForgeAPI } from '../types';
2
- import { type TestingRegistryServices } from './support';
2
+ import { type TestingRegistryServices } from './support.js';
3
3
  import type { TestingBackendMethodContribution, TestingBackgroundServiceContribution } from './contracts';
4
4
  export declare class TestingBackendServicesFake {
5
5
  private readonly services;
@@ -1,4 +1,4 @@
1
- import { assertFunction, createDisposable } from './support';
1
+ import { assertFunction, createDisposable } from './support.js';
2
2
  export class TestingBackendServicesFake {
3
3
  services;
4
4
  backendMethods = new Map();
@@ -1,5 +1,5 @@
1
1
  import type { BackendOpenForgeAPI, FrontendOpenForgeAPI, OpenForgeCommonAPI } from '../types';
2
- import { type TestingRegistryServices } from './support';
2
+ import { type TestingRegistryServices } from './support.js';
3
3
  import type { TestingCommandContribution, TestingEventListenerContribution } from './contracts';
4
4
  export type TestingCommonApi = OpenForgeCommonAPI & Pick<FrontendOpenForgeAPI, 'navigation'>;
5
5
  export declare class TestingCommonApiFake {
@@ -1,5 +1,5 @@
1
- import { resolveExternalTextFileChunkSize } from '../types';
2
- import { assertFunction, assertTitle, commandDescriptor, createDisposable, isJsonValue, normalizeAgentCommandMetadata, } from './support';
1
+ import { resolveExternalTextFileChunkSize } from '../types.js';
2
+ import { assertFunction, assertTitle, commandDescriptor, createDisposable, isJsonValue, normalizeAgentCommandMetadata, } from './support.js';
3
3
  const UTF8_ENCODER = new TextEncoder();
4
4
  function* splitExternalTextFile(content, maxBytes) {
5
5
  let chunk = '';
@@ -1,9 +1,9 @@
1
1
  import type { BrowserSurfaceVisualFeedback } from '../browserSurfaces';
2
2
  import type { TestingOpenForgeRegistryFake } from './registryFake';
3
- import type { BackendMethodRegistration, BackendOpenForgeAPI, BackgroundServiceRegistration, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ConfigureStartPromptContributionRequest, CreateTaskRequest, FrontendOpenForgeAPI, InjectionPointLocation, JsonValue, NotificationRequest, OpenForgeNavigationRequest, OpenForgePackageMetadata, PluginSettingsSectionRegistration, PluginStorage, PluginTaskPaneTabRegistration, PluginTaskUISectionRegistration, PluginViewRegistration, ShellSpawnRequest, SendTaskFollowUpRequest, StartTaskImplementationRequest, TaskLinkOpenRequest, TaskStartPrefixContext, ExternalReadDirectoryRequest, ExternalReadFileRequest, ExternalReadTextFileChunksRequest, UserDataDirectoryRequest, UserDataFileRequest, UserDataFileWriteRequest } from '../types';
3
+ import type { BackendMethodRegistration, BackendOpenForgeAPI, BackgroundServiceRegistration, CommandRegistration, CommandShortcutMetadata, ComposeTaskRequest, ConfigureStartPromptContributionRequest, CreateTaskRequest, FrontendOpenForgeAPI, InjectionPointLocation, JsonValue, NotificationRequest, OpenForgeNavigationRequest, OpenForgePackageMetadata, PluginSettingsSectionRegistration, PluginStorage, PluginTaskPaneTabRegistration, PluginReviewRowActionRegistration, PluginTaskUISectionRegistration, PluginViewRegistration, ShellSpawnRequest, SendTaskFollowUpRequest, StartTaskImplementationRequest, TaskLinkOpenRequest, TaskStartPrefixContext, ExternalReadDirectoryRequest, ExternalReadFileRequest, ExternalReadTextFileChunksRequest, UserDataDirectoryRequest, UserDataFileRequest, UserDataFileWriteRequest } from '../types';
4
4
  import type { Task } from '../domain';
5
5
  export type TestingRuntimeScope = 'global' | 'project' | 'task';
6
- export type TestingRuntimeKind = 'commands' | 'events' | 'views' | 'taskPane' | 'taskUI' | 'settings' | 'backend' | 'background';
6
+ export type TestingRuntimeKind = 'commands' | 'events' | 'views' | 'taskPane' | 'taskUI' | 'reviewUI' | 'settings' | 'backend' | 'background';
7
7
  export type TestingMaybePromise<T> = T | Promise<T>;
8
8
  export type TestingCommandHandler = (payload?: unknown) => TestingMaybePromise<unknown>;
9
9
  export type TestingEventHandler = (payload: unknown) => void;
@@ -200,6 +200,7 @@ export type TestingEventListenerContribution = TestingContributionBase & {
200
200
  export type TestingViewContribution = TestingContributionBase & PluginViewRegistration;
201
201
  export type TestingTaskPaneTabContribution = TestingContributionBase & PluginTaskPaneTabRegistration;
202
202
  export type TestingTaskUISectionContribution = TestingContributionBase & PluginTaskUISectionRegistration;
203
+ export type TestingReviewRowActionContribution = TestingContributionBase & PluginReviewRowActionRegistration;
203
204
  export type TestingSettingsSectionContribution = TestingContributionBase & PluginSettingsSectionRegistration;
204
205
  export type TestingBackendMethodContribution = TestingContributionBase & {
205
206
  registration: BackendMethodRegistration;
@@ -223,6 +224,7 @@ export interface TestingOpenForgeRegistrySnapshot {
223
224
  views: TestingViewContribution[];
224
225
  taskPaneTabs: TestingTaskPaneTabContribution[];
225
226
  taskUISections: TestingTaskUISectionContribution[];
227
+ reviewRowActions: TestingReviewRowActionContribution[];
226
228
  settingsSections: TestingSettingsSectionContribution[];
227
229
  commands: TestingCommandContribution[];
228
230
  eventListeners: TestingEventListenerContribution[];
@@ -1,14 +1,15 @@
1
- import { type TaskBrowserSurfaceState } from '../browserSurfaces';
1
+ import { type TaskBrowserSurfaceState } from '../browserSurfaces.js';
2
2
  import type { FrontendOpenForgeAPI } from '../types';
3
- import { type TestingRegistryServices } from './support';
4
- import type { TestingInjectionPointContribution, TestingTaskStartPrefixProviderContribution, TestingSettingsSectionContribution, TestingTaskPaneTabContribution, TestingTaskUISectionContribution, TestingViewContribution } from './contracts';
5
- type TestingFrontendContributionApi = Pick<FrontendOpenForgeAPI, 'browserSurfaces' | 'taskLinks' | 'views' | 'taskUI' | 'taskPane' | 'settings' | 'backend' | 'injectionPoints' | 'taskStart'>;
3
+ import { type TestingRegistryServices } from './support.js';
4
+ import type { TestingInjectionPointContribution, TestingTaskStartPrefixProviderContribution, TestingSettingsSectionContribution, TestingTaskPaneTabContribution, TestingReviewRowActionContribution, TestingTaskUISectionContribution, TestingViewContribution } from './contracts';
5
+ type TestingFrontendContributionApi = Pick<FrontendOpenForgeAPI, 'browserSurfaces' | 'taskLinks' | 'views' | 'taskUI' | 'reviewUI' | 'taskPane' | 'settings' | 'backend' | 'injectionPoints' | 'taskStart'>;
6
6
  export declare class TestingFrontendContributionFake {
7
7
  private readonly services;
8
8
  private readonly invokeBackendMethod;
9
9
  private readonly views;
10
10
  private readonly taskPaneTabs;
11
11
  private readonly taskUISections;
12
+ private readonly reviewRowActions;
12
13
  private readonly settingsSections;
13
14
  private readonly injectionPoints;
14
15
  private readonly taskStartPrefixProviders;
@@ -22,6 +23,7 @@ export declare class TestingFrontendContributionFake {
22
23
  views: TestingViewContribution[];
23
24
  taskPaneTabs: TestingTaskPaneTabContribution[];
24
25
  taskUISections: TestingTaskUISectionContribution[];
26
+ reviewRowActions: TestingReviewRowActionContribution[];
25
27
  settingsSections: TestingSettingsSectionContribution[];
26
28
  injectionPoints: TestingInjectionPointContribution[];
27
29
  taskStartPrefixProviders: TestingTaskStartPrefixProviderContribution[];
@@ -29,6 +31,7 @@ export declare class TestingFrontendContributionFake {
29
31
  private registerView;
30
32
  private registerTaskPaneTab;
31
33
  private registerTaskUISection;
34
+ private registerReviewRowAction;
32
35
  private registerSettingsSection;
33
36
  private registerTaskStartPrefixProvider;
34
37
  private registerInjectionPoint;
@@ -1,12 +1,13 @@
1
- import { createTestingBrowserSurfaces } from '../browserSurfacesTesting';
2
- import { isAllowedBrowserSurfaceUrl } from '../browserSurfaces';
3
- import { assertFunction, assertTitle, createDisposable, } from './support';
1
+ import { createTestingBrowserSurfaces } from '../browserSurfacesTesting.js';
2
+ import { isAllowedBrowserSurfaceUrl } from '../browserSurfaces.js';
3
+ import { assertFunction, assertTitle, createDisposable, } from './support.js';
4
4
  export class TestingFrontendContributionFake {
5
5
  services;
6
6
  invokeBackendMethod;
7
7
  views = new Map();
8
8
  taskPaneTabs = new Map();
9
9
  taskUISections = new Map();
10
+ reviewRowActions = new Map();
10
11
  settingsSections = new Map();
11
12
  injectionPoints = new Map();
12
13
  taskStartPrefixProviders = new Map();
@@ -60,6 +61,9 @@ export class TestingFrontendContributionFake {
60
61
  registerTab: (registration) => this.registerTaskPaneTab(registration),
61
62
  registerSection: (registration) => this.registerTaskUISection(registration),
62
63
  },
64
+ reviewUI: {
65
+ registerRowAction: (registration) => this.registerReviewRowAction(registration),
66
+ },
63
67
  taskPane: {
64
68
  registerTab: (registration) => this.registerTaskPaneTab(registration),
65
69
  },
@@ -93,6 +97,7 @@ export class TestingFrontendContributionFake {
93
97
  views: Array.from(this.views.values()),
94
98
  taskPaneTabs: Array.from(this.taskPaneTabs.values()),
95
99
  taskUISections: Array.from(this.taskUISections.values()),
100
+ reviewRowActions: Array.from(this.reviewRowActions.values()),
96
101
  settingsSections: Array.from(this.settingsSections.values()),
97
102
  injectionPoints: Array.from(this.injectionPoints.values()),
98
103
  taskStartPrefixProviders: Array.from(this.taskStartPrefixProviders.values()).sort((left, right) => left.order - right.order || left.id.localeCompare(right.id)),
@@ -162,6 +167,23 @@ export class TestingFrontendContributionFake {
162
167
  this.services.claims.release('taskUI', qualifiedId);
163
168
  });
164
169
  }
170
+ registerReviewRowAction(registration) {
171
+ const qualifiedId = this.services.localQualifiedId('reviewUI', registration.id);
172
+ assertFunction('reviewUI', 'component', registration.component);
173
+ this.services.claims.claim('reviewUI', qualifiedId);
174
+ const contribution = {
175
+ ...registration,
176
+ id: registration.id.trim(),
177
+ qualifiedId,
178
+ pluginId: this.services.pluginId,
179
+ projectId: this.services.projectId,
180
+ };
181
+ this.reviewRowActions.set(qualifiedId, contribution);
182
+ return createDisposable(() => {
183
+ this.reviewRowActions.delete(qualifiedId);
184
+ this.services.claims.release('reviewUI', qualifiedId);
185
+ });
186
+ }
165
187
  registerSettingsSection(registration) {
166
188
  const qualifiedId = this.services.localQualifiedId('settings', registration.id);
167
189
  assertTitle('settings', registration.title);
@@ -1,7 +1,7 @@
1
1
  import type { TaskBrowserSurfaceState } from '../browserSurfaces';
2
2
  import type { BackendPlugin, BackendPluginContext, FrontendPlugin, FrontendPluginContext, OpenForgePackageMetadata, PluginStorage } from '../types';
3
3
  import type { MockBackendOpenForgeAPI, MockFrontendOpenForgeAPI, TestingOpenForgeApiCalls, TestingOpenForgeApiOptions, TestingOpenForgeRegistrySnapshot } from './contracts';
4
- import { TestingSubscriptionSink } from './support';
4
+ import { TestingSubscriptionSink } from './support.js';
5
5
  export declare class TestingOpenForgeRegistryFake {
6
6
  readonly pluginId: string;
7
7
  readonly projectId: string | null;
@@ -1,7 +1,7 @@
1
- import { TestingBackendServicesFake } from './backendServicesFake';
2
- import { TestingCommonApiFake } from './commonApiFake';
3
- import { TestingFrontendContributionFake } from './frontendContributionFake';
4
- import { TestingRegistryServices, TestingSubscriptionSink, } from './support';
1
+ import { TestingBackendServicesFake } from './backendServicesFake.js';
2
+ import { TestingCommonApiFake } from './commonApiFake.js';
3
+ import { TestingFrontendContributionFake } from './frontendContributionFake.js';
4
+ import { TestingRegistryServices, TestingSubscriptionSink, } from './support.js';
5
5
  export class TestingOpenForgeRegistryFake {
6
6
  pluginId;
7
7
  projectId;
package/dist/testing.d.ts CHANGED
@@ -1,3 +1,3 @@
1
- export { createMockBackendOpenForgeApi, createMockFrontendOpenForgeApi, createMockOpenForgeApi, createMockPluginContext, createOpenForgeRegistryFake, TestingOpenForgeRegistryFake, } from './testing/registryFake';
2
- export { createMemoryPluginStorage, createTestingCalls, TestingSubscriptionSink, } from './testing/support';
3
- export type { MockBackendOpenForgeAPI, MockFrontendOpenForgeAPI, TestingBackgroundServiceContribution, TestingBackendMethodContribution, TestingCommandContribution, TestingContributionBase, TestingExternalTextFile, TestingExternalTextFileChunksCall, TestingEventListenerContribution, TestingInjectionPointContribution, TestingOpenForgeApiCalls, TestingOpenForgeApiOptions, TestingOpenForgeRegistrySnapshot, TestingRuntimeKind, TestingRuntimeScope, TestingSettingsSectionContribution, TestingTaskPaneTabContribution, TestingTaskUISectionContribution, TestingViewContribution, } from './testing/contracts';
1
+ export { createMockBackendOpenForgeApi, createMockFrontendOpenForgeApi, createMockOpenForgeApi, createMockPluginContext, createOpenForgeRegistryFake, TestingOpenForgeRegistryFake, } from './testing/registryFake.js';
2
+ export { createMemoryPluginStorage, createTestingCalls, TestingSubscriptionSink, } from './testing/support.js';
3
+ export type { MockBackendOpenForgeAPI, MockFrontendOpenForgeAPI, TestingBackgroundServiceContribution, TestingBackendMethodContribution, TestingCommandContribution, TestingContributionBase, TestingExternalTextFile, TestingExternalTextFileChunksCall, TestingEventListenerContribution, TestingInjectionPointContribution, TestingOpenForgeApiCalls, TestingOpenForgeApiOptions, TestingOpenForgeRegistrySnapshot, TestingRuntimeKind, TestingRuntimeScope, TestingSettingsSectionContribution, TestingTaskPaneTabContribution, TestingTaskUISectionContribution, TestingViewContribution, } from './testing/contracts.js';
package/dist/testing.js CHANGED
@@ -1,2 +1,2 @@
1
- export { createMockBackendOpenForgeApi, createMockFrontendOpenForgeApi, createMockOpenForgeApi, createMockPluginContext, createOpenForgeRegistryFake, TestingOpenForgeRegistryFake, } from './testing/registryFake';
2
- export { createMemoryPluginStorage, createTestingCalls, TestingSubscriptionSink, } from './testing/support';
1
+ export { createMockBackendOpenForgeApi, createMockFrontendOpenForgeApi, createMockOpenForgeApi, createMockPluginContext, createOpenForgeRegistryFake, TestingOpenForgeRegistryFake, } from './testing/registryFake.js';
2
+ export { createMemoryPluginStorage, createTestingCalls, TestingSubscriptionSink, } from './testing/support.js';
package/dist/types.d.ts CHANGED
@@ -1,6 +1,6 @@
1
1
  import type { Component } from 'svelte';
2
2
  import type { BrowserSurfacesAPI } from './browserSurfaces';
3
- import type { AgentSession, CommandInfo, FileContent, FileEntry, Project, ProjectAttention, Task, TaskWorkspaceInfo, WritableBoardStatus } from './domain';
3
+ import type { AgentSession, CommandInfo, FileContent, FileEntry, Project, ProjectAttention, ReviewPullRequest, Task, TaskWorkspaceInfo, WritableBoardStatus } from './domain';
4
4
  export type SupportedOpenForgeApiVersion = 1;
5
5
  export declare const SUPPORTED_OPENFORGE_API_VERSIONS: readonly [1, ...1[]];
6
6
  export declare const OPENFORGE_PLUGIN_API_VERSION: SupportedOpenForgeApiVersion;
@@ -17,7 +17,7 @@ export interface ValidationError {
17
17
  path: string;
18
18
  message: string;
19
19
  }
20
- declare const OPENFORGE_PLUGIN_CAPABILITY_TYPE_MEMBERS: readonly ['commands', 'events', 'views', 'injectionPoints', 'taskPane', 'taskStart', 'settings', 'background', 'backend', 'storage', 'context', 'navigation', 'tasks', 'projects', 'fs', 'shell', 'notifications', 'attention', 'system.openUrl', 'system.writeClipboardText', 'config', 'projectConfig', 'browserSurfaces', 'taskLinks', 'appEnablement', 'customSidebarNavigation'];
20
+ declare const OPENFORGE_PLUGIN_CAPABILITY_TYPE_MEMBERS: readonly ['commands', 'events', 'views', 'injectionPoints', 'taskPane', 'taskStart', 'settings', 'background', 'backend', 'storage', 'context', 'navigation', 'tasks', 'projects', 'fs', 'shell', 'notifications', 'attention', 'system.openUrl', 'system.writeClipboardText', 'config', 'projectConfig', 'browserSurfaces', 'taskLinks', 'appEnablement', 'customSidebarNavigation', 'reviewUI'];
21
21
  export type OpenForgePluginCapability = (typeof OPENFORGE_PLUGIN_CAPABILITY_TYPE_MEMBERS)[number];
22
22
  export interface OpenForgePackageMetadata {
23
23
  id: string;
@@ -280,9 +280,34 @@ export interface PluginSettingsSectionRegistration {
280
280
  scope?: PluginSettingsSectionScope;
281
281
  component: PluginComponentLoader<PluginSettingsSectionProps> | PluginComponent<PluginSettingsSectionProps>;
282
282
  }
283
+ /**
284
+ * Props a review-row action receives. `pr` is the review-requested pull request whose row
285
+ * is being rendered, and `projectId` is the local project that owns its repo (null when the
286
+ * host surface has none for it). The same contribution renders once per row, so the host
287
+ * remounts it with a different `pr` rather than handing over the whole list.
288
+ */
289
+ export interface PluginReviewRowActionProps extends Record<string, unknown> {
290
+ api: FrontendOpenForgeAPI;
291
+ context: OpenForgeContextSnapshot;
292
+ pr: ReviewPullRequest;
293
+ projectId: string | null;
294
+ }
295
+ export interface PluginReviewRowActionRegistration {
296
+ id: string;
297
+ order?: number;
298
+ component: PluginComponentLoader<PluginReviewRowActionProps> | PluginComponent<PluginReviewRowActionProps>;
299
+ }
283
300
  export interface FrontendViewRegistry {
284
301
  register(registration: PluginViewRegistration): Disposable;
285
302
  }
303
+ export interface FrontendReviewUIRegistry {
304
+ /**
305
+ * Contribute a control onto every review-requested pull-request row a host surface shows
306
+ * (today the attention overview). Rows are narrow and there is one per pull request, so
307
+ * keep the component to a chip or a single button and let it fetch its own state.
308
+ */
309
+ registerRowAction(registration: PluginReviewRowActionRegistration): Disposable;
310
+ }
286
311
  export type InjectionPointLocation = 'createTaskPrompt' | 'agentSession' | 'backlogPrompt';
287
312
  export interface PluginInjectionPointProps extends Record<string, unknown> {
288
313
  api: FrontendOpenForgeAPI;
@@ -440,8 +465,15 @@ export interface ShellResizeRequest extends ShellSessionRequest {
440
465
  cols: number;
441
466
  rows: number;
442
467
  }
468
+ export interface TerminalViewSnapshot {
469
+ instanceId: number;
470
+ watermark: number;
471
+ data: string;
472
+ }
443
473
  export interface PtyBufferState {
474
+ authority?: 'xterm-authoritative' | 'ghostty-authoritative';
444
475
  buffer: string | null;
476
+ snapshot?: TerminalViewSnapshot | null;
445
477
  isLive: boolean;
446
478
  instanceId: number | null;
447
479
  }
@@ -585,6 +617,7 @@ export interface FrontendOpenForgeAPI extends OpenForgeCommonAPI {
585
617
  navigation: NavigationAPI;
586
618
  views: FrontendViewRegistry;
587
619
  taskUI: FrontendTaskUIRegistry;
620
+ reviewUI: FrontendReviewUIRegistry;
588
621
  /** @deprecated Use `taskUI.registerTab(...)`. */
589
622
  taskPane: FrontendTaskPaneRegistry;
590
623
  settings: FrontendSettingsRegistry;
package/dist/types.js CHANGED
@@ -1,4 +1,4 @@
1
- import packageMetadataSchemaData from './openforgePackageMetadataSchema.json';
1
+ import packageMetadataSchemaData from './openforgePackageMetadataSchema.json' with { type: 'json' };
2
2
  function readSupportedOpenForgeApiVersions() {
3
3
  const versions = packageMetadataSchemaData.properties.apiVersion.enum;
4
4
  if (!Array.isArray(versions) || versions.length === 0 || !versions.every((version) => typeof version === 'number' && Number.isInteger(version))) {
@@ -37,6 +37,7 @@ const OPENFORGE_PLUGIN_CAPABILITY_TYPE_MEMBERS = [
37
37
  'taskLinks',
38
38
  'appEnablement',
39
39
  'customSidebarNavigation',
40
+ 'reviewUI',
40
41
  ];
41
42
  function assertOpenForgePluginCapabilitiesMatchSchema() {
42
43
  const schemaCapabilities = packageMetadataSchemaData.properties.requires.items.enum;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@openforge-app/plugin-sdk",
3
- "version": "0.2.7",
3
+ "version": "0.2.9",
4
4
  "license": "MIT",
5
5
  "repository": {
6
6
  "type": "git",
@@ -87,28 +87,27 @@
87
87
  "publishConfig": {
88
88
  "access": "public"
89
89
  },
90
- "scripts": {
91
- "clean": "node -e \"import('node:fs').then(({ rmSync }) => rmSync('dist', { recursive: true, force: true }))\"",
92
- "build": "pnpm run clean && tsc && pnpm run build:assets",
93
- "build:assets": "node ./scripts/copy-package-assets.mjs",
94
- "check:contract": "node ./scripts/check-published-contract.mjs",
95
- "icons:generate": "node ./scripts/generate-file-type-icons.mjs",
96
- "prepack": "pnpm run build",
97
- "prepublishOnly": "pnpm run check:contract",
98
- "test": "vitest run"
99
- },
100
90
  "dependencies": {
101
- "dompurify": "catalog:",
102
- "marked": "catalog:"
91
+ "dompurify": "^3.4.13",
92
+ "marked": "^18.0.10"
103
93
  },
104
94
  "peerDependencies": {
105
95
  "svelte": "^5.0.0"
106
96
  },
107
97
  "devDependencies": {
108
- "@types/node": "catalog:pinned",
109
- "svelte": "catalog:pinned",
110
- "typescript": "catalog:",
111
- "vitest": "catalog:",
98
+ "@types/node": "26.2.0",
99
+ "svelte": "5.56.9",
100
+ "semver": "^7.8.5",
101
+ "typescript": "^7.0.2",
102
+ "vitest": "^4.1.11",
112
103
  "vscode-material-icons": "^0.1.1"
104
+ },
105
+ "scripts": {
106
+ "clean": "node -e \"import('node:fs').then(({ rmSync }) => rmSync('dist', { recursive: true, force: true }))\"",
107
+ "build": "pnpm run clean && tsc && pnpm run build:assets",
108
+ "build:assets": "node ./scripts/copy-package-assets.mjs",
109
+ "check:contract": "node ./scripts/check-published-contract.mjs",
110
+ "icons:generate": "node ./scripts/generate-file-type-icons.mjs",
111
+ "test": "vitest run"
113
112
  }
114
- }
113
+ }