@rigkit/provider-freestyle 0.2.2 → 0.2.3

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/README.md CHANGED
@@ -6,5 +6,6 @@ This package supplies:
6
6
 
7
7
  - `freestyle.provider(...)` for Freestyle VM/snapshot workflow tasks
8
8
  - `freestyle.terminal()` for provider-owned browser terminal sessions targeting Freestyle VMs
9
+ - `providers.freestyle.cmux.createSshOptions(...)` and `providers.freestyle.vscode.createUrl(...)` adapter helpers
9
10
  - `createFreestyleProvider(...)` for low-level Freestyle VM operations
10
11
  - Freestyle-specific JSON state helpers backed by the Rigkit-owned provider storage table
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rigkit/provider-freestyle",
3
- "version": "0.2.2",
3
+ "version": "0.2.3",
4
4
  "type": "module",
5
5
  "repository": {
6
6
  "type": "git",
@@ -18,8 +18,9 @@
18
18
  "dependencies": {
19
19
  "freestyle": "latest",
20
20
  "zod": "^4",
21
- "@rigkit/engine": "0.2.2",
22
- "@rigkit/sdk": "0.2.2"
21
+ "@rigkit/sdk": "0.2.3",
22
+ "@rigkit/provider-cmux": "0.2.3",
23
+ "@rigkit/engine": "0.2.3"
23
24
  },
24
25
  "devDependencies": {
25
26
  "@types/bun": "latest",
package/src/index.ts CHANGED
@@ -14,7 +14,7 @@ import {
14
14
  createFreestyleWorkflowProvider,
15
15
  isFreestyleVmSnapshotRef,
16
16
  } from "./provider.ts";
17
- import type { FreestyleRuntime, FreestyleTerminalRuntime, FreestyleWorkspaceContext } from "./provider.ts";
17
+ import type { FreestyleRuntime, FreestyleTerminalRuntime } from "./provider.ts";
18
18
  import { createFreestyleStore } from "./store.ts";
19
19
 
20
20
  const freestyleProviderConfigSchema = z.object({
@@ -31,8 +31,7 @@ export type FreestyleProviderConfig = z.output<typeof freestyleProviderConfigSch
31
31
  export type FreestyleProviderDefinition = WorkflowProviderDefinition<
32
32
  typeof FREESTYLE_PROVIDER_ID,
33
33
  FreestyleProviderConfig,
34
- FreestyleRuntime,
35
- FreestyleWorkspaceContext
34
+ FreestyleRuntime
36
35
  >;
37
36
 
38
37
  export type FreestyleTerminalProviderDefinition = WorkflowProviderDefinition<
@@ -63,7 +62,7 @@ export const freestyleProviderPlugin: BaseProviderPlugin = {
63
62
  createProvider({ provider, storage }) {
64
63
  const config = parseFreestyleProviderConfig(provider.config);
65
64
  const { apiKey, ...vm } = config;
66
- let controller: Promise<WorkflowProviderController<FreestyleRuntime, FreestyleWorkspaceContext>> | undefined;
65
+ let controller: Promise<WorkflowProviderController<FreestyleRuntime>> | undefined;
67
66
 
68
67
  const load = async () => {
69
68
  controller ??= create();
@@ -103,20 +102,7 @@ export const freestyleProviderPlugin: BaseProviderPlugin = {
103
102
  providerId: FREESTYLE_PROVIDER_ID,
104
103
  runtime: async (context) => await (await load()).runtime(context),
105
104
  validateArtifact: (ref) => isFreestyleVmSnapshotRef(ref),
106
- workspace: {
107
- canUse: (ref) => isFreestyleVmSnapshotRef(ref),
108
- createWorkspace: async (sourceRef, input) =>
109
- await (await load()).workspace!.createWorkspace(sourceRef, input),
110
- deleteWorkspace: async (workspace) =>
111
- await (await load()).workspace!.deleteWorkspace(workspace),
112
- snapshotWorkspace: async (workspace) =>
113
- await (await load()).workspace!.snapshotWorkspace(workspace),
114
- ssh: async (workspaceOrResourceId, options) =>
115
- await (await load()).workspace!.ssh(workspaceOrResourceId, options),
116
- workspaceContext: async (workspace) =>
117
- await (await load()).workspace!.workspaceContext!(workspace),
118
- },
119
- } satisfies WorkflowProviderController<FreestyleRuntime, FreestyleWorkspaceContext>;
105
+ } satisfies WorkflowProviderController<FreestyleRuntime>;
120
106
  },
121
107
  };
122
108
 
@@ -148,12 +134,14 @@ export { createFreestyleStore } from "./store.ts";
148
134
  export { createFreestyleTerminalSession } from "./terminal-session.ts";
149
135
  export { RIGKIT_PROVIDER_FREESTYLE_VERSION } from "./version.ts";
150
136
  export type {
137
+ FreestyleCmuxSshOptions,
138
+ FreestyleCmuxSshOptionsInput,
151
139
  FreestyleRuntime,
152
140
  FreestyleTerminalRuntime,
141
+ FreestyleVscodeUrlOptions,
153
142
  FreestyleVmConfig,
154
143
  FreestyleVmRuntime,
155
144
  FreestyleVmSnapshotRef,
156
- FreestyleWorkspaceContext,
157
145
  } from "./provider.ts";
158
146
  export type { FreestyleGitRelationship, FreestyleIdentity } from "./store.ts";
159
147
 
@@ -8,7 +8,6 @@ import type {
8
8
  WorkflowEvent,
9
9
  } from "@rigkit/engine";
10
10
  import { createFreestyleWorkflowController, wrapCommand } from "./provider.ts";
11
- import type { FreestyleWorkspaceContext } from "./provider.ts";
12
11
 
13
12
  describe("Freestyle provider command wrapper", () => {
14
13
  test("sets a root HOME fallback for exec commands", () => {
@@ -30,7 +29,7 @@ describe("Freestyle provider command wrapper", () => {
30
29
  const provider = new StreamingProvider();
31
30
  const controller = createFreestyleWorkflowController(provider);
32
31
  const runtime = await controller.runtime(providerContext(events));
33
- const vm = runtime.vms.fromWorkspace({ resourceId: "vm-stream" });
32
+ const vm = runtime.vms.fromId("vm-stream");
34
33
 
35
34
  const result = await vm.exec("printf ready", {
36
35
  name: "stream command",
@@ -63,6 +62,46 @@ describe("Freestyle provider command wrapper", () => {
63
62
  },
64
63
  ]);
65
64
  });
65
+
66
+ test("creates cmux ssh options with Freestyle-owned ssh settings", async () => {
67
+ const provider = new StreamingProvider();
68
+ const controller = createFreestyleWorkflowController(provider);
69
+ const runtime = await controller.runtime(providerContext([]));
70
+ const vm = runtime.vms.fromId("vm-stream");
71
+
72
+ const ssh = await runtime.cmux.createSshOptions(vm, {
73
+ sshOptions: ["ServerAliveInterval=15"],
74
+ skipDaemonBootstrap: true,
75
+ });
76
+
77
+ expect(ssh).toEqual({
78
+ kind: "ssh",
79
+ destination: "root,token@localhost",
80
+ skipDaemonBootstrap: true,
81
+ sshOptions: [
82
+ "StrictHostKeyChecking=no",
83
+ "UserKnownHostsFile=/dev/null",
84
+ "LogLevel=ERROR",
85
+ "IdentitiesOnly=yes",
86
+ "IdentityFile=/dev/null",
87
+ "ControlMaster=no",
88
+ "ServerAliveInterval=15",
89
+ ],
90
+ });
91
+ });
92
+
93
+ test("creates VS Code URLs using the Freestyle ssh authority", async () => {
94
+ const provider = new StreamingProvider();
95
+ const controller = createFreestyleWorkflowController(provider);
96
+ const runtime = await controller.runtime(providerContext([]));
97
+ const vm = runtime.vms.fromId("vm-stream");
98
+
99
+ const url = await runtime.vscode.createUrl(vm, { cwd: "/workspace/site" });
100
+
101
+ expect(url).toBe(
102
+ "vscode://vscode-remote/ssh-remote+root%3Atoken%40localhost/workspace/site?windowId=_blank",
103
+ );
104
+ });
66
105
  });
67
106
 
68
107
  const sshConnection: SshConnection = {
@@ -73,7 +112,7 @@ const sshConnection: SshConnection = {
73
112
  command: "ssh vm-stream",
74
113
  };
75
114
 
76
- class StreamingProvider implements BaseDevMachineProvider<FreestyleWorkspaceContext> {
115
+ class StreamingProvider implements BaseDevMachineProvider {
77
116
  readonly providerId = "freestyle";
78
117
 
79
118
  async createVm(): Promise<VmHandle> {
@@ -103,19 +142,13 @@ class StreamingProvider implements BaseDevMachineProvider<FreestyleWorkspaceCont
103
142
  return sshConnection;
104
143
  }
105
144
 
106
- async workspaceContext(): Promise<FreestyleWorkspaceContext> {
107
- return {
108
- ssh: sshConnection,
109
- host: sshConnection.host,
110
- username: sshConnection.username,
111
- vscodeAuthority: "root@localhost",
112
- };
113
- }
114
-
115
145
  async deleteVm(): Promise<void> {}
116
146
  }
117
147
 
118
- function providerContext(events: WorkflowEvent[]): ProviderRuntimeContext {
148
+ function providerContext(
149
+ events: WorkflowEvent[],
150
+ local: Partial<ProviderRuntimeContext["local"]> = {},
151
+ ): ProviderRuntimeContext {
119
152
  return {
120
153
  workflow: "workflow",
121
154
  nodePath: "workflow.step",
@@ -129,6 +162,7 @@ function providerContext(events: WorkflowEvent[]): ProviderRuntimeContext {
129
162
  },
130
163
  local: {
131
164
  open: async () => {},
165
+ ...local,
132
166
  },
133
167
  metadata: () => {},
134
168
  };
package/src/provider.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  import { Freestyle, VmBaseImage } from "freestyle";
2
- import type { CommandOptions, ExecOptions, ExecOutputChunk, ExecResult, JsonValue, WorkspaceRecord } from "@rigkit/sdk";
2
+ import type { CommandOptions, ExecOptions, ExecOutputChunk, ExecResult } from "@rigkit/sdk";
3
3
  import type {
4
4
  BaseDevMachineProvider,
5
5
  ProviderRuntimeContext,
@@ -9,6 +9,7 @@ import type {
9
9
  VmHandle,
10
10
  WorkflowProviderController,
11
11
  } from "@rigkit/engine";
12
+ import type { CmuxOpenSshInput } from "@rigkit/provider-cmux";
12
13
  import type { FreestyleIdentityId, FreestyleToken } from "./auth.ts";
13
14
  import { createFreestyleTerminalSession } from "./terminal-session.ts";
14
15
 
@@ -25,13 +26,6 @@ export type FreestyleVmConfig = {
25
26
  idleTimeoutSeconds?: number | null;
26
27
  };
27
28
 
28
- export type FreestyleWorkspaceContext = {
29
- ssh: SshConnection;
30
- host: string;
31
- username: string;
32
- vscodeAuthority: string;
33
- };
34
-
35
29
  export type FreestyleVmSnapshotRef = {
36
30
  provider: typeof FREESTYLE_PROVIDER_ID;
37
31
  kind: "vmSnapshot";
@@ -50,13 +44,36 @@ export type FreestyleVmRuntime = {
50
44
  ssh(options?: SshOptions): Promise<SshConnection>;
51
45
  };
52
46
 
47
+ export type FreestyleCmuxSshOptions = Exclude<CmuxOpenSshInput, string>;
48
+
49
+ export type FreestyleCmuxSshOptionsInput = Omit<
50
+ FreestyleCmuxSshOptions,
51
+ "kind" | "destination" | "host" | "username"
52
+ > & SshOptions;
53
+
54
+ export type FreestyleVscodeUrlOptions = SshOptions & {
55
+ cwd?: string;
56
+ };
57
+
53
58
  export type FreestyleRuntime = {
54
59
  vms: {
55
60
  create(): Promise<FreestyleVmRuntime>;
56
61
  fromSnapshot(ref: FreestyleVmSnapshotRef): Promise<FreestyleVmRuntime>;
57
- fromWorkspace(workspace: Pick<WorkspaceRecord, "resourceId">): FreestyleVmRuntime;
62
+ fromId(vmId: string): FreestyleVmRuntime;
63
+ delete(vmId: string): Promise<void>;
64
+ };
65
+ cmux: {
66
+ createSshOptions(
67
+ target: FreestyleVmRuntime | FreestyleVmSnapshotRef,
68
+ options?: FreestyleCmuxSshOptionsInput,
69
+ ): Promise<FreestyleCmuxSshOptions>;
70
+ };
71
+ vscode: {
72
+ createUrl(
73
+ target: FreestyleVmRuntime | FreestyleVmSnapshotRef,
74
+ options?: FreestyleVscodeUrlOptions,
75
+ ): Promise<string>;
58
76
  };
59
- openWorkspace(target: FreestyleVmRuntime | FreestyleVmSnapshotRef, options?: { cwd?: string }): Promise<void>;
60
77
  };
61
78
 
62
79
  export type FreestyleTerminalRuntime = {
@@ -75,7 +92,7 @@ export function createFreestyleProvider(input: {
75
92
  identityId: FreestyleIdentityId;
76
93
  token: FreestyleToken;
77
94
  vm: FreestyleVmConfig;
78
- }): BaseDevMachineProvider<FreestyleWorkspaceContext> {
95
+ }): BaseDevMachineProvider {
79
96
  return new FreestyleProvider(input.apiKey, input.identityId, input.token, input.vm);
80
97
  }
81
98
 
@@ -84,13 +101,13 @@ export function createFreestyleWorkflowProvider(input: {
84
101
  identityId: FreestyleIdentityId;
85
102
  token: FreestyleToken;
86
103
  vm: FreestyleVmConfig;
87
- }): WorkflowProviderController<FreestyleRuntime, FreestyleWorkspaceContext> {
104
+ }): WorkflowProviderController<FreestyleRuntime> {
88
105
  return createFreestyleWorkflowController(createFreestyleProvider(input));
89
106
  }
90
107
 
91
108
  export function createFreestyleWorkflowController(
92
- provider: BaseDevMachineProvider<FreestyleWorkspaceContext>,
93
- ): WorkflowProviderController<FreestyleRuntime, FreestyleWorkspaceContext> {
109
+ provider: BaseDevMachineProvider,
110
+ ): WorkflowProviderController<FreestyleRuntime> {
94
111
  return {
95
112
  providerId: FREESTYLE_PROVIDER_ID,
96
113
  runtime(context) {
@@ -99,44 +116,6 @@ export function createFreestyleWorkflowController(
99
116
  validateArtifact(ref) {
100
117
  return isFreestyleVmSnapshotRef(ref);
101
118
  },
102
- workspace: {
103
- canUse(ref) {
104
- return isFreestyleVmSnapshotRef(ref);
105
- },
106
- async createWorkspace(ref, input) {
107
- if (!isFreestyleVmSnapshotRef(ref)) {
108
- throw new Error(`Freestyle cannot create a workspace from this artifact`);
109
- }
110
- const vm = await provider.createVmFromSnapshot({ snapshotId: ref.snapshotId });
111
- return {
112
- providerId: FREESTYLE_PROVIDER_ID,
113
- resourceId: vm.vmId,
114
- snapshotId: ref.snapshotId,
115
- sourceRef: ref,
116
- metadata: { name: input.name },
117
- };
118
- },
119
- async deleteWorkspace(workspace) {
120
- await provider.deleteVm({ vmId: workspace.resourceId });
121
- },
122
- async snapshotWorkspace(workspace) {
123
- const snapshot = await provider.snapshot({ vmId: workspace.resourceId });
124
- return {
125
- providerId: FREESTYLE_PROVIDER_ID,
126
- resourceId: workspace.resourceId,
127
- snapshotId: snapshot.snapshotId,
128
- sourceRef: snapshotRef(snapshot),
129
- };
130
- },
131
- async ssh(workspaceOrResourceId, options) {
132
- return await provider.ssh({ vmId: workspaceOrResourceId }, options);
133
- },
134
- async workspaceContext(workspace) {
135
- const context = await provider.workspaceContext?.({ vmId: workspace.resourceId }, { workspace });
136
- if (!context) throw new Error(`Freestyle provider does not expose workspace context`);
137
- return context;
138
- },
139
- },
140
119
  };
141
120
  }
142
121
 
@@ -162,7 +141,7 @@ export function createFreestyleTerminalController(): WorkflowProviderController<
162
141
  };
163
142
  }
164
143
 
165
- class FreestyleProvider implements BaseDevMachineProvider<FreestyleWorkspaceContext> {
144
+ class FreestyleProvider implements BaseDevMachineProvider {
166
145
  readonly providerId = FREESTYLE_PROVIDER_ID;
167
146
  private readonly client: Freestyle;
168
147
  private readonly identityId: FreestyleIdentityId;
@@ -261,13 +240,18 @@ class FreestyleProvider implements BaseDevMachineProvider<FreestyleWorkspaceCont
261
240
  };
262
241
  }
263
242
 
264
- async workspaceContext(vm: VmHandle): Promise<FreestyleWorkspaceContext> {
243
+ async workspaceContext(vm: VmHandle): Promise<{
244
+ ssh: SshConnection;
245
+ host: string;
246
+ username: string;
247
+ vscodeAuthority: string;
248
+ }> {
265
249
  const ssh = await this.ssh(vm);
266
250
  return {
267
251
  ssh,
268
252
  host: ssh.host,
269
253
  username: ssh.username,
270
- vscodeAuthority: `${ssh.username}:${this.token}@${ssh.host}`,
254
+ vscodeAuthority: vscodeAuthorityForSsh(ssh),
271
255
  };
272
256
  }
273
257
 
@@ -293,60 +277,103 @@ class FreestyleProvider implements BaseDevMachineProvider<FreestyleWorkspaceCont
293
277
  }
294
278
 
295
279
  function createFreestyleRuntime(
296
- provider: BaseDevMachineProvider<FreestyleWorkspaceContext>,
280
+ provider: BaseDevMachineProvider,
297
281
  context: ProviderRuntimeContext,
298
282
  ): FreestyleRuntime {
299
283
  const fromHandle = (vm: VmHandle): FreestyleVmRuntime => createVmRuntime(provider, vm, context);
300
284
 
301
- return {
302
- vms: {
303
- create: async () => {
304
- const vm = await provider.createVm();
305
- context.emit({ type: "vm.created", providerId: provider.providerId, vmId: vm.vmId });
306
- return fromHandle(vm);
307
- },
308
- fromSnapshot: async (ref) => {
309
- const vm = await provider.createVmFromSnapshot({ snapshotId: ref.snapshotId });
310
- context.emit({
311
- type: "vm.created",
312
- providerId: provider.providerId,
313
- vmId: vm.vmId,
314
- fromSnapshotId: ref.snapshotId,
315
- });
316
- return fromHandle(vm);
317
- },
318
- fromWorkspace: (workspace) => fromHandle({ vmId: workspace.resourceId }),
285
+ const vms: FreestyleRuntime["vms"] = {
286
+ create: async () => {
287
+ const vm = await provider.createVm();
288
+ context.emit({ type: "vm.created", providerId: provider.providerId, vmId: vm.vmId });
289
+ return fromHandle(vm);
319
290
  },
320
- openWorkspace: async (target, options) => {
321
- const vm = isFreestyleVmSnapshotRef(target)
322
- ? await createFreestyleRuntime(provider, context).vms.fromSnapshot(target)
323
- : target;
324
- const workspaceContext = await provider.workspaceContext?.({ vmId: vm.vmId }, {
325
- workspace: {
326
- id: vm.vmId,
327
- name: vm.vmId,
328
- providerId: provider.providerId,
329
- workflow: context.workflow,
330
- resourceId: vm.vmId,
331
- sourceRef: null,
332
- context: {},
333
- createdAt: new Date().toISOString(),
334
- updatedAt: new Date().toISOString(),
335
- metadata: {},
336
- },
291
+ fromSnapshot: async (ref) => {
292
+ const vm = await provider.createVmFromSnapshot({ snapshotId: ref.snapshotId });
293
+ context.emit({
294
+ type: "vm.created",
295
+ providerId: provider.providerId,
296
+ vmId: vm.vmId,
297
+ fromSnapshotId: ref.snapshotId,
337
298
  });
338
- if (!workspaceContext?.vscodeAuthority) {
339
- throw new Error(`Freestyle workspace context did not include a VS Code authority`);
340
- }
341
- await context.local.open(
342
- `vscode://vscode-remote/ssh-remote+${encodeURIComponent(workspaceContext.vscodeAuthority)}${options?.cwd ?? ""}?windowId=_blank`,
343
- );
299
+ return fromHandle(vm);
300
+ },
301
+ fromId: (vmId) => fromHandle({ vmId }),
302
+ delete: async (vmId) => {
303
+ await provider.deleteVm({ vmId });
304
+ },
305
+ };
306
+
307
+ const resolveVm = async (
308
+ target: FreestyleVmRuntime | FreestyleVmSnapshotRef,
309
+ ): Promise<FreestyleVmRuntime> => isFreestyleVmSnapshotRef(target) ? await vms.fromSnapshot(target) : target;
310
+
311
+ const vscode: FreestyleRuntime["vscode"] = {
312
+ createUrl: async (target, options) => {
313
+ const vm = await resolveVm(target);
314
+ const { cwd, user } = options ?? {};
315
+ const ssh = await vm.ssh(user !== undefined ? { user } : undefined);
316
+ return freestyleVscodeUrl(ssh, { cwd });
344
317
  },
345
318
  };
319
+
320
+ return {
321
+ vms,
322
+ cmux: {
323
+ createSshOptions: async (target, options) => {
324
+ const vm = await resolveVm(target);
325
+ const { user, ...sshOptions } = options ?? {};
326
+ const ssh = await vm.ssh(user !== undefined ? { user } : undefined);
327
+ return freestyleCmuxSshOptions(ssh, sshOptions);
328
+ },
329
+ },
330
+ vscode,
331
+ };
332
+ }
333
+
334
+ const freestyleCmuxTokenSshOptions = [
335
+ "StrictHostKeyChecking=no",
336
+ "UserKnownHostsFile=/dev/null",
337
+ "LogLevel=ERROR",
338
+ "IdentitiesOnly=yes",
339
+ "IdentityFile=/dev/null",
340
+ "ControlMaster=no",
341
+ ] as const;
342
+
343
+ function freestyleCmuxSshOptions(
344
+ connection: SshConnection,
345
+ options: Omit<FreestyleCmuxSshOptionsInput, keyof SshOptions> | undefined,
346
+ ): FreestyleCmuxSshOptions {
347
+ const { sshOptions, port, ...rest } = options ?? {};
348
+ const mergedSshOptions = [
349
+ ...(connection.auth.type === "token" ? freestyleCmuxTokenSshOptions : []),
350
+ ...(sshOptions ?? []),
351
+ ];
352
+ return {
353
+ kind: "ssh",
354
+ destination: freestyleCmuxDestination(connection),
355
+ ...(port !== undefined || connection.port !== undefined ? { port: port ?? connection.port } : {}),
356
+ ...rest,
357
+ ...(mergedSshOptions.length ? { sshOptions: mergedSshOptions } : {}),
358
+ };
359
+ }
360
+
361
+ function freestyleCmuxDestination(connection: SshConnection): string {
362
+ if (connection.auth.type === "token") return `${connection.username},${connection.auth.token}@${connection.host}`;
363
+ return `${connection.username}@${connection.host}`;
364
+ }
365
+
366
+ function vscodeAuthorityForSsh(connection: SshConnection): string {
367
+ if (connection.auth.type === "token") return `${connection.username}:${connection.auth.token}@${connection.host}`;
368
+ return `${connection.username}@${connection.host}`;
369
+ }
370
+
371
+ function freestyleVscodeUrl(connection: SshConnection, options: { cwd?: string } = {}): string {
372
+ return `vscode://vscode-remote/ssh-remote+${encodeURIComponent(vscodeAuthorityForSsh(connection))}${options.cwd ?? ""}?windowId=_blank`;
346
373
  }
347
374
 
348
375
  function createVmRuntime(
349
- provider: BaseDevMachineProvider<FreestyleWorkspaceContext>,
376
+ provider: BaseDevMachineProvider,
350
377
  vm: VmHandle,
351
378
  context: ProviderRuntimeContext,
352
379
  ): FreestyleVmRuntime {
package/src/version.ts CHANGED
@@ -1 +1 @@
1
- export const RIGKIT_PROVIDER_FREESTYLE_VERSION = "0.2.2";
1
+ export const RIGKIT_PROVIDER_FREESTYLE_VERSION = "0.2.3";