@agenticmail/enterprise 0.5.391 → 0.5.392
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{agent-heartbeat-YS4UEQES.js → agent-heartbeat-4ANIPGGS.js} +1 -1
- package/dist/{agent-tools-2XUSIG4S.js → agent-tools-HLCHRVEV.js} +583 -46
- package/dist/{chunk-A2XPEZ7L.js → chunk-7E7MVJI7.js} +203 -21
- package/dist/{chunk-N3CFP4AQ.js → chunk-CJ6NJPJ6.js} +13 -13
- package/dist/{chunk-MPDSMMSJ.js → chunk-GF6IRQOC.js} +2 -2
- package/dist/{chunk-TCDRCMJJ.js → chunk-GRWV7MDT.js} +1 -1
- package/dist/{chunk-I5MQXMPP.js → chunk-VYP6FF3B.js} +4 -4
- package/dist/{chunk-5TFB3EIE.js → chunk-X54GHR4W.js} +34 -19
- package/dist/{cli-agent-FKBRZT3B.js → cli-agent-WWDX3RIJ.js} +6 -6
- package/dist/{cli-serve-WA6BNLZ3.js → cli-serve-KNEKNOJT.js} +1 -1
- package/dist/{cli-validate-M5OAL2WX.js → cli-validate-5OWQCA4S.js} +1 -1
- package/dist/cli.js +4 -4
- package/dist/index.js +6 -6
- package/dist/{routes-3UJKWSYJ.js → routes-DONZ5NBL.js} +3 -3
- package/dist/{runtime-G6SEDQA6.js → runtime-U3YSWLFD.js} +1 -1
- package/dist/{server-VGZXHRIM.js → server-K5QLSS55.js} +4 -4
- package/dist/{setup-YVTDNY7K.js → setup-5XWBZMTT.js} +1 -1
- package/dist/{skills-SYCLOBYM.js → skills-OKZFMTQT.js} +2 -2
- package/package.json +1 -1
|
@@ -103,10 +103,10 @@ function createPathSandbox(workspaceDir, opts) {
|
|
|
103
103
|
"PATH_TRAVERSAL"
|
|
104
104
|
);
|
|
105
105
|
}
|
|
106
|
-
var
|
|
107
|
-
if (BLOCKED_BASENAMES.indexOf(
|
|
106
|
+
var basename3 = path.basename(normalized);
|
|
107
|
+
if (BLOCKED_BASENAMES.indexOf(basename3) !== -1) {
|
|
108
108
|
throw new SecurityError(
|
|
109
|
-
"Access to sensitive file blocked: " +
|
|
109
|
+
"Access to sensitive file blocked: " + basename3,
|
|
110
110
|
"PATH_BLOCKED"
|
|
111
111
|
);
|
|
112
112
|
}
|
|
@@ -117,7 +117,7 @@ function createPathSandbox(workspaceDir, opts) {
|
|
|
117
117
|
"PATH_BLOCKED"
|
|
118
118
|
);
|
|
119
119
|
}
|
|
120
|
-
if (
|
|
120
|
+
if (basename3 === "config.json" && normalized.indexOf(".docker" + path.sep) !== -1) {
|
|
121
121
|
throw new SecurityError(
|
|
122
122
|
"Access to .docker/config.json blocked",
|
|
123
123
|
"PATH_BLOCKED"
|
|
@@ -347,11 +347,11 @@ function computeOutputSize(result) {
|
|
|
347
347
|
}
|
|
348
348
|
return size;
|
|
349
349
|
}
|
|
350
|
-
function resolveRateLimiterOpts(
|
|
351
|
-
if (overrides && overrides[
|
|
352
|
-
return overrides[
|
|
350
|
+
function resolveRateLimiterOpts(tool2, overrides) {
|
|
351
|
+
if (overrides && overrides[tool2.name]) {
|
|
352
|
+
return overrides[tool2.name];
|
|
353
353
|
}
|
|
354
|
-
var category =
|
|
354
|
+
var category = tool2.category || "utility";
|
|
355
355
|
return DEFAULT_RATE_LIMITS[category] || { maxTokens: 60, refillRate: 60 / 60 };
|
|
356
356
|
}
|
|
357
357
|
var rateLimiters = /* @__PURE__ */ new Map();
|
|
@@ -364,7 +364,7 @@ function getRateLimiter(opts) {
|
|
|
364
364
|
}
|
|
365
365
|
return limiter;
|
|
366
366
|
}
|
|
367
|
-
function wrapToolWithMiddleware(
|
|
367
|
+
function wrapToolWithMiddleware(tool2, config) {
|
|
368
368
|
var agentId = config.agentId || "unknown";
|
|
369
369
|
var auditSink = config.audit?.sink || ConsoleAuditSink;
|
|
370
370
|
var auditEnabled = config.audit?.enabled !== false;
|
|
@@ -372,16 +372,16 @@ function wrapToolWithMiddleware(tool, config) {
|
|
|
372
372
|
var cbEnabled = config.circuitBreaker?.enabled !== false;
|
|
373
373
|
var telemetryEnabled = config.telemetry?.enabled !== false && !!config.telemetry?.sink;
|
|
374
374
|
var telemetrySink = config.telemetry?.sink;
|
|
375
|
-
var useCircuitBreaker = cbEnabled && (
|
|
376
|
-
var rlOpts = resolveRateLimiterOpts(
|
|
375
|
+
var useCircuitBreaker = cbEnabled && (tool2.category === "web" || tool2.category === "browser");
|
|
376
|
+
var rlOpts = resolveRateLimiterOpts(tool2, config.rateLimit?.overrides);
|
|
377
377
|
var wrappedExecute = function(toolCallId, params) {
|
|
378
378
|
return (async function() {
|
|
379
379
|
if (rateLimitEnabled) {
|
|
380
380
|
var limiter = getRateLimiter(rlOpts);
|
|
381
|
-
var rlKey = agentId + ":" +
|
|
381
|
+
var rlKey = agentId + ":" + tool2.name;
|
|
382
382
|
if (!limiter.tryConsume(rlKey)) {
|
|
383
383
|
var retryAfterMs = limiter.getRetryAfterMs(rlKey);
|
|
384
|
-
return errorResult("Rate limited: " +
|
|
384
|
+
return errorResult("Rate limited: " + tool2.name + ". Retry after " + retryAfterMs + "ms.");
|
|
385
385
|
}
|
|
386
386
|
}
|
|
387
387
|
var traceId = requestId();
|
|
@@ -391,19 +391,19 @@ function wrapToolWithMiddleware(tool, config) {
|
|
|
391
391
|
var result;
|
|
392
392
|
try {
|
|
393
393
|
if (useCircuitBreaker) {
|
|
394
|
-
var cb = getCircuitBreaker(
|
|
394
|
+
var cb = getCircuitBreaker(tool2.name);
|
|
395
395
|
try {
|
|
396
396
|
result = await cb.execute(function() {
|
|
397
|
-
return
|
|
397
|
+
return tool2.execute(toolCallId, params);
|
|
398
398
|
});
|
|
399
399
|
} catch (err) {
|
|
400
400
|
if (err instanceof CircuitOpenError) {
|
|
401
|
-
return errorResult("Circuit breaker open for " +
|
|
401
|
+
return errorResult("Circuit breaker open for " + tool2.name + ". Service temporarily unavailable.");
|
|
402
402
|
}
|
|
403
403
|
throw err;
|
|
404
404
|
}
|
|
405
405
|
} else {
|
|
406
|
-
result = await
|
|
406
|
+
result = await tool2.execute(toolCallId, params);
|
|
407
407
|
}
|
|
408
408
|
} catch (err) {
|
|
409
409
|
success = false;
|
|
@@ -420,7 +420,7 @@ function wrapToolWithMiddleware(tool, config) {
|
|
|
420
420
|
);
|
|
421
421
|
auditSink.log({
|
|
422
422
|
traceId,
|
|
423
|
-
toolName:
|
|
423
|
+
toolName: tool2.name,
|
|
424
424
|
toolCallId,
|
|
425
425
|
agentId,
|
|
426
426
|
timestamp: new Date(startTime).toISOString(),
|
|
@@ -433,7 +433,7 @@ function wrapToolWithMiddleware(tool, config) {
|
|
|
433
433
|
}
|
|
434
434
|
if (telemetryEnabled && telemetrySink) {
|
|
435
435
|
telemetrySink.record({
|
|
436
|
-
toolName:
|
|
436
|
+
toolName: tool2.name,
|
|
437
437
|
agentId,
|
|
438
438
|
durationMs,
|
|
439
439
|
success,
|
|
@@ -445,14 +445,14 @@ function wrapToolWithMiddleware(tool, config) {
|
|
|
445
445
|
})();
|
|
446
446
|
};
|
|
447
447
|
return {
|
|
448
|
-
name:
|
|
449
|
-
label:
|
|
450
|
-
description:
|
|
451
|
-
parameters:
|
|
448
|
+
name: tool2.name,
|
|
449
|
+
label: tool2.label,
|
|
450
|
+
description: tool2.description,
|
|
451
|
+
parameters: tool2.parameters,
|
|
452
452
|
execute: wrappedExecute,
|
|
453
|
-
ownerOnly:
|
|
454
|
-
category:
|
|
455
|
-
risk:
|
|
453
|
+
ownerOnly: tool2.ownerOnly,
|
|
454
|
+
category: tool2.category,
|
|
455
|
+
risk: tool2.risk
|
|
456
456
|
};
|
|
457
457
|
}
|
|
458
458
|
function createToolMiddleware(config) {
|
|
@@ -492,17 +492,17 @@ function createToolMiddleware(config) {
|
|
|
492
492
|
}
|
|
493
493
|
return limiter;
|
|
494
494
|
}
|
|
495
|
-
function wrap(
|
|
496
|
-
var useCircuitBreaker = cbEnabled && (
|
|
497
|
-
var rlOpts = resolveRateLimiterOpts(
|
|
495
|
+
function wrap(tool2) {
|
|
496
|
+
var useCircuitBreaker = cbEnabled && (tool2.category === "web" || tool2.category === "browser");
|
|
497
|
+
var rlOpts = resolveRateLimiterOpts(tool2, config.rateLimit?.overrides);
|
|
498
498
|
var wrappedExecute = function(toolCallId, params) {
|
|
499
499
|
return (async function() {
|
|
500
500
|
if (rateLimitEnabled) {
|
|
501
501
|
var limiter = getCachedRateLimiter(rlOpts);
|
|
502
|
-
var rlKey = agentId + ":" +
|
|
502
|
+
var rlKey = agentId + ":" + tool2.name;
|
|
503
503
|
if (!limiter.tryConsume(rlKey)) {
|
|
504
504
|
var retryAfterMs = limiter.getRetryAfterMs(rlKey);
|
|
505
|
-
return errorResult("Rate limited: " +
|
|
505
|
+
return errorResult("Rate limited: " + tool2.name + ". Retry after " + retryAfterMs + "ms.");
|
|
506
506
|
}
|
|
507
507
|
}
|
|
508
508
|
var traceId = requestId();
|
|
@@ -512,19 +512,19 @@ function createToolMiddleware(config) {
|
|
|
512
512
|
var result;
|
|
513
513
|
try {
|
|
514
514
|
if (useCircuitBreaker) {
|
|
515
|
-
var cb = getLocalCircuitBreaker(
|
|
515
|
+
var cb = getLocalCircuitBreaker(tool2.name);
|
|
516
516
|
try {
|
|
517
517
|
result = await cb.execute(function() {
|
|
518
|
-
return
|
|
518
|
+
return tool2.execute(toolCallId, params);
|
|
519
519
|
});
|
|
520
520
|
} catch (err) {
|
|
521
521
|
if (err instanceof CircuitOpenError) {
|
|
522
|
-
return errorResult("Circuit breaker open for " +
|
|
522
|
+
return errorResult("Circuit breaker open for " + tool2.name + ". Service temporarily unavailable.");
|
|
523
523
|
}
|
|
524
524
|
throw err;
|
|
525
525
|
}
|
|
526
526
|
} else {
|
|
527
|
-
result = await
|
|
527
|
+
result = await tool2.execute(toolCallId, params);
|
|
528
528
|
}
|
|
529
529
|
} catch (err) {
|
|
530
530
|
success = false;
|
|
@@ -541,7 +541,7 @@ function createToolMiddleware(config) {
|
|
|
541
541
|
);
|
|
542
542
|
auditSink.log({
|
|
543
543
|
traceId,
|
|
544
|
-
toolName:
|
|
544
|
+
toolName: tool2.name,
|
|
545
545
|
toolCallId,
|
|
546
546
|
agentId,
|
|
547
547
|
timestamp: new Date(startTime).toISOString(),
|
|
@@ -554,7 +554,7 @@ function createToolMiddleware(config) {
|
|
|
554
554
|
}
|
|
555
555
|
if (telemetryEnabled && telemetrySink) {
|
|
556
556
|
telemetrySink.record({
|
|
557
|
-
toolName:
|
|
557
|
+
toolName: tool2.name,
|
|
558
558
|
agentId,
|
|
559
559
|
durationMs,
|
|
560
560
|
success,
|
|
@@ -566,14 +566,14 @@ function createToolMiddleware(config) {
|
|
|
566
566
|
})();
|
|
567
567
|
};
|
|
568
568
|
return {
|
|
569
|
-
name:
|
|
570
|
-
label:
|
|
571
|
-
description:
|
|
572
|
-
parameters:
|
|
569
|
+
name: tool2.name,
|
|
570
|
+
label: tool2.label,
|
|
571
|
+
description: tool2.description,
|
|
572
|
+
parameters: tool2.parameters,
|
|
573
573
|
execute: wrappedExecute,
|
|
574
|
-
ownerOnly:
|
|
575
|
-
category:
|
|
576
|
-
risk:
|
|
574
|
+
ownerOnly: tool2.ownerOnly,
|
|
575
|
+
category: tool2.category,
|
|
576
|
+
risk: tool2.risk
|
|
577
577
|
};
|
|
578
578
|
}
|
|
579
579
|
function destroy() {
|
|
@@ -12336,6 +12336,541 @@ function createDiffTools(options) {
|
|
|
12336
12336
|
return [entDiffText, entDiffJson, entDiffSpreadsheet, entDiffSummary];
|
|
12337
12337
|
}
|
|
12338
12338
|
|
|
12339
|
+
// src/agent-tools/tools/remotion-video.ts
|
|
12340
|
+
import { execSync } from "child_process";
|
|
12341
|
+
import { existsSync, mkdirSync, writeFileSync, copyFileSync, readdirSync } from "fs";
|
|
12342
|
+
import { join, basename as basename2 } from "path";
|
|
12343
|
+
function ensureDir(dir) {
|
|
12344
|
+
if (!existsSync(dir)) mkdirSync(dir, { recursive: true });
|
|
12345
|
+
}
|
|
12346
|
+
function runInProject(projectDir, cmd, timeout = 12e4) {
|
|
12347
|
+
return execSync(cmd, { cwd: projectDir, encoding: "utf-8", timeout, stdio: "pipe" }).trim();
|
|
12348
|
+
}
|
|
12349
|
+
function isRemotonInstalled(projectDir) {
|
|
12350
|
+
return existsSync(join(projectDir, "node_modules", "remotion"));
|
|
12351
|
+
}
|
|
12352
|
+
var ROOT_INDEX_TSX = `import { registerRoot } from "remotion";
|
|
12353
|
+
import { RemotionRoot } from "./Root";
|
|
12354
|
+
registerRoot(RemotionRoot);
|
|
12355
|
+
`;
|
|
12356
|
+
var ROOT_TSX_TEMPLATE = (compositions) => `import { Composition } from "remotion";
|
|
12357
|
+
${compositions.map((c) => `import { ${pascalCase(c)} } from "./compositions/${c}";`).join("\n")}
|
|
12358
|
+
|
|
12359
|
+
export const RemotionRoot: React.FC = () => {
|
|
12360
|
+
return (
|
|
12361
|
+
<>
|
|
12362
|
+
${compositions.map((c) => ` {/* @ts-ignore */}
|
|
12363
|
+
<Composition id="${c}" component={${pascalCase(c)}} durationInFrames={450} fps={30} width={1080} height={1920} />`).join("\n")}
|
|
12364
|
+
</>
|
|
12365
|
+
);
|
|
12366
|
+
};
|
|
12367
|
+
`;
|
|
12368
|
+
function pascalCase(s) {
|
|
12369
|
+
return s.replace(/(^|[-_])(\w)/g, (_, __, c) => c.toUpperCase());
|
|
12370
|
+
}
|
|
12371
|
+
var BLANK_COMPOSITION = (id) => `import { AbsoluteFill, useCurrentFrame, interpolate } from "remotion";
|
|
12372
|
+
|
|
12373
|
+
export const ${pascalCase(id)}: React.FC<{ title?: string }> = ({ title = "Hello World" }) => {
|
|
12374
|
+
const frame = useCurrentFrame();
|
|
12375
|
+
const opacity = interpolate(frame, [0, 30], [0, 1], { extrapolateRight: "clamp" });
|
|
12376
|
+
|
|
12377
|
+
return (
|
|
12378
|
+
<AbsoluteFill style={{ backgroundColor: "#0f0f0f", justifyContent: "center", alignItems: "center" }}>
|
|
12379
|
+
<h1 style={{ color: "white", fontSize: 80, fontWeight: "bold", opacity, textAlign: "center", padding: 40 }}>
|
|
12380
|
+
{title}
|
|
12381
|
+
</h1>
|
|
12382
|
+
</AbsoluteFill>
|
|
12383
|
+
);
|
|
12384
|
+
};
|
|
12385
|
+
`;
|
|
12386
|
+
var TEXT_ANIMATION = (id) => `import { AbsoluteFill, useCurrentFrame, interpolate, spring, useVideoConfig, Sequence } from "remotion";
|
|
12387
|
+
|
|
12388
|
+
const AnimatedText: React.FC<{ text: string; delay: number }> = ({ text, delay }) => {
|
|
12389
|
+
const frame = useCurrentFrame();
|
|
12390
|
+
const { fps } = useVideoConfig();
|
|
12391
|
+
const scale = spring({ frame: frame - delay, fps, config: { damping: 12 } });
|
|
12392
|
+
const opacity = interpolate(frame - delay, [0, 15], [0, 1], { extrapolateLeft: "clamp", extrapolateRight: "clamp" });
|
|
12393
|
+
|
|
12394
|
+
return (
|
|
12395
|
+
<div style={{ transform: \`scale(\${scale})\`, opacity, fontSize: 64, fontWeight: "bold", color: "white", textAlign: "center", padding: "0 40px" }}>
|
|
12396
|
+
{text}
|
|
12397
|
+
</div>
|
|
12398
|
+
);
|
|
12399
|
+
};
|
|
12400
|
+
|
|
12401
|
+
export const ${pascalCase(id)}: React.FC<{ lines?: string[] }> = ({ lines = ["Create", "Amazing", "Videos"] }) => {
|
|
12402
|
+
const frame = useCurrentFrame();
|
|
12403
|
+
|
|
12404
|
+
return (
|
|
12405
|
+
<AbsoluteFill style={{ backgroundColor: "#1a1a2e", justifyContent: "center", alignItems: "center", gap: 20 }}>
|
|
12406
|
+
{lines.map((line, i) => (
|
|
12407
|
+
<Sequence key={i} from={i * 20}>
|
|
12408
|
+
<AnimatedText text={line} delay={0} />
|
|
12409
|
+
</Sequence>
|
|
12410
|
+
))}
|
|
12411
|
+
</AbsoluteFill>
|
|
12412
|
+
);
|
|
12413
|
+
};
|
|
12414
|
+
`;
|
|
12415
|
+
var SLIDESHOW = (id) => `import { AbsoluteFill, useCurrentFrame, interpolate, Img, Sequence, useVideoConfig, staticFile } from "remotion";
|
|
12416
|
+
|
|
12417
|
+
const Slide: React.FC<{ src: string; caption?: string }> = ({ src, caption }) => {
|
|
12418
|
+
const frame = useCurrentFrame();
|
|
12419
|
+
const opacity = interpolate(frame, [0, 15, 135, 150], [0, 1, 1, 0], { extrapolateLeft: "clamp", extrapolateRight: "clamp" });
|
|
12420
|
+
const scale = interpolate(frame, [0, 150], [1, 1.05]);
|
|
12421
|
+
|
|
12422
|
+
return (
|
|
12423
|
+
<AbsoluteFill style={{ opacity }}>
|
|
12424
|
+
<Img src={src} style={{ width: "100%", height: "100%", objectFit: "cover", transform: \`scale(\${scale})\` }} />
|
|
12425
|
+
{caption && (
|
|
12426
|
+
<div style={{ position: "absolute", bottom: 80, left: 0, right: 0, textAlign: "center", color: "white", fontSize: 48, fontWeight: "bold", textShadow: "0 2px 20px rgba(0,0,0,0.8)", padding: "0 40px" }}>
|
|
12427
|
+
{caption}
|
|
12428
|
+
</div>
|
|
12429
|
+
)}
|
|
12430
|
+
</AbsoluteFill>
|
|
12431
|
+
);
|
|
12432
|
+
};
|
|
12433
|
+
|
|
12434
|
+
export const ${pascalCase(id)}: React.FC<{ slides?: Array<{ src: string; caption?: string }> }> = ({ slides = [] }) => {
|
|
12435
|
+
const { fps } = useVideoConfig();
|
|
12436
|
+
const slideDuration = fps * 5; // 5 seconds per slide
|
|
12437
|
+
|
|
12438
|
+
return (
|
|
12439
|
+
<AbsoluteFill style={{ backgroundColor: "#000" }}>
|
|
12440
|
+
{slides.map((slide, i) => (
|
|
12441
|
+
<Sequence key={i} from={i * slideDuration} durationInFrames={slideDuration}>
|
|
12442
|
+
<Slide src={slide.src} caption={slide.caption} />
|
|
12443
|
+
</Sequence>
|
|
12444
|
+
))}
|
|
12445
|
+
</AbsoluteFill>
|
|
12446
|
+
);
|
|
12447
|
+
};
|
|
12448
|
+
`;
|
|
12449
|
+
var SOCIAL_REEL = (id) => `import { AbsoluteFill, useCurrentFrame, interpolate, spring, useVideoConfig, Sequence, Audio, staticFile } from "remotion";
|
|
12450
|
+
|
|
12451
|
+
const HookText: React.FC<{ text: string }> = ({ text }) => {
|
|
12452
|
+
const frame = useCurrentFrame();
|
|
12453
|
+
const { fps } = useVideoConfig();
|
|
12454
|
+
const y = spring({ frame, fps, config: { damping: 15 } });
|
|
12455
|
+
const translateY = interpolate(y, [0, 1], [100, 0]);
|
|
12456
|
+
|
|
12457
|
+
return (
|
|
12458
|
+
<div style={{ transform: \`translateY(\${translateY}px)\`, fontSize: 56, fontWeight: 900, color: "white", textAlign: "center", padding: "0 50px", lineHeight: 1.3, textShadow: "0 2px 10px rgba(0,0,0,0.5)" }}>
|
|
12459
|
+
{text}
|
|
12460
|
+
</div>
|
|
12461
|
+
);
|
|
12462
|
+
};
|
|
12463
|
+
|
|
12464
|
+
const BodyPoint: React.FC<{ text: string; emoji?: string }> = ({ text, emoji = "\u2728" }) => {
|
|
12465
|
+
const frame = useCurrentFrame();
|
|
12466
|
+
const { fps } = useVideoConfig();
|
|
12467
|
+
const progress = spring({ frame, fps, config: { damping: 12, stiffness: 100 } });
|
|
12468
|
+
const opacity = interpolate(progress, [0, 1], [0, 1]);
|
|
12469
|
+
const x = interpolate(progress, [0, 1], [-50, 0]);
|
|
12470
|
+
|
|
12471
|
+
return (
|
|
12472
|
+
<div style={{ opacity, transform: \`translateX(\${x}px)\`, fontSize: 36, color: "white", padding: "8px 50px", lineHeight: 1.5 }}>
|
|
12473
|
+
{emoji} {text}
|
|
12474
|
+
</div>
|
|
12475
|
+
);
|
|
12476
|
+
};
|
|
12477
|
+
|
|
12478
|
+
const CTA: React.FC<{ text: string; handle: string }> = ({ text, handle }) => {
|
|
12479
|
+
const frame = useCurrentFrame();
|
|
12480
|
+
const { fps } = useVideoConfig();
|
|
12481
|
+
const scale = spring({ frame, fps, config: { damping: 10, mass: 0.5 } });
|
|
12482
|
+
|
|
12483
|
+
return (
|
|
12484
|
+
<div style={{ textAlign: "center", transform: \`scale(\${scale})\` }}>
|
|
12485
|
+
<div style={{ fontSize: 40, fontWeight: 800, color: "#FFD700", marginBottom: 12 }}>{text}</div>
|
|
12486
|
+
<div style={{ fontSize: 32, color: "rgba(255,255,255,0.8)" }}>{handle}</div>
|
|
12487
|
+
</div>
|
|
12488
|
+
);
|
|
12489
|
+
};
|
|
12490
|
+
|
|
12491
|
+
export const ${pascalCase(id)}: React.FC<{
|
|
12492
|
+
hook?: string;
|
|
12493
|
+
points?: Array<{ text: string; emoji?: string }>;
|
|
12494
|
+
cta?: string;
|
|
12495
|
+
handle?: string;
|
|
12496
|
+
bgColor?: string;
|
|
12497
|
+
accentColor?: string;
|
|
12498
|
+
audioSrc?: string;
|
|
12499
|
+
}> = ({
|
|
12500
|
+
hook = "5 Signs You Need To Know",
|
|
12501
|
+
points = [
|
|
12502
|
+
{ text: "They always make time for you", emoji: "\u{1F495}" },
|
|
12503
|
+
{ text: "They remember the small things", emoji: "\u{1F90D}" },
|
|
12504
|
+
{ text: "They support your growth", emoji: "\u{1F331}" },
|
|
12505
|
+
],
|
|
12506
|
+
cta = "Follow for more",
|
|
12507
|
+
handle = "@yourpage",
|
|
12508
|
+
bgColor = "#1a1a2e",
|
|
12509
|
+
accentColor = "#e94560",
|
|
12510
|
+
audioSrc,
|
|
12511
|
+
}) => {
|
|
12512
|
+
const { fps } = useVideoConfig();
|
|
12513
|
+
|
|
12514
|
+
return (
|
|
12515
|
+
<AbsoluteFill style={{ background: \`linear-gradient(135deg, \${bgColor} 0%, \${accentColor}33 100%)\` }}>
|
|
12516
|
+
{audioSrc && <Audio src={staticFile(audioSrc)} volume={0.5} />}
|
|
12517
|
+
|
|
12518
|
+
{/* Hook */}
|
|
12519
|
+
<Sequence from={0} durationInFrames={fps * 3}>
|
|
12520
|
+
<AbsoluteFill style={{ justifyContent: "center", alignItems: "center" }}>
|
|
12521
|
+
<HookText text={hook} />
|
|
12522
|
+
<div style={{ position: "absolute", bottom: 120, fontSize: 28, color: "rgba(255,255,255,0.6)" }}>
|
|
12523
|
+
Check comments \u{1F447}
|
|
12524
|
+
</div>
|
|
12525
|
+
</AbsoluteFill>
|
|
12526
|
+
</Sequence>
|
|
12527
|
+
|
|
12528
|
+
{/* Points */}
|
|
12529
|
+
{points.map((point, i) => (
|
|
12530
|
+
<Sequence key={i} from={fps * 3 + i * fps * 2.5} durationInFrames={fps * 2.5}>
|
|
12531
|
+
<AbsoluteFill style={{ justifyContent: "center" }}>
|
|
12532
|
+
<BodyPoint text={point.text} emoji={point.emoji} />
|
|
12533
|
+
</AbsoluteFill>
|
|
12534
|
+
</Sequence>
|
|
12535
|
+
))}
|
|
12536
|
+
|
|
12537
|
+
{/* CTA */}
|
|
12538
|
+
<Sequence from={fps * 3 + points.length * fps * 2.5} durationInFrames={fps * 3}>
|
|
12539
|
+
<AbsoluteFill style={{ justifyContent: "center", alignItems: "center" }}>
|
|
12540
|
+
<CTA text={cta} handle={handle} />
|
|
12541
|
+
</AbsoluteFill>
|
|
12542
|
+
</Sequence>
|
|
12543
|
+
</AbsoluteFill>
|
|
12544
|
+
);
|
|
12545
|
+
};
|
|
12546
|
+
`;
|
|
12547
|
+
var TEMPLATES = {
|
|
12548
|
+
"blank": BLANK_COMPOSITION,
|
|
12549
|
+
"hello-world": BLANK_COMPOSITION,
|
|
12550
|
+
"text-animation": TEXT_ANIMATION,
|
|
12551
|
+
"slideshow": SLIDESHOW,
|
|
12552
|
+
"social-reel": SOCIAL_REEL
|
|
12553
|
+
};
|
|
12554
|
+
var PACKAGE_JSON = (name) => JSON.stringify({
|
|
12555
|
+
name: name || "remotion-project",
|
|
12556
|
+
version: "1.0.0",
|
|
12557
|
+
private: true,
|
|
12558
|
+
scripts: {
|
|
12559
|
+
start: "remotion studio",
|
|
12560
|
+
build: "remotion render",
|
|
12561
|
+
render: "remotion render"
|
|
12562
|
+
},
|
|
12563
|
+
dependencies: {
|
|
12564
|
+
"@remotion/cli": "^4",
|
|
12565
|
+
"@remotion/renderer": "^4",
|
|
12566
|
+
"remotion": "^4",
|
|
12567
|
+
"react": "^18",
|
|
12568
|
+
"react-dom": "^18"
|
|
12569
|
+
},
|
|
12570
|
+
devDependencies: {
|
|
12571
|
+
"@types/react": "^18",
|
|
12572
|
+
"typescript": "^5"
|
|
12573
|
+
}
|
|
12574
|
+
}, null, 2);
|
|
12575
|
+
var TSCONFIG = JSON.stringify({
|
|
12576
|
+
compilerOptions: {
|
|
12577
|
+
target: "ES2022",
|
|
12578
|
+
module: "ES2022",
|
|
12579
|
+
moduleResolution: "bundler",
|
|
12580
|
+
jsx: "react-jsx",
|
|
12581
|
+
strict: true,
|
|
12582
|
+
skipLibCheck: true,
|
|
12583
|
+
esModuleInterop: true,
|
|
12584
|
+
outDir: "./dist"
|
|
12585
|
+
},
|
|
12586
|
+
include: ["src/**/*"]
|
|
12587
|
+
}, null, 2);
|
|
12588
|
+
var createProject = async (_id, params) => {
|
|
12589
|
+
const { projectDir, name, template = "blank" } = params;
|
|
12590
|
+
if (!projectDir) return { error: "projectDir is required" };
|
|
12591
|
+
ensureDir(projectDir);
|
|
12592
|
+
ensureDir(join(projectDir, "src", "compositions"));
|
|
12593
|
+
ensureDir(join(projectDir, "public"));
|
|
12594
|
+
writeFileSync(join(projectDir, "package.json"), PACKAGE_JSON(name || basename2(projectDir)));
|
|
12595
|
+
writeFileSync(join(projectDir, "tsconfig.json"), TSCONFIG);
|
|
12596
|
+
writeFileSync(join(projectDir, "src", "index.ts"), ROOT_INDEX_TSX);
|
|
12597
|
+
const compId = "main";
|
|
12598
|
+
const templateFn = TEMPLATES[template] || TEMPLATES["blank"];
|
|
12599
|
+
writeFileSync(join(projectDir, "src", "compositions", `${compId}.tsx`), templateFn(compId));
|
|
12600
|
+
writeFileSync(join(projectDir, "src", "Root.tsx"), ROOT_TSX_TEMPLATE([compId]));
|
|
12601
|
+
try {
|
|
12602
|
+
runInProject(projectDir, "npm install --no-audit --no-fund 2>&1", 18e4);
|
|
12603
|
+
} catch (e) {
|
|
12604
|
+
return {
|
|
12605
|
+
success: true,
|
|
12606
|
+
projectDir,
|
|
12607
|
+
warning: `Project created but npm install failed: ${e.message?.substring(0, 200)}. Run \`cd ${projectDir} && npm install\` manually.`,
|
|
12608
|
+
files: ["package.json", "tsconfig.json", "src/index.ts", "src/Root.tsx", `src/compositions/${compId}.tsx`]
|
|
12609
|
+
};
|
|
12610
|
+
}
|
|
12611
|
+
return {
|
|
12612
|
+
success: true,
|
|
12613
|
+
projectDir,
|
|
12614
|
+
template,
|
|
12615
|
+
compositionId: compId,
|
|
12616
|
+
files: ["package.json", "tsconfig.json", "src/index.ts", "src/Root.tsx", `src/compositions/${compId}.tsx`],
|
|
12617
|
+
nextSteps: [
|
|
12618
|
+
`Edit the composition: remotion_create_composition with your content`,
|
|
12619
|
+
`Preview: remotion_preview_url to start the studio`,
|
|
12620
|
+
`Render: remotion_render to create the video file`
|
|
12621
|
+
]
|
|
12622
|
+
};
|
|
12623
|
+
};
|
|
12624
|
+
var createComposition = async (_id, params) => {
|
|
12625
|
+
const { projectDir, compositionId, code, width = 1080, height = 1920, fps = 30, durationInSeconds = 15 } = params;
|
|
12626
|
+
if (!projectDir || !compositionId || !code) return { error: "projectDir, compositionId, and code are required" };
|
|
12627
|
+
if (!existsSync(projectDir)) return { error: `Project directory not found: ${projectDir}` };
|
|
12628
|
+
const compDir = join(projectDir, "src", "compositions");
|
|
12629
|
+
ensureDir(compDir);
|
|
12630
|
+
const filePath = join(compDir, `${compositionId}.tsx`);
|
|
12631
|
+
writeFileSync(filePath, code);
|
|
12632
|
+
const compositions = readdirSync(compDir).filter((f) => f.endsWith(".tsx")).map((f) => f.replace(".tsx", ""));
|
|
12633
|
+
const rootContent = `import { Composition } from "remotion";
|
|
12634
|
+
${compositions.map((c) => `import { ${pascalCase(c)} } from "./compositions/${c}";`).join("\n")}
|
|
12635
|
+
|
|
12636
|
+
export const RemotionRoot: React.FC = () => {
|
|
12637
|
+
return (
|
|
12638
|
+
<>
|
|
12639
|
+
${compositions.map((c) => {
|
|
12640
|
+
const isTarget = c === compositionId;
|
|
12641
|
+
const w = isTarget ? width : 1080;
|
|
12642
|
+
const h = isTarget ? height : 1920;
|
|
12643
|
+
const f = isTarget ? fps : 30;
|
|
12644
|
+
const dur = isTarget ? durationInSeconds * fps : 450;
|
|
12645
|
+
return ` <Composition id="${c}" component={${pascalCase(c)}} durationInFrames={${dur}} fps={${f}} width={${w}} height={${h}} />`;
|
|
12646
|
+
}).join("\n")}
|
|
12647
|
+
</>
|
|
12648
|
+
);
|
|
12649
|
+
};
|
|
12650
|
+
`;
|
|
12651
|
+
writeFileSync(join(projectDir, "src", "Root.tsx"), rootContent);
|
|
12652
|
+
return {
|
|
12653
|
+
success: true,
|
|
12654
|
+
compositionId,
|
|
12655
|
+
filePath: `src/compositions/${compositionId}.tsx`,
|
|
12656
|
+
dimensions: `${width}x${height}`,
|
|
12657
|
+
fps,
|
|
12658
|
+
duration: `${durationInSeconds}s (${durationInSeconds * fps} frames)`
|
|
12659
|
+
};
|
|
12660
|
+
};
|
|
12661
|
+
var renderVideo = async (_id, params) => {
|
|
12662
|
+
const { projectDir, compositionId, outputPath, codec = "h264", quality, inputProps, concurrency, scale } = params;
|
|
12663
|
+
if (!projectDir || !compositionId || !outputPath) return { error: "projectDir, compositionId, and outputPath are required" };
|
|
12664
|
+
if (!existsSync(projectDir)) return { error: `Project directory not found: ${projectDir}` };
|
|
12665
|
+
if (!isRemotonInstalled(projectDir)) return { error: "Remotion not installed. Run remotion_create_project first or npm install in the project." };
|
|
12666
|
+
const outDir = join(outputPath, "..");
|
|
12667
|
+
ensureDir(outDir);
|
|
12668
|
+
let cmd = `npx remotion render ${compositionId} "${outputPath}" --codec ${codec}`;
|
|
12669
|
+
if (quality !== void 0) cmd += ` --crf ${quality}`;
|
|
12670
|
+
if (concurrency) cmd += ` --concurrency ${concurrency}`;
|
|
12671
|
+
if (scale && scale !== 1) cmd += ` --scale ${scale}`;
|
|
12672
|
+
if (inputProps) {
|
|
12673
|
+
const propsFile = join(projectDir, ".remotion-props.json");
|
|
12674
|
+
writeFileSync(propsFile, JSON.stringify(inputProps));
|
|
12675
|
+
cmd += ` --props "${propsFile}"`;
|
|
12676
|
+
}
|
|
12677
|
+
try {
|
|
12678
|
+
const output = runInProject(projectDir, cmd, 6e5);
|
|
12679
|
+
return {
|
|
12680
|
+
success: true,
|
|
12681
|
+
outputPath,
|
|
12682
|
+
compositionId,
|
|
12683
|
+
codec,
|
|
12684
|
+
message: "Video rendered successfully",
|
|
12685
|
+
output: output.substring(output.length - 500)
|
|
12686
|
+
// last 500 chars of output
|
|
12687
|
+
};
|
|
12688
|
+
} catch (e) {
|
|
12689
|
+
return {
|
|
12690
|
+
error: `Render failed: ${e.message?.substring(0, 500)}`,
|
|
12691
|
+
stderr: e.stderr?.substring(0, 500)
|
|
12692
|
+
};
|
|
12693
|
+
}
|
|
12694
|
+
};
|
|
12695
|
+
var renderStill = async (_id, params) => {
|
|
12696
|
+
const { projectDir, compositionId, outputPath, frame = 0, inputProps, format = "png", scale } = params;
|
|
12697
|
+
if (!projectDir || !compositionId || !outputPath) return { error: "projectDir, compositionId, and outputPath are required" };
|
|
12698
|
+
if (!existsSync(projectDir)) return { error: `Project directory not found: ${projectDir}` };
|
|
12699
|
+
if (!isRemotonInstalled(projectDir)) return { error: "Remotion not installed." };
|
|
12700
|
+
ensureDir(join(outputPath, ".."));
|
|
12701
|
+
let cmd = `npx remotion still ${compositionId} "${outputPath}" --frame ${frame} --image-format ${format}`;
|
|
12702
|
+
if (scale && scale !== 1) cmd += ` --scale ${scale}`;
|
|
12703
|
+
if (inputProps) {
|
|
12704
|
+
const propsFile = join(projectDir, ".remotion-props.json");
|
|
12705
|
+
writeFileSync(propsFile, JSON.stringify(inputProps));
|
|
12706
|
+
cmd += ` --props "${propsFile}"`;
|
|
12707
|
+
}
|
|
12708
|
+
try {
|
|
12709
|
+
runInProject(projectDir, cmd, 12e4);
|
|
12710
|
+
return { success: true, outputPath, compositionId, frame, format };
|
|
12711
|
+
} catch (e) {
|
|
12712
|
+
return { error: `Still render failed: ${e.message?.substring(0, 500)}` };
|
|
12713
|
+
}
|
|
12714
|
+
};
|
|
12715
|
+
var listCompositions = async (_id, params) => {
|
|
12716
|
+
const { projectDir } = params;
|
|
12717
|
+
if (!projectDir) return { error: "projectDir is required" };
|
|
12718
|
+
if (!existsSync(projectDir)) return { error: `Project directory not found: ${projectDir}` };
|
|
12719
|
+
const compDir = join(projectDir, "src", "compositions");
|
|
12720
|
+
if (!existsSync(compDir)) return { compositions: [] };
|
|
12721
|
+
const files = readdirSync(compDir).filter((f) => f.endsWith(".tsx") || f.endsWith(".jsx"));
|
|
12722
|
+
const compositions = files.map((f) => ({
|
|
12723
|
+
id: f.replace(/\.(tsx|jsx)$/, ""),
|
|
12724
|
+
file: `src/compositions/${f}`
|
|
12725
|
+
}));
|
|
12726
|
+
return { compositions, projectDir };
|
|
12727
|
+
};
|
|
12728
|
+
var startPreview = async (_id, params) => {
|
|
12729
|
+
const { projectDir, port = 3333 } = params;
|
|
12730
|
+
if (!projectDir) return { error: "projectDir is required" };
|
|
12731
|
+
if (!existsSync(projectDir)) return { error: `Project directory not found: ${projectDir}` };
|
|
12732
|
+
if (!isRemotonInstalled(projectDir)) return { error: "Remotion not installed." };
|
|
12733
|
+
try {
|
|
12734
|
+
execSync(`cd "${projectDir}" && npx remotion studio --port ${port} &`, {
|
|
12735
|
+
stdio: "ignore",
|
|
12736
|
+
timeout: 5e3
|
|
12737
|
+
});
|
|
12738
|
+
} catch {
|
|
12739
|
+
}
|
|
12740
|
+
return {
|
|
12741
|
+
success: true,
|
|
12742
|
+
url: `http://localhost:${port}`,
|
|
12743
|
+
message: `Remotion Studio starting on port ${port}. Open the URL in a browser to preview compositions.`
|
|
12744
|
+
};
|
|
12745
|
+
};
|
|
12746
|
+
var addAsset = async (_id, params) => {
|
|
12747
|
+
const { projectDir, source, filename } = params;
|
|
12748
|
+
if (!projectDir || !source || !filename) return { error: "projectDir, source, and filename are required" };
|
|
12749
|
+
const publicDir = join(projectDir, "public");
|
|
12750
|
+
ensureDir(publicDir);
|
|
12751
|
+
const destPath = join(publicDir, filename);
|
|
12752
|
+
if (source.startsWith("http://") || source.startsWith("https://")) {
|
|
12753
|
+
try {
|
|
12754
|
+
execSync(`curl -sL -o "${destPath}" "${source}"`, { timeout: 6e4 });
|
|
12755
|
+
} catch (e) {
|
|
12756
|
+
return { error: `Failed to download asset: ${e.message?.substring(0, 200)}` };
|
|
12757
|
+
}
|
|
12758
|
+
} else if (existsSync(source)) {
|
|
12759
|
+
copyFileSync(source, destPath);
|
|
12760
|
+
} else {
|
|
12761
|
+
return { error: `Source not found: ${source}` };
|
|
12762
|
+
}
|
|
12763
|
+
return {
|
|
12764
|
+
success: true,
|
|
12765
|
+
path: `public/${filename}`,
|
|
12766
|
+
usage: `In your composition, use: staticFile("${filename}")`
|
|
12767
|
+
};
|
|
12768
|
+
};
|
|
12769
|
+
var installPackage = async (_id, params) => {
|
|
12770
|
+
const { projectDir, packages } = params;
|
|
12771
|
+
if (!projectDir || !packages?.length) return { error: "projectDir and packages are required" };
|
|
12772
|
+
if (!existsSync(projectDir)) return { error: `Project directory not found: ${projectDir}` };
|
|
12773
|
+
const safePackages = packages.filter((p) => /^[@a-z0-9][\w./-]*$/.test(p));
|
|
12774
|
+
if (safePackages.length === 0) return { error: "No valid package names provided" };
|
|
12775
|
+
try {
|
|
12776
|
+
const output = runInProject(projectDir, `npm install ${safePackages.join(" ")} --no-audit --no-fund 2>&1`, 12e4);
|
|
12777
|
+
return { success: true, installed: safePackages, output: output.substring(output.length - 300) };
|
|
12778
|
+
} catch (e) {
|
|
12779
|
+
return { error: `Install failed: ${e.message?.substring(0, 300)}` };
|
|
12780
|
+
}
|
|
12781
|
+
};
|
|
12782
|
+
function tool(name, label, description, params, executor) {
|
|
12783
|
+
return {
|
|
12784
|
+
name,
|
|
12785
|
+
label,
|
|
12786
|
+
description,
|
|
12787
|
+
category: "media",
|
|
12788
|
+
risk: "medium",
|
|
12789
|
+
parameters: params,
|
|
12790
|
+
execute: async (_id, args) => executor(_id, args)
|
|
12791
|
+
};
|
|
12792
|
+
}
|
|
12793
|
+
function createRemotonTools() {
|
|
12794
|
+
return [
|
|
12795
|
+
tool("remotion_create_project", "Create Video Project", "Initialize a new Remotion video project with templates (blank, text-animation, slideshow, social-reel).", {
|
|
12796
|
+
type: "object",
|
|
12797
|
+
properties: {
|
|
12798
|
+
projectDir: { type: "string", description: "Directory for the project" },
|
|
12799
|
+
name: { type: "string", description: "Project name" },
|
|
12800
|
+
template: { type: "string", enum: ["blank", "hello-world", "text-animation", "slideshow", "social-reel"], description: "Starter template" }
|
|
12801
|
+
},
|
|
12802
|
+
required: ["projectDir"]
|
|
12803
|
+
}, createProject),
|
|
12804
|
+
tool("remotion_create_composition", "Create Video Composition", "Create or update a Remotion composition (React component) that defines video content. Use React + Remotion APIs: useCurrentFrame(), interpolate(), spring(), Sequence, AbsoluteFill.", {
|
|
12805
|
+
type: "object",
|
|
12806
|
+
properties: {
|
|
12807
|
+
projectDir: { type: "string", description: "Project directory" },
|
|
12808
|
+
compositionId: { type: "string", description: "Unique composition ID" },
|
|
12809
|
+
code: { type: "string", description: "Full React/TSX component code" },
|
|
12810
|
+
width: { type: "number", default: 1080 },
|
|
12811
|
+
height: { type: "number", default: 1920 },
|
|
12812
|
+
fps: { type: "number", default: 30 },
|
|
12813
|
+
durationInSeconds: { type: "number", default: 15 }
|
|
12814
|
+
},
|
|
12815
|
+
required: ["projectDir", "compositionId", "code"]
|
|
12816
|
+
}, createComposition),
|
|
12817
|
+
tool("remotion_render", "Render Video", "Render a composition to MP4/WebM/GIF. Requires ffmpeg.", {
|
|
12818
|
+
type: "object",
|
|
12819
|
+
properties: {
|
|
12820
|
+
projectDir: { type: "string" },
|
|
12821
|
+
compositionId: { type: "string" },
|
|
12822
|
+
outputPath: { type: "string" },
|
|
12823
|
+
codec: { type: "string", enum: ["h264", "h265", "vp8", "vp9", "gif", "prores"], default: "h264" },
|
|
12824
|
+
quality: { type: "number" },
|
|
12825
|
+
inputProps: { type: "object" },
|
|
12826
|
+
concurrency: { type: "number" },
|
|
12827
|
+
scale: { type: "number" }
|
|
12828
|
+
},
|
|
12829
|
+
required: ["projectDir", "compositionId", "outputPath"]
|
|
12830
|
+
}, renderVideo),
|
|
12831
|
+
tool("remotion_render_still", "Render Still Image", "Render a single frame as PNG/JPEG for thumbnails or previews.", {
|
|
12832
|
+
type: "object",
|
|
12833
|
+
properties: {
|
|
12834
|
+
projectDir: { type: "string" },
|
|
12835
|
+
compositionId: { type: "string" },
|
|
12836
|
+
outputPath: { type: "string" },
|
|
12837
|
+
frame: { type: "number", default: 0 },
|
|
12838
|
+
inputProps: { type: "object" },
|
|
12839
|
+
format: { type: "string", enum: ["png", "jpeg", "webp"], default: "png" },
|
|
12840
|
+
scale: { type: "number" }
|
|
12841
|
+
},
|
|
12842
|
+
required: ["projectDir", "compositionId", "outputPath"]
|
|
12843
|
+
}, renderStill),
|
|
12844
|
+
tool("remotion_list_compositions", "List Compositions", "List all compositions in a Remotion project.", {
|
|
12845
|
+
type: "object",
|
|
12846
|
+
properties: { projectDir: { type: "string" } },
|
|
12847
|
+
required: ["projectDir"]
|
|
12848
|
+
}, listCompositions),
|
|
12849
|
+
tool("remotion_preview_url", "Start Preview Server", "Start Remotion Studio to preview compositions in browser.", {
|
|
12850
|
+
type: "object",
|
|
12851
|
+
properties: { projectDir: { type: "string" }, port: { type: "number", default: 3333 } },
|
|
12852
|
+
required: ["projectDir"]
|
|
12853
|
+
}, startPreview),
|
|
12854
|
+
tool("remotion_add_asset", "Add Asset", "Add image/audio/video/font asset to project public/ directory from URL or local path.", {
|
|
12855
|
+
type: "object",
|
|
12856
|
+
properties: {
|
|
12857
|
+
projectDir: { type: "string" },
|
|
12858
|
+
source: { type: "string", description: "URL or local path" },
|
|
12859
|
+
filename: { type: "string", description: "Filename in public/" }
|
|
12860
|
+
},
|
|
12861
|
+
required: ["projectDir", "source", "filename"]
|
|
12862
|
+
}, addAsset),
|
|
12863
|
+
tool("remotion_install_package", "Install Remotion Package", "Install additional packages: @remotion/transitions, @remotion/motion-blur, @remotion/shapes, @remotion/lottie, @remotion/three, etc.", {
|
|
12864
|
+
type: "object",
|
|
12865
|
+
properties: {
|
|
12866
|
+
projectDir: { type: "string" },
|
|
12867
|
+
packages: { type: "array", items: { type: "string" } }
|
|
12868
|
+
},
|
|
12869
|
+
required: ["projectDir", "packages"]
|
|
12870
|
+
}, installPackage)
|
|
12871
|
+
];
|
|
12872
|
+
}
|
|
12873
|
+
|
|
12339
12874
|
// src/agent-tools/index.ts
|
|
12340
12875
|
init_whatsapp();
|
|
12341
12876
|
init_telegram();
|
|
@@ -13692,6 +14227,7 @@ async function createAllTools(options) {
|
|
|
13692
14227
|
...createSecurityScanTools(options),
|
|
13693
14228
|
...createCodeSandboxTools(options),
|
|
13694
14229
|
...createDiffTools(options),
|
|
14230
|
+
...createRemotonTools(),
|
|
13695
14231
|
...createKnowledgeSearchTools(options || {})
|
|
13696
14232
|
];
|
|
13697
14233
|
var agenticmailTools = [];
|
|
@@ -13936,8 +14472,8 @@ async function createAllTools(options) {
|
|
|
13936
14472
|
circuitBreaker: options.middleware.circuitBreaker,
|
|
13937
14473
|
telemetry: options.middleware.telemetry
|
|
13938
14474
|
});
|
|
13939
|
-
enabledTools = enabledTools.map(function(
|
|
13940
|
-
return mw.wrap(
|
|
14475
|
+
enabledTools = enabledTools.map(function(tool2) {
|
|
14476
|
+
return mw.wrap(tool2);
|
|
13941
14477
|
});
|
|
13942
14478
|
}
|
|
13943
14479
|
return enabledTools;
|
|
@@ -13974,6 +14510,7 @@ export {
|
|
|
13974
14510
|
createMemoryTools,
|
|
13975
14511
|
createPathSandbox,
|
|
13976
14512
|
createReadTool,
|
|
14513
|
+
createRemotonTools,
|
|
13977
14514
|
createSecurityScanTools,
|
|
13978
14515
|
createSpreadsheetTools,
|
|
13979
14516
|
createSsrfGuard,
|