makefx 0.1.1 → 0.1.2
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 +1 -1
- package/makefx.mjs +202 -160
- package/package.json +2 -2
package/README.md
CHANGED
package/makefx.mjs
CHANGED
|
@@ -808,65 +808,91 @@ function validateProjectConfig(config, configPath) {
|
|
|
808
808
|
* makefx spaces --id <space_id> Show details for a specific space
|
|
809
809
|
* makefx spaces create <name> Create a new space
|
|
810
810
|
*/
|
|
811
|
+
var defaultDeps$9 = {
|
|
812
|
+
loadConfig: loadStoredConfig,
|
|
813
|
+
resolveBaseUrl,
|
|
814
|
+
saveProjectConfig,
|
|
815
|
+
fetch,
|
|
816
|
+
print: console.log
|
|
817
|
+
};
|
|
811
818
|
async function handleSpaces(parsed) {
|
|
819
|
+
try {
|
|
820
|
+
await executeSpaces(parsed);
|
|
821
|
+
} catch (error) {
|
|
822
|
+
console.error("Error:", error instanceof Error ? error.message : error);
|
|
823
|
+
process$1.exitCode = 1;
|
|
824
|
+
}
|
|
825
|
+
}
|
|
826
|
+
async function executeSpaces(parsed, deps = defaultDeps$9) {
|
|
812
827
|
const env = resolveCommandEnvironment(parsed);
|
|
813
828
|
const showDetails = parsed.options.details === "true";
|
|
814
829
|
const spaceId = parsed.options.id;
|
|
815
830
|
const subcommand = parsed.positionals[0];
|
|
816
831
|
const jsonOutput = parsed.options.json === "true";
|
|
817
|
-
const config = await
|
|
818
|
-
if (!config) {
|
|
819
|
-
|
|
820
|
-
console.error(`Run: ${loginCommandForEnvironment(env)}`);
|
|
821
|
-
process$1.exitCode = 1;
|
|
822
|
-
return;
|
|
823
|
-
}
|
|
824
|
-
if (config.token.expiresAt < Date.now()) {
|
|
825
|
-
console.error(`Token expired for ${env} environment.`);
|
|
826
|
-
console.error(`Run: ${loginCommandForEnvironment(env)}`);
|
|
827
|
-
process$1.exitCode = 1;
|
|
828
|
-
return;
|
|
829
|
-
}
|
|
830
|
-
const baseUrl = resolveBaseUrl(env);
|
|
831
|
-
const accessToken = config.token.accessToken;
|
|
832
|
+
const config = await deps.loadConfig(env);
|
|
833
|
+
if (!config) throw new Error(`Not logged in to ${env} environment. Run: ${loginCommandForEnvironment(env)}`);
|
|
834
|
+
if (config.token.expiresAt < Date.now()) throw new Error(`Token expired for ${env} environment. Run: ${loginCommandForEnvironment(env)}`);
|
|
832
835
|
if (env === "local") process$1.env.NODE_TLS_REJECT_UNAUTHORIZED = "0";
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
|
|
844
|
-
const project = parsed.options.init === "true" ? {
|
|
845
|
-
configPath: await saveProjectConfig({
|
|
846
|
-
environment: env,
|
|
847
|
-
spaceId: space.id
|
|
848
|
-
}),
|
|
836
|
+
const ctx = {
|
|
837
|
+
env,
|
|
838
|
+
baseUrl: deps.resolveBaseUrl(env),
|
|
839
|
+
accessToken: config.token.accessToken
|
|
840
|
+
};
|
|
841
|
+
if (subcommand === "create") {
|
|
842
|
+
const spaceName = parsed.positionals.slice(1).join(" ") || parsed.options.name;
|
|
843
|
+
if (!spaceName) throw new Error("Space name is required. Usage: makefx spaces create <name>");
|
|
844
|
+
const space = await createSpace(ctx, deps, spaceName);
|
|
845
|
+
const project = parsed.options.init === "true" ? {
|
|
846
|
+
configPath: await deps.saveProjectConfig({
|
|
849
847
|
environment: env,
|
|
850
848
|
spaceId: space.id
|
|
851
|
-
}
|
|
852
|
-
|
|
853
|
-
|
|
854
|
-
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
else
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
849
|
+
}),
|
|
850
|
+
environment: env,
|
|
851
|
+
spaceId: space.id
|
|
852
|
+
} : void 0;
|
|
853
|
+
if (jsonOutput) deps.print(JSON.stringify({
|
|
854
|
+
space,
|
|
855
|
+
project
|
|
856
|
+
}, null, 2));
|
|
857
|
+
else printCreatedSpace(space, ctx.env, project?.configPath, deps.print);
|
|
858
|
+
return {
|
|
859
|
+
type: "create",
|
|
860
|
+
space,
|
|
861
|
+
project
|
|
862
|
+
};
|
|
863
|
+
}
|
|
864
|
+
if (spaceId) {
|
|
865
|
+
const details = await getSpaceDetails(ctx, deps, spaceId);
|
|
866
|
+
if (jsonOutput) deps.print(JSON.stringify(details, null, 2));
|
|
867
|
+
else printSpaceDetails(details, deps.print);
|
|
868
|
+
return {
|
|
869
|
+
type: "show",
|
|
870
|
+
space: details.space,
|
|
871
|
+
assets: details.assets
|
|
872
|
+
};
|
|
863
873
|
}
|
|
874
|
+
if (showDetails) {
|
|
875
|
+
const spaces = await listSpaceSummaries(ctx, deps);
|
|
876
|
+
if (jsonOutput) deps.print(JSON.stringify(spaces, null, 2));
|
|
877
|
+
else printSpaceSummaries(spaces, deps.print);
|
|
878
|
+
return {
|
|
879
|
+
type: "details",
|
|
880
|
+
spaces
|
|
881
|
+
};
|
|
882
|
+
}
|
|
883
|
+
const spaces = await fetchSpaces(ctx, deps);
|
|
884
|
+
if (jsonOutput) deps.print(JSON.stringify(spaces, null, 2));
|
|
885
|
+
else printSpaces(spaces, deps.print);
|
|
886
|
+
return {
|
|
887
|
+
type: "list",
|
|
888
|
+
spaces
|
|
889
|
+
};
|
|
864
890
|
}
|
|
865
|
-
async function createSpace(
|
|
866
|
-
const response = await fetch(`${baseUrl}/api/spaces`, {
|
|
891
|
+
async function createSpace(ctx, deps, name) {
|
|
892
|
+
const response = await deps.fetch(`${ctx.baseUrl}/api/spaces`, {
|
|
867
893
|
method: "POST",
|
|
868
894
|
headers: {
|
|
869
|
-
"Authorization": `Bearer ${accessToken}`,
|
|
895
|
+
"Authorization": `Bearer ${ctx.accessToken}`,
|
|
870
896
|
"Content-Type": "application/json"
|
|
871
897
|
},
|
|
872
898
|
body: JSON.stringify({ name })
|
|
@@ -877,83 +903,82 @@ async function createSpace(baseUrl, accessToken, name) {
|
|
|
877
903
|
}
|
|
878
904
|
return (await response.json()).space;
|
|
879
905
|
}
|
|
880
|
-
function printCreatedSpace(space, env, configPath) {
|
|
906
|
+
function printCreatedSpace(space, env, configPath, print) {
|
|
881
907
|
const envFlag = env === "production" ? "" : env === "local" ? " --local" : ` --env ${env}`;
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
if (configPath)
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
}
|
|
892
|
-
async function
|
|
893
|
-
const response = await fetch(`${baseUrl}/api/spaces`, { headers: {
|
|
894
|
-
"Authorization": `Bearer ${accessToken}`,
|
|
908
|
+
print(`\nSpace created successfully!\n`);
|
|
909
|
+
print(` ID: ${space.id}`);
|
|
910
|
+
print(` Name: ${space.name}`);
|
|
911
|
+
print(` Role: ${space.role}`);
|
|
912
|
+
if (configPath) print(` Config: ${configPath}`);
|
|
913
|
+
print(`\nTo bind this directory:`);
|
|
914
|
+
print(` makefx init --space ${space.id}${envFlag}`);
|
|
915
|
+
print(`\nTo listen for events:`);
|
|
916
|
+
print(` makefx listen --space ${space.id}${envFlag}`);
|
|
917
|
+
}
|
|
918
|
+
async function fetchSpaces(ctx, deps) {
|
|
919
|
+
const response = await deps.fetch(`${ctx.baseUrl}/api/spaces`, { headers: {
|
|
920
|
+
"Authorization": `Bearer ${ctx.accessToken}`,
|
|
895
921
|
"Content-Type": "application/json"
|
|
896
922
|
} });
|
|
897
923
|
if (!response.ok) throw new Error(`Failed to fetch spaces: ${response.status}`);
|
|
898
|
-
|
|
924
|
+
return (await response.json()).spaces;
|
|
925
|
+
}
|
|
926
|
+
function printSpaces(spaces, print) {
|
|
899
927
|
if (spaces.length === 0) {
|
|
900
|
-
|
|
928
|
+
print("No spaces found.");
|
|
901
929
|
return;
|
|
902
930
|
}
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
|
|
906
|
-
for (const space of spaces)
|
|
907
|
-
|
|
908
|
-
|
|
931
|
+
print(`\nFound ${spaces.length} space(s):\n`);
|
|
932
|
+
print("ID".padEnd(38) + "Name".padEnd(30) + "Role");
|
|
933
|
+
print("-".repeat(80));
|
|
934
|
+
for (const space of spaces) print(space.id.padEnd(38) + truncatePad(space.name, 30) + space.role);
|
|
935
|
+
print(`\nFor details: makefx spaces --details`);
|
|
936
|
+
print(`For a specific space: makefx spaces --id <space_id>`);
|
|
909
937
|
}
|
|
910
|
-
async function
|
|
911
|
-
const
|
|
912
|
-
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
|
|
917
|
-
|
|
918
|
-
|
|
938
|
+
async function listSpaceSummaries(ctx, deps) {
|
|
939
|
+
const spaces = await fetchSpaces(ctx, deps);
|
|
940
|
+
const summaries = [];
|
|
941
|
+
for (const space of spaces) {
|
|
942
|
+
const assets = await fetchSpaceAssets(ctx, deps, space.id);
|
|
943
|
+
summaries.push({
|
|
944
|
+
space,
|
|
945
|
+
assetCount: assets.length,
|
|
946
|
+
assetSummary: summarizeAssets(assets)
|
|
947
|
+
});
|
|
948
|
+
}
|
|
949
|
+
return summaries;
|
|
950
|
+
}
|
|
951
|
+
function printSpaceSummaries(summaries, print) {
|
|
952
|
+
if (summaries.length === 0) {
|
|
953
|
+
print("No spaces found.");
|
|
919
954
|
return;
|
|
920
955
|
}
|
|
921
|
-
|
|
922
|
-
for (const
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
if (assetsResponse.ok) {
|
|
930
|
-
const assets = (await assetsResponse.json()).assets;
|
|
931
|
-
assetCount = assets.length;
|
|
932
|
-
if (assets.length > 0) {
|
|
933
|
-
const byType = /* @__PURE__ */ new Map();
|
|
934
|
-
for (const asset of assets) {
|
|
935
|
-
const type = asset.type || "unknown";
|
|
936
|
-
byType.set(type, (byType.get(type) || 0) + 1);
|
|
937
|
-
}
|
|
938
|
-
const typeParts = [];
|
|
939
|
-
for (const [type, count] of byType) typeParts.push(`${count} ${type}`);
|
|
940
|
-
assetSummary = typeParts.join(", ");
|
|
941
|
-
const firstNames = assets.slice(0, 3).map((a) => a.name);
|
|
942
|
-
if (assets.length > 3) firstNames.push(`+${assets.length - 3} more`);
|
|
943
|
-
assetSummary += ` (${firstNames.join(", ")})`;
|
|
944
|
-
}
|
|
945
|
-
}
|
|
946
|
-
console.log(`━━━ ${space.name} ━━━`);
|
|
947
|
-
console.log(` ID: ${space.id}`);
|
|
948
|
-
console.log(` Role: ${space.role}`);
|
|
949
|
-
console.log(` Assets: ${assetCount}`);
|
|
950
|
-
if (assetSummary) console.log(` Content: ${assetSummary}`);
|
|
951
|
-
console.log("");
|
|
956
|
+
print(`\nFetching details for ${summaries.length} space(s)...\n`);
|
|
957
|
+
for (const summary of summaries) {
|
|
958
|
+
print(`━━━ ${summary.space.name} ━━━`);
|
|
959
|
+
print(` ID: ${summary.space.id}`);
|
|
960
|
+
print(` Role: ${summary.space.role}`);
|
|
961
|
+
print(` Assets: ${summary.assetCount}`);
|
|
962
|
+
if (summary.assetSummary) print(` Content: ${summary.assetSummary}`);
|
|
963
|
+
print("");
|
|
952
964
|
}
|
|
953
965
|
}
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
966
|
+
function summarizeAssets(assets) {
|
|
967
|
+
if (assets.length === 0) return "";
|
|
968
|
+
const byType = /* @__PURE__ */ new Map();
|
|
969
|
+
for (const asset of assets) {
|
|
970
|
+
const type = asset.type || "unknown";
|
|
971
|
+
byType.set(type, (byType.get(type) || 0) + 1);
|
|
972
|
+
}
|
|
973
|
+
const typeParts = [];
|
|
974
|
+
for (const [type, count] of byType) typeParts.push(`${count} ${type}`);
|
|
975
|
+
const firstNames = assets.slice(0, 3).map((a) => a.name);
|
|
976
|
+
if (assets.length > 3) firstNames.push(`+${assets.length - 3} more`);
|
|
977
|
+
return `${typeParts.join(", ")} (${firstNames.join(", ")})`;
|
|
978
|
+
}
|
|
979
|
+
async function getSpaceDetails(ctx, deps, spaceId) {
|
|
980
|
+
const spaceResponse = await deps.fetch(`${ctx.baseUrl}/api/spaces/${spaceId}`, { headers: {
|
|
981
|
+
"Authorization": `Bearer ${ctx.accessToken}`,
|
|
957
982
|
"Content-Type": "application/json"
|
|
958
983
|
} });
|
|
959
984
|
if (!spaceResponse.ok) {
|
|
@@ -961,18 +986,28 @@ async function showSpaceDetails(baseUrl, accessToken, spaceId) {
|
|
|
961
986
|
if (spaceResponse.status === 404) throw new Error(`Space not found: ${spaceId}`);
|
|
962
987
|
throw new Error(`Failed to fetch space: ${spaceResponse.status}`);
|
|
963
988
|
}
|
|
964
|
-
const
|
|
965
|
-
const
|
|
966
|
-
|
|
989
|
+
const spaceData = await spaceResponse.json();
|
|
990
|
+
const assets = await fetchSpaceAssets(ctx, deps, spaceId);
|
|
991
|
+
return {
|
|
992
|
+
space: spaceData.space,
|
|
993
|
+
assets
|
|
994
|
+
};
|
|
995
|
+
}
|
|
996
|
+
async function fetchSpaceAssets(ctx, deps, spaceId) {
|
|
997
|
+
const assetsResponse = await deps.fetch(`${ctx.baseUrl}/api/spaces/${spaceId}/assets`, { headers: {
|
|
998
|
+
"Authorization": `Bearer ${ctx.accessToken}`,
|
|
967
999
|
"Content-Type": "application/json"
|
|
968
1000
|
} });
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
1001
|
+
if (assetsResponse.ok) return (await assetsResponse.json()).assets;
|
|
1002
|
+
throw new Error(`Failed to fetch assets for space ${spaceId}: ${assetsResponse.status}`);
|
|
1003
|
+
}
|
|
1004
|
+
function printSpaceDetails(details, print) {
|
|
1005
|
+
const { space, assets } = details;
|
|
1006
|
+
print(`\n━━━ ${space.name} ━━━`);
|
|
1007
|
+
print(`ID: ${space.id}`);
|
|
1008
|
+
print(`Assets: ${assets.length}\n`);
|
|
974
1009
|
if (assets.length === 0) {
|
|
975
|
-
|
|
1010
|
+
print("(No assets in this space)");
|
|
976
1011
|
return;
|
|
977
1012
|
}
|
|
978
1013
|
const byType = /* @__PURE__ */ new Map();
|
|
@@ -982,16 +1017,15 @@ async function showSpaceDetails(baseUrl, accessToken, spaceId) {
|
|
|
982
1017
|
byType.get(type).push(asset);
|
|
983
1018
|
}
|
|
984
1019
|
for (const [type, typeAssets] of byType) {
|
|
985
|
-
|
|
1020
|
+
print(`${type.charAt(0).toUpperCase() + type.slice(1)}s (${typeAssets.length}):`);
|
|
986
1021
|
for (const asset of typeAssets) {
|
|
987
|
-
|
|
988
|
-
|
|
989
|
-
console.log(` ID: ${asset.id}`);
|
|
1022
|
+
print(` ${asset.active_variant_id ? "✓" : "○"} ${asset.name}`);
|
|
1023
|
+
print(` ID: ${asset.id}`);
|
|
990
1024
|
}
|
|
991
|
-
|
|
1025
|
+
print("");
|
|
992
1026
|
}
|
|
993
|
-
|
|
994
|
-
|
|
1027
|
+
print(`\nTo start a chat session with this space:`);
|
|
1028
|
+
print(` makefx chat send "What's in this space?" --space ${space.id} --state ./test/${space.name.toLowerCase().replace(/\s+/g, "-")}.json`);
|
|
995
1029
|
}
|
|
996
1030
|
function truncatePad(str, width) {
|
|
997
1031
|
if (str.length > width - 2) return str.slice(0, width - 3) + ".. ";
|
|
@@ -21594,9 +21628,9 @@ async function executeForgeCommand(command, parsed, deps = defaultDeps$6, option
|
|
|
21594
21628
|
try {
|
|
21595
21629
|
await client.connect();
|
|
21596
21630
|
switch (command) {
|
|
21597
|
-
case "generate": return await executeGenerate(parsed, ctx, client, deps, mediaKind);
|
|
21631
|
+
case "generate": return await executeGenerate(parsed, ctx, client, deps, mediaKind, { audioMode: options.audioMode });
|
|
21598
21632
|
case "refine": return await executeRefine(parsed, ctx, client, deps, mediaKind);
|
|
21599
|
-
case "derive": return await executeDerive(parsed, ctx, client, deps, mediaKind);
|
|
21633
|
+
case "derive": return await executeDerive(parsed, ctx, client, deps, mediaKind, { audioMode: options.audioMode });
|
|
21600
21634
|
case "batch": return await executeBatch(parsed, ctx, client, deps, mediaKind, saveBatchManifest);
|
|
21601
21635
|
}
|
|
21602
21636
|
} finally {
|
|
@@ -21612,7 +21646,8 @@ async function executeAudioCommand(command, parsed, deps = defaultDeps$6, option
|
|
|
21612
21646
|
if (parsed.options.input && command !== "generate") throw new Error("Audio --input is only supported with generate");
|
|
21613
21647
|
return executeForgeCommand(command, await prepareAudioParsedArgs(parsed, options.mode), deps, {
|
|
21614
21648
|
mediaKind: audioProfile.mediaKind,
|
|
21615
|
-
saveBatchManifest: audioProfile.savesBatchManifest
|
|
21649
|
+
saveBatchManifest: audioProfile.savesBatchManifest,
|
|
21650
|
+
audioMode: options.mode
|
|
21616
21651
|
});
|
|
21617
21652
|
}
|
|
21618
21653
|
async function executeVideoCommand(command, parsed, deps = defaultDeps$6) {
|
|
@@ -21635,12 +21670,17 @@ async function prepareAudioParsedArgs(parsed, mode) {
|
|
|
21635
21670
|
const input = await readFile(options.input, "utf8");
|
|
21636
21671
|
positionals.push(input);
|
|
21637
21672
|
}
|
|
21673
|
+
if (!options.follow) validateAudioModeRequiredVoiceOptions(options, effectiveMode);
|
|
21638
21674
|
return {
|
|
21639
21675
|
options,
|
|
21640
21676
|
positionals
|
|
21641
21677
|
};
|
|
21642
21678
|
}
|
|
21643
|
-
|
|
21679
|
+
function validateAudioModeRequiredVoiceOptions(options, mode) {
|
|
21680
|
+
if (mode === "speech" && !normalizeCliOption(options.voice)) throw new Error("Speech generation requires --voice <voice_id>. Run: makefx audio voices");
|
|
21681
|
+
if (mode === "dialogue" && !normalizeCliOption(options["dialogue-voices"] ?? options.dialogueVoices)) throw new Error("Dialogue generation requires --dialogue-voices <voice_id,voice_id>. Run: makefx audio voices");
|
|
21682
|
+
}
|
|
21683
|
+
async function executeGenerate(parsed, ctx, client, deps, mediaKind, followOptions = {}) {
|
|
21644
21684
|
const prompt = getPrompt(parsed, "generate");
|
|
21645
21685
|
const outputPath = getOutputPath$1(parsed);
|
|
21646
21686
|
const name = requireOption(parsed, "name");
|
|
@@ -21671,7 +21711,7 @@ async function executeGenerate(parsed, ctx, client, deps, mediaKind) {
|
|
|
21671
21711
|
...musicProvider ? { musicProvider } : {},
|
|
21672
21712
|
...videoAudioOptions,
|
|
21673
21713
|
...videoOptions,
|
|
21674
|
-
onStarted: (started) => printFollowHint(started, ctx, outputPath, "generate", mediaKind)
|
|
21714
|
+
onStarted: (started) => printFollowHint(started, ctx, outputPath, "generate", mediaKind, followOptions)
|
|
21675
21715
|
});
|
|
21676
21716
|
const productionRecord = await placeProductionRecordFromScene({
|
|
21677
21717
|
command: "generate",
|
|
@@ -21773,7 +21813,7 @@ async function executeRefine(parsed, ctx, client, deps, mediaKind) {
|
|
|
21773
21813
|
printResult(result, outputPath, ctx, manifestPath, productionRecord);
|
|
21774
21814
|
return result;
|
|
21775
21815
|
}
|
|
21776
|
-
async function executeDerive(parsed, ctx, client, deps, mediaKind) {
|
|
21816
|
+
async function executeDerive(parsed, ctx, client, deps, mediaKind, followOptions = {}) {
|
|
21777
21817
|
const prompt = getPrompt(parsed, "derive");
|
|
21778
21818
|
const outputPath = getOutputPath$1(parsed);
|
|
21779
21819
|
const name = requireOption(parsed, "name");
|
|
@@ -21804,7 +21844,7 @@ async function executeDerive(parsed, ctx, client, deps, mediaKind) {
|
|
|
21804
21844
|
mediaKind,
|
|
21805
21845
|
...videoAudioOptions,
|
|
21806
21846
|
...videoOptions,
|
|
21807
|
-
onStarted: (started) => printFollowHint(started, ctx, outputPath, "derive", mediaKind)
|
|
21847
|
+
onStarted: (started) => printFollowHint(started, ctx, outputPath, "derive", mediaKind, followOptions)
|
|
21808
21848
|
});
|
|
21809
21849
|
const productionRecord = await placeProductionRecordFromScene({
|
|
21810
21850
|
command: "derive",
|
|
@@ -22227,16 +22267,17 @@ function printResult(result, outputPath, ctx, manifestPath, productionRecord) {
|
|
|
22227
22267
|
if (productionRecord) console.log(` Production: ${productionRecord.production_id} (${productionRecord.id})`);
|
|
22228
22268
|
console.log(` Web: ${ctx.baseUrl}/spaces/${ctx.spaceId}/assets/${variant.asset_id}`);
|
|
22229
22269
|
}
|
|
22230
|
-
function printFollowHint(started, ctx, outputPath, command, mediaKind) {
|
|
22270
|
+
function printFollowHint(started, ctx, outputPath, command, mediaKind, options = {}) {
|
|
22231
22271
|
console.log(` Started variant: ${started.jobId}`);
|
|
22232
|
-
console.log(` Follow: ${formatFollowCommand(started.jobId, outputPath, ctx, command, mediaKind)}`);
|
|
22272
|
+
console.log(` Follow: ${formatFollowCommand(started.jobId, outputPath, ctx, command, mediaKind, options)}`);
|
|
22233
22273
|
}
|
|
22234
|
-
function formatFollowCommand(variantId, outputPath, ctx, command, mediaKind) {
|
|
22274
|
+
function formatFollowCommand(variantId, outputPath, ctx, command, mediaKind, options = {}) {
|
|
22235
22275
|
const baseCommand = mediaKind === "audio" ? [
|
|
22236
22276
|
"makefx",
|
|
22237
22277
|
"audio",
|
|
22278
|
+
options.audioMode,
|
|
22238
22279
|
"generate"
|
|
22239
|
-
] : mediaKind === "video" ? [
|
|
22280
|
+
].filter((part) => Boolean(part)) : mediaKind === "video" ? [
|
|
22240
22281
|
"makefx",
|
|
22241
22282
|
"video",
|
|
22242
22283
|
command
|
|
@@ -22302,10 +22343,11 @@ function validateVideoAudioOptions(parsed, mediaKind) {
|
|
|
22302
22343
|
if (parsed.options.audio !== void 0 && (parsed.options["no-audio"] !== void 0 || parsed.options.noAudio !== void 0)) throw new Error("Pass either --audio or --no-audio, not both");
|
|
22303
22344
|
}
|
|
22304
22345
|
function parseVideoAudioOptions(parsed, mediaKind) {
|
|
22305
|
-
if (mediaKind
|
|
22306
|
-
|
|
22307
|
-
|
|
22308
|
-
|
|
22346
|
+
if (mediaKind === "video") {
|
|
22347
|
+
if (parsed.options.audio !== void 0) return { generateAudio: true };
|
|
22348
|
+
if (parsed.options["no-audio"] !== void 0 || parsed.options.noAudio !== void 0) return { generateAudio: false };
|
|
22349
|
+
}
|
|
22350
|
+
return {};
|
|
22309
22351
|
}
|
|
22310
22352
|
function parseVideoGenerationOptions(parsed, mediaKind) {
|
|
22311
22353
|
const resolutionValue = readOptionalOption(parsed, "resolution", "resolution") ?? readOptionalOption(parsed, "video-resolution", "videoResolution");
|
|
@@ -22620,9 +22662,9 @@ Usage:
|
|
|
22620
22662
|
makefx audio <${modes}> batch "prompt" --name <name> --count <2-8> --output-dir <dir> [--space <id>]
|
|
22621
22663
|
makefx audio music generate "prompt" --provider lyria --name <name> -o <file> [--space <id>]
|
|
22622
22664
|
|
|
22623
|
-
Voice selection:
|
|
22665
|
+
Voice selection (run 'makefx audio voices' to list voice IDs):
|
|
22624
22666
|
makefx audio speech generate "text" --voice <voice_id> --name <name> -o <file>
|
|
22625
|
-
makefx audio dialogue generate --input script.txt --
|
|
22667
|
+
makefx audio dialogue generate --input script.txt --dialogue-voices <voice_id,voice_id> --name <name> -o <file>
|
|
22626
22668
|
|
|
22627
22669
|
Low-level compatibility:
|
|
22628
22670
|
makefx audio generate "prompt" --name <name> --type <type> -o <file> [--space <id>]
|
|
@@ -22670,8 +22712,8 @@ Video:
|
|
|
22670
22712
|
--tier <tier> Veo model tier: ${tierValues}
|
|
22671
22713
|
|
|
22672
22714
|
Audio:
|
|
22673
|
-
--audio Request native synchronized Veo audio
|
|
22674
|
-
--no-audio Request a silent video
|
|
22715
|
+
--audio Request native synchronized Veo audio (default)
|
|
22716
|
+
--no-audio Request a silent video; MakeFX records this and adds a silent-video instruction.
|
|
22675
22717
|
|
|
22676
22718
|
Production metadata:
|
|
22677
22719
|
--scene-label <label> --timeline-start-ms <ms> --duration-ms <ms>
|
|
@@ -23565,9 +23607,11 @@ Options:
|
|
|
23565
23607
|
}
|
|
23566
23608
|
//#endregion
|
|
23567
23609
|
//#region src/cli/index.ts
|
|
23568
|
-
var CLI_VERSION = "0.1.
|
|
23610
|
+
var CLI_VERSION = "0.1.2+2907a84228d9";
|
|
23569
23611
|
async function main() {
|
|
23570
|
-
const
|
|
23612
|
+
const argv = process$1.argv.slice(2);
|
|
23613
|
+
if (argv[0] === "--") argv.shift();
|
|
23614
|
+
const [command, ...args] = argv;
|
|
23571
23615
|
if (command === "--version" || command === "version") {
|
|
23572
23616
|
console.log(CLI_VERSION);
|
|
23573
23617
|
return;
|
|
@@ -23760,8 +23804,9 @@ Billing (Polar.sh):
|
|
|
23760
23804
|
|
|
23761
23805
|
Spaces:
|
|
23762
23806
|
spaces List all spaces
|
|
23763
|
-
spaces --
|
|
23764
|
-
spaces --
|
|
23807
|
+
spaces --json List all spaces as JSON
|
|
23808
|
+
spaces --details [--json] List spaces with asset summaries
|
|
23809
|
+
spaces --id <id> [--json] Show details for a specific space
|
|
23765
23810
|
spaces create <name> Create a new space
|
|
23766
23811
|
|
|
23767
23812
|
Listen:
|
|
@@ -23866,8 +23911,9 @@ function printSpacesHelp() {
|
|
|
23866
23911
|
console.log(`
|
|
23867
23912
|
Usage:
|
|
23868
23913
|
makefx spaces
|
|
23869
|
-
makefx spaces --
|
|
23870
|
-
makefx spaces --
|
|
23914
|
+
makefx spaces --json
|
|
23915
|
+
makefx spaces --details [--json]
|
|
23916
|
+
makefx spaces --id <space_id> [--json]
|
|
23871
23917
|
makefx spaces create <name>
|
|
23872
23918
|
makefx spaces create --name "My Space" [--init] [--json]
|
|
23873
23919
|
`);
|
|
@@ -24044,8 +24090,7 @@ Usage:
|
|
|
24044
24090
|
${videoCapabilityHelp()}
|
|
24045
24091
|
|
|
24046
24092
|
Audio:
|
|
24047
|
-
--audio
|
|
24048
|
-
--no-audio Request a silent video (default)
|
|
24093
|
+
Video defaults to generated audio. Use --no-audio to record a silent-video request and add a silent-video instruction.
|
|
24049
24094
|
|
|
24050
24095
|
Production metadata:
|
|
24051
24096
|
--scene-label <label> --timeline-start-ms <ms> --duration-ms <ms>
|
|
@@ -24062,8 +24107,7 @@ Usage:
|
|
|
24062
24107
|
${videoCapabilityHelp()}
|
|
24063
24108
|
|
|
24064
24109
|
Audio:
|
|
24065
|
-
--audio
|
|
24066
|
-
--no-audio Request a silent video (default)
|
|
24110
|
+
Video defaults to generated audio. Use --no-audio to record a silent-video request and add a silent-video instruction.
|
|
24067
24111
|
|
|
24068
24112
|
Production metadata:
|
|
24069
24113
|
--scene-label <label> --timeline-start-ms <ms> --duration-ms <ms>
|
|
@@ -24080,8 +24124,7 @@ Usage:
|
|
|
24080
24124
|
${videoCapabilityHelp()}
|
|
24081
24125
|
|
|
24082
24126
|
Audio:
|
|
24083
|
-
--audio
|
|
24084
|
-
--no-audio Request a silent video (default)
|
|
24127
|
+
Video defaults to generated audio. Use --no-audio to record a silent-video request and add a silent-video instruction.
|
|
24085
24128
|
|
|
24086
24129
|
Production metadata:
|
|
24087
24130
|
--scene-label <label> --timeline-start-ms <ms> --duration-ms <ms>
|
|
@@ -24099,8 +24142,7 @@ Usage:
|
|
|
24099
24142
|
${videoCapabilityHelp()}
|
|
24100
24143
|
|
|
24101
24144
|
Audio:
|
|
24102
|
-
--audio
|
|
24103
|
-
--no-audio Request a silent video (default)
|
|
24145
|
+
Video defaults to generated audio. Use --no-audio to record a silent-video request and add a silent-video instruction.
|
|
24104
24146
|
|
|
24105
24147
|
Production metadata:
|
|
24106
24148
|
--scene-label <label> --timeline-start-ms <ms> --duration-ms <ms>
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "makefx",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.2",
|
|
4
4
|
"description": "Command-line interface for AI-assisted game asset production with Make Effects.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
"url": "git+https://github.com/krasnoperov/inventory.git"
|
|
10
10
|
},
|
|
11
11
|
"bin": {
|
|
12
|
-
"makefx": "
|
|
12
|
+
"makefx": "makefx.mjs"
|
|
13
13
|
},
|
|
14
14
|
"files": [
|
|
15
15
|
"makefx.mjs",
|