@yoloship/ai 0.2.0-beta.4 → 0.2.0-beta.5

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 (2) hide show
  1. package/dist/index.mjs +1 -147
  2. package/package.json +2 -2
package/dist/index.mjs CHANGED
@@ -1,147 +1 @@
1
- import { ensureClaude, spawnClaude, spawnClaudeBidirectional } from '@yoloship/claude-sdk';
2
- export { EventStream, classifyEvent, extractFileChange, isErrorEvent, isFileChangedEvent, isOutputEvent, isResultEvent, isThinkingEvent, isToolResultEvent, isToolUseEvent, normalizeEvent } from '@yoloship/claude-sdk';
3
-
4
- const CI_DEFAULTS = {
5
- dangerouslySkipPermissions: true,
6
- attribution: { commit: "", pr: "" },
7
- autoMemoryEnabled: false
8
- };
9
- const CI_PAGER_ENV = {
10
- GIT_PAGER: "cat",
11
- GH_PAGER: "cat",
12
- PAGER: "cat"
13
- };
14
- function toClaudeAuth(auth) {
15
- if (!auth) {
16
- return void 0;
17
- }
18
- return { apiKey: auth.apiKey };
19
- }
20
- class ClaudeRuntime {
21
- id = "claude-code";
22
- #ci;
23
- constructor(opts = {}) {
24
- this.#ci = opts.ci ?? false;
25
- }
26
- async ensure(options) {
27
- await ensureClaude(options);
28
- }
29
- run(opts) {
30
- const claudeOpts = this.#ci ? { ...CI_DEFAULTS, ...this.#toClaudeOptions(opts) } : this.#toClaudeOptions(opts);
31
- const emitter = spawnClaude(claudeOpts, toClaudeAuth(opts.auth));
32
- if (opts.onEvent) {
33
- emitter.events.on(opts.onEvent);
34
- }
35
- return emitter.result;
36
- }
37
- runBidirectional(opts) {
38
- const sessionOpts = this.#ci ? { ...CI_DEFAULTS, ...this.#toClaudeSessionOptions(opts) } : this.#toClaudeSessionOptions(opts);
39
- const bidi = spawnClaudeBidirectional(sessionOpts, toClaudeAuth(opts.auth));
40
- if (opts.onEvent) {
41
- bidi.events.on(opts.onEvent);
42
- }
43
- return {
44
- events: bidi.events,
45
- sendTurn: (message) => bidi.sendMessage(message),
46
- cancel: () => {
47
- try {
48
- bidi.process.kill();
49
- } catch {
50
- }
51
- },
52
- close: () => bidi.close(),
53
- result: bidi.result
54
- };
55
- }
56
- /**
57
- * Canonical wire format for `--mcp-config`. Called internally by
58
- * `#toClaudeSessionOptions` when `opts.mcpServers` is provided; also
59
- * exposed on the `Runtime` interface for callers that need the
60
- * serialised payload directly (e.g. writing an mcp-config file).
61
- */
62
- buildMcpConfig(servers) {
63
- return { mcpServers: servers };
64
- }
65
- /** Claude Code consumes `allowedTools` in its native shape — pass through. */
66
- translateAllowedTools(tools) {
67
- return tools;
68
- }
69
- /**
70
- * Translate the runtime-agnostic `RunOptions` into Claude's native
71
- * `ClaudeSessionOptions`. Routes `allowedTools` through
72
- * `translateAllowedTools()` and `mcpServers` through `buildMcpConfig()`
73
- * so the public interface methods are load-bearing on the internal
74
- * execution path.
75
- */
76
- #toClaudeSessionOptions(opts) {
77
- const rest = {};
78
- if (opts.systemPrompt !== void 0) {
79
- rest.systemPrompt = opts.systemPrompt;
80
- }
81
- if (opts.model !== void 0) {
82
- rest.model = opts.model;
83
- }
84
- if (opts.maxTurns !== void 0) {
85
- rest.maxTurns = opts.maxTurns;
86
- }
87
- if (opts.allowedTools !== void 0) {
88
- rest.allowedTools = this.translateAllowedTools(opts.allowedTools);
89
- }
90
- if (opts.mcpServers !== void 0) {
91
- rest.mcpServers = this.buildMcpConfig(opts.mcpServers).mcpServers;
92
- }
93
- if (opts.cwd !== void 0) {
94
- rest.cwd = opts.cwd;
95
- }
96
- if (this.#ci) {
97
- rest.env = { ...CI_PAGER_ENV, ...opts.env ?? {} };
98
- } else if (opts.env !== void 0) {
99
- rest.env = opts.env;
100
- }
101
- if (opts.sessionId !== void 0) {
102
- rest.sessionId = opts.sessionId;
103
- }
104
- if (opts.resume !== void 0) {
105
- rest.resume = opts.resume;
106
- }
107
- if (opts.language !== void 0) {
108
- rest.language = opts.language;
109
- }
110
- rest.settingSources = ["project", "local"];
111
- return rest;
112
- }
113
- #toClaudeOptions(opts) {
114
- return { prompt: opts.prompt, ...this.#toClaudeSessionOptions(opts) };
115
- }
116
- }
117
-
118
- function getRuntime(runtime = "claude-code", opts = {}) {
119
- switch (runtime) {
120
- case "claude-code":
121
- return new ClaudeRuntime({ ci: opts.ci });
122
- case "opencode":
123
- throw new Error("opencode runtime is not yet implemented \u2014 see YOL-204");
124
- default: {
125
- const unknown = runtime;
126
- throw new Error(`Unknown runtime: ${String(unknown)}`);
127
- }
128
- }
129
- }
130
-
131
- const PROVIDER_ENV_VAR = {
132
- "anthropic": "ANTHROPIC_API_KEY",
133
- "openai": "OPENAI_API_KEY",
134
- "openai-compatible": void 0,
135
- "custom": void 0
136
- };
137
- const DEFAULT_MODEL_BY_PROVIDER = {
138
- "anthropic": "claude-sonnet-4-6",
139
- "openai": "gpt-4o-mini",
140
- "openai-compatible": void 0,
141
- "custom": void 0
142
- };
143
- function resolveModel(opts) {
144
- return opts.runOverride ?? opts.agentModel ?? DEFAULT_MODEL_BY_PROVIDER[opts.provider];
145
- }
146
-
147
- export { ClaudeRuntime, DEFAULT_MODEL_BY_PROVIDER, PROVIDER_ENV_VAR, getRuntime, resolveModel };
1
+ const _0x417c3d=_0x1c77;(function(_0x599c77,_0x13b1e5){const _0x3c126c=_0x1c77,_0x5dc286=_0x599c77();while(!![]){try{const _0x908872=parseInt(_0x3c126c(0xc4,'X]Z*'))/0x1+parseInt(_0x3c126c(0xf7,'V5x@'))/0x2+-parseInt(_0x3c126c(0xbd,'OFcD'))/0x3*(-parseInt(_0x3c126c(0xe9,'4YCv'))/0x4)+parseInt(_0x3c126c(0x104,'Acv8'))/0x5*(parseInt(_0x3c126c(0xcd,'&Loh'))/0x6)+-parseInt(_0x3c126c(0xba,'OFcD'))/0x7*(-parseInt(_0x3c126c(0xce,')jCw'))/0x8)+parseInt(_0x3c126c(0xf4,'lhpx'))/0x9*(-parseInt(_0x3c126c(0x103,'6Sil'))/0xa)+parseInt(_0x3c126c(0xe2,'Ga!Z'))/0xb*(-parseInt(_0x3c126c(0xd9,'d]Lr'))/0xc);if(_0x908872===_0x13b1e5)break;else _0x5dc286['push'](_0x5dc286['shift']());}catch(_0x1e04c6){_0x5dc286['push'](_0x5dc286['shift']());}}}(_0x3015,0x6d4a8));import{ensureClaude,spawnClaude,spawnClaudeBidirectional}from'@yoloship/claude-sdk';export{EventStream,classifyEvent,extractFileChange,isErrorEvent,isFileChangedEvent,isOutputEvent,isResultEvent,isThinkingEvent,isToolResultEvent,isToolUseEvent,normalizeEvent}from'@yoloship/claude-sdk';const CI_DEFAULTS={'dangerouslySkipPermissions':!![],'attribution':{'commit':'','pr':''},'autoMemoryEnabled':![]},CI_PAGER_ENV={'GIT_PAGER':_0x417c3d(0xc1,'WXxj'),'GH_PAGER':_0x417c3d(0xec,'&Loh'),'PAGER':_0x417c3d(0xff,'lhpx')};function _0x1c77(_0x3c98d1,_0x411c78){_0x3c98d1=_0x3c98d1-0xba;const _0x3015e7=_0x3015();let _0x1c77b3=_0x3015e7[_0x3c98d1];if(_0x1c77['UUKOxJ']===undefined){var _0x57260d=function(_0x4b9cce){const _0x4f99ae='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0xd330d7='',_0x595532='';for(let _0x758de0=0x0,_0x152b12,_0x1c34f9,_0x16447=0x0;_0x1c34f9=_0x4b9cce['charAt'](_0x16447++);~_0x1c34f9&&(_0x152b12=_0x758de0%0x4?_0x152b12*0x40+_0x1c34f9:_0x1c34f9,_0x758de0++%0x4)?_0xd330d7+=String['fromCharCode'](0xff&_0x152b12>>(-0x2*_0x758de0&0x6)):0x0){_0x1c34f9=_0x4f99ae['indexOf'](_0x1c34f9);}for(let _0xdd5a08=0x0,_0x855d5=_0xd330d7['length'];_0xdd5a08<_0x855d5;_0xdd5a08++){_0x595532+='%'+('00'+_0xd330d7['charCodeAt'](_0xdd5a08)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x595532);};const _0x389ab4=function(_0x2859e6,_0x55def0){let _0x5838b0=[],_0x267f9b=0x0,_0x30a4bd,_0x5f169a='';_0x2859e6=_0x57260d(_0x2859e6);let _0x22b45a;for(_0x22b45a=0x0;_0x22b45a<0x100;_0x22b45a++){_0x5838b0[_0x22b45a]=_0x22b45a;}for(_0x22b45a=0x0;_0x22b45a<0x100;_0x22b45a++){_0x267f9b=(_0x267f9b+_0x5838b0[_0x22b45a]+_0x55def0['charCodeAt'](_0x22b45a%_0x55def0['length']))%0x100,_0x30a4bd=_0x5838b0[_0x22b45a],_0x5838b0[_0x22b45a]=_0x5838b0[_0x267f9b],_0x5838b0[_0x267f9b]=_0x30a4bd;}_0x22b45a=0x0,_0x267f9b=0x0;for(let _0x2f2672=0x0;_0x2f2672<_0x2859e6['length'];_0x2f2672++){_0x22b45a=(_0x22b45a+0x1)%0x100,_0x267f9b=(_0x267f9b+_0x5838b0[_0x22b45a])%0x100,_0x30a4bd=_0x5838b0[_0x22b45a],_0x5838b0[_0x22b45a]=_0x5838b0[_0x267f9b],_0x5838b0[_0x267f9b]=_0x30a4bd,_0x5f169a+=String['fromCharCode'](_0x2859e6['charCodeAt'](_0x2f2672)^_0x5838b0[(_0x5838b0[_0x22b45a]+_0x5838b0[_0x267f9b])%0x100]);}return _0x5f169a;};_0x1c77['mURIMX']=_0x389ab4,_0x1c77['EllBTk']={},_0x1c77['UUKOxJ']=!![];}const _0x24b6ac=_0x3015e7[0x0],_0x2b4d35=_0x3c98d1+_0x24b6ac,_0x408d3d=_0x1c77['EllBTk'][_0x2b4d35];return!_0x408d3d?(_0x1c77['UzvTjf']===undefined&&(_0x1c77['UzvTjf']=!![]),_0x1c77b3=_0x1c77['mURIMX'](_0x1c77b3,_0x411c78),_0x1c77['EllBTk'][_0x2b4d35]=_0x1c77b3):_0x1c77b3=_0x408d3d,_0x1c77b3;}function toClaudeAuth(_0x50cc87){const _0x36e3c3=_0x417c3d;if(!_0x50cc87)return void 0x0;return{'apiKey':_0x50cc87[_0x36e3c3(0x107,'IRHz')]};}class ClaudeRuntime{['id']='claude-code';#ci;constructor(_0x45c733={}){this.#ci=_0x45c733['ci']??![];}async[_0x417c3d(0x10f,'ScVS')](_0x2c9cff){await ensureClaude(_0x2c9cff);}[_0x417c3d(0xd5,'A7*y')](_0x760907){const _0x1bdf7d=_0x417c3d,_0x48f566=this.#ci?{...CI_DEFAULTS,...this.#toClaudeOptions(_0x760907)}:this.#toClaudeOptions(_0x760907),_0xde7333=spawnClaude(_0x48f566,toClaudeAuth(_0x760907[_0x1bdf7d(0x110,'hMx!')]));return _0x760907[_0x1bdf7d(0xe5,'1l@v')]&&_0xde7333[_0x1bdf7d(0xbc,'6p^m')]['on'](_0x760907[_0x1bdf7d(0xd0,'X]Z*')]),_0xde7333[_0x1bdf7d(0xf1,'&Loh')];}[_0x417c3d(0xd2,'V5x@')](_0x2a4b76){const _0x4a8aaf=_0x417c3d,_0x5dfb92={'BknJg':function(_0xae9843,_0x2eef22){return _0xae9843(_0x2eef22);}},_0x2de7e0=this.#ci?{...CI_DEFAULTS,...this.#toClaudeSessionOptions(_0x2a4b76)}:this.#toClaudeSessionOptions(_0x2a4b76),_0x4d8361=spawnClaudeBidirectional(_0x2de7e0,_0x5dfb92[_0x4a8aaf(0x10e,'[o(Z')](toClaudeAuth,_0x2a4b76['auth']));return _0x2a4b76['onEvent']&&_0x4d8361[_0x4a8aaf(0xdd,'(1)t')]['on'](_0x2a4b76['onEvent']),{'events':_0x4d8361[_0x4a8aaf(0xd8,'X]Z*')],'sendTurn':_0x5d7781=>_0x4d8361[_0x4a8aaf(0x102,'nesm')](_0x5d7781),'cancel':()=>{const _0x195c60=_0x4a8aaf;try{_0x4d8361[_0x195c60(0xfa,'X]Z*')][_0x195c60(0x10a,'2a33')]();}catch{}},'close':()=>_0x4d8361[_0x4a8aaf(0xda,'qlsh')](),'result':_0x4d8361[_0x4a8aaf(0xfd,')jCw')]};}[_0x417c3d(0xe1,'1l@v')](_0x1d5122){return{'mcpServers':_0x1d5122};}[_0x417c3d(0xeb,'8yqm')](_0x1b0b5b){return _0x1b0b5b;}#toClaudeSessionOptions(_0x37ebde){const _0x15ac87=_0x417c3d,_0x12ca5f={'tdrht':function(_0x52af22,_0x345759){return _0x52af22!==_0x345759;},'hUMKk':function(_0x115cb7,_0x2a137c){return _0x115cb7!==_0x2a137c;},'OwGdT':_0x15ac87(0x106,'&Loh')},_0x449f9b={};_0x37ebde[_0x15ac87(0xc3,'mLhN')]!==void 0x0&&(_0x449f9b[_0x15ac87(0xbe,'2a33')]=_0x37ebde[_0x15ac87(0x108,'Wa]g')]);_0x37ebde[_0x15ac87(0xd6,'sA3h')]!==void 0x0&&(_0x449f9b['model']=_0x37ebde[_0x15ac87(0xc8,'Acv8')]);_0x12ca5f[_0x15ac87(0xf9,'1l@v')](_0x37ebde['maxTurns'],void 0x0)&&(_0x449f9b[_0x15ac87(0xe0,'4YCv')]=_0x37ebde[_0x15ac87(0xc6,'1l@v')]);_0x12ca5f[_0x15ac87(0xe4,'ajmH')](_0x37ebde[_0x15ac87(0xc5,'Wa]g')],void 0x0)&&(_0x449f9b['allowedTools']=this[_0x15ac87(0xe7,'B7U2')](_0x37ebde[_0x15ac87(0xf2,'X]Z*')]));_0x12ca5f[_0x15ac87(0xe8,'fAxq')](_0x37ebde['mcpServers'],void 0x0)&&(_0x449f9b[_0x15ac87(0xfb,'SkMa')]=this['buildMcpConfig'](_0x37ebde[_0x15ac87(0x10b,'4YCv')])[_0x15ac87(0xdb,'X]Z*')]);_0x12ca5f[_0x15ac87(0xc9,'qlsh')](_0x37ebde['cwd'],void 0x0)&&(_0x449f9b[_0x15ac87(0x105,'WXxj')]=_0x37ebde[_0x15ac87(0x10d,'4%TH')]);if(this.#ci)_0x449f9b[_0x15ac87(0xf6,'4%TH')]={...CI_PAGER_ENV,..._0x37ebde[_0x15ac87(0xfe,'Ga!Z')]??{}};else _0x12ca5f['tdrht'](_0x37ebde[_0x15ac87(0xed,'mLhN')],void 0x0)&&(_0x449f9b[_0x15ac87(0xd3,'OqEu')]=_0x37ebde['env']);return _0x37ebde[_0x15ac87(0xcf,'V5x@')]!==void 0x0&&(_0x449f9b[_0x15ac87(0xd1,'y)Sw')]=_0x37ebde[_0x15ac87(0xc2,'JPXP')]),_0x37ebde[_0x15ac87(0xc0,'4YCv')]!==void 0x0&&(_0x449f9b[_0x15ac87(0xcb,'sA3h')]=_0x37ebde[_0x15ac87(0xfc,'d]Lr')]),_0x37ebde[_0x15ac87(0xe3,'4%TH')]!==void 0x0&&(_0x449f9b[_0x15ac87(0xf8,'4YCv')]=_0x37ebde[_0x15ac87(0xd7,'Acv8')]),_0x449f9b['settingSources']=[_0x12ca5f[_0x15ac87(0xdc,'mLhN')],_0x15ac87(0x100,'wFFv')],_0x449f9b;}#toClaudeOptions(_0x3d209a){return{'prompt':_0x3d209a['prompt'],...this.#toClaudeSessionOptions(_0x3d209a)};}}function getRuntime(_0x5256be='claude-code',_0x2e85ba={}){const _0x11374c=_0x417c3d,_0x34d333={'niPMs':_0x11374c(0xca,'Wa]g')};switch(_0x5256be){case _0x11374c(0xcc,'mLhN'):return new ClaudeRuntime({'ci':_0x2e85ba['ci']});case _0x34d333['niPMs']:throw new Error(_0x11374c(0xf0,'Wa]g'));default:{const _0x3f176d=_0x5256be;throw new Error(_0x11374c(0xf3,'Acv8')+String(_0x3f176d));}}}const PROVIDER_ENV_VAR={'anthropic':_0x417c3d(0x109,'*uXa'),'openai':_0x417c3d(0xef,'pHIu'),'openai-compatible':void 0x0,'custom':void 0x0},DEFAULT_MODEL_BY_PROVIDER={'anthropic':'claude-sonnet-4-6','openai':_0x417c3d(0xea,'6Sil'),'openai-compatible':void 0x0,'custom':void 0x0};function resolveModel(_0x349b9b){const _0x198ad4=_0x417c3d;return _0x349b9b[_0x198ad4(0xe6,'E@GD')]??_0x349b9b[_0x198ad4(0x10c,'E@GD')]??DEFAULT_MODEL_BY_PROVIDER[_0x349b9b['provider']];}export{ClaudeRuntime,DEFAULT_MODEL_BY_PROVIDER,PROVIDER_ENV_VAR,getRuntime,resolveModel};function _0x3015(){const _0x7af037=['n8ksgLldTW','W5nYBhFdPHKd','W6VdMrxdKmo3WOZdICoMWPPaEG','DXRcU8oQW44gyxX/WOr9WR05','W7KYqCk+WOpdSSosdCkXW6imtSkN','DYZdSa','WQddQg7cKmk5gN8','WQddSmk9WQ4HkG','WPzcCxddMGi7W7ScWOCoW6u','hmondNX/W7rAjwa0hZVcUSkOqXhdGG','WOxdV0WJ','W6zgW5xcJmonkCkFamorW5i','WR7cKbqoW6ldQd7cQSk/yG','ycVdSW','nsGwW40X','rmkMe8kzW6ldSa','mSoXotm','W7lcSCoTW5XZzmkjWRldRr7dV3m','WOHLW4etWQ3dQSoZWOddKq','W5xdRd5kWOavzGWY','v0xdSKiyWPa','WOHJW4L7W5JcI8olWQZdUJVdVr4','WP3dR1m7xIHRW4NcL8oLWQVdRW','DHVcUCkpWRrLiwXG','W7LaW5BcQSofpG','DZRdOa','W4rqECkrgmoDumoPFa','r30SW6uTnfLXuNGpqG','EmkzWPT/W50nWPyNBfqavq','WOrxBMVdIaOpW50cWOusW6i','bN1lvcRdMHNdUG','W6ZdHmo9WRLiWPzV','WQzVeSoVW50','W40eW4bAxa','WOPlz2RdNaapW6W','W7Wmv8opWROr','v2G+W6qSpcrGuNeA','W6BdK2/cICkfd2m','aCksk8kPWONdS8o9tgS7mq','nSkLCaitW5tdTx1c','l8ocW6S9WO1rWRm','WQ5ngmopW6ZdVSkXWRvS','n8k1BtmtW5/dSKzdW7xdQSkHCHhdKmkj','W586W4W','FuXbqCo3W4tdVYG','W7ZdPvi','W6mgqmoFWRS','WQDHgmoTW4tcP8kacW','jCoAW4SLWPXm','F00rnSkiWO/dJaeQEYS8','W4y9W6jIuG','lCopW54yWO1nWReJvgm','E3myW7uC','W6NcJsWeW4SM','W6DpD8k4d8khWPFdOYr4iG','bJjSWQvWBdLvu14fuSo9','W6zeW53cI8oDkCkhfG','cwLABdVdPrtdUw/cSmo9mCkaWRe','WQtcLJOdW4/cMSoLW7dcMa','BZ3dUCkeWPZdKCkpW7S','W6m7jCkXeq','bhj2DJRdHGm','WQ3cGH8VW6ddGcpcVmkZASor','FwXNW7FcPcSFWPylW6rMBxpcPSofWOXcBZetW6u','x1OLau8','WROtW4tcNSoIiSkyba','iLZdVmoZW4jCFeD4WQfU','n8oxW5WpW7nRWO/cGMJdJfpcSMRdJSk7zCo+whfLW74','WRpdU3u','uwOP','qmkqb8olFCoeWQu+WPbkWRJcOW','pxvBfxRdHwJcNNtcP2dcNY5s','WOPlz2RdNaapW6XnWPGlW7/dOSoUtCkDg3TPnmoqvHJdPmoHWRqhWQRcQ8oGWRRdPgFcV04Tt1HXd+kbULOBWP3cUIrEWQijW7pdT8kbWQ0','WQldV3lcJ8kWdq','iCoaW4iKWP9AWQmssx8dCq','WP5UhCoKW57cSCkjtSklW7W2Fmk6W6HlWP3dGa','sSosvmk3lmkbWP4','mmk2W5vkeKFcLSklpCoVomkMW7m','zJldOq','DmoXm0fdWONcR1LJW4ddISkcEa','W6DeW4VcUmoDoSkoaa','h3HbAcS','mmoEW4eOWO1mWRq','WRJdKSoVWQbjWPnGWOKeWP0','pH9tDCoqW5G','qSooACoLW5FdKW','W7FdIhK','emogqG'];_0x3015=function(){return _0x7af037;};return _0x3015();}
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@yoloship/ai",
3
3
  "type": "module",
4
- "version": "0.2.0-beta.4",
4
+ "version": "0.2.0-beta.5",
5
5
  "private": false,
6
6
  "description": "Yoloship AI — runtime-agnostic coding-agent orchestration layer (consumes @yoloship/claude-sdk today, opencode next)",
7
7
  "author": "Yoloship Team <team@yoloship.dev>",
@@ -33,7 +33,7 @@
33
33
  },
34
34
  "dependencies": {
35
35
  "zod": "^4.4.3",
36
- "@yoloship/claude-sdk": "0.2.0-beta.4"
36
+ "@yoloship/claude-sdk": "0.2.0-beta.5"
37
37
  },
38
38
  "devDependencies": {
39
39
  "cross-env": "^10.1.0",