index.ts 2.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. #!/usr/bin/env node
  2. import * as path from 'node:path';
  3. import { createOrEmptyTargetDirectory } from './utils/fsHelpers';
  4. import { getInputs } from './utils/getInputs';
  5. import { getLanguage } from './utils/getLanguage';
  6. import { logBanner, logDone, logStep } from './utils/getLogs';
  7. import { RenderContext, getRenderContext } from './utils/getRenderContext';
  8. import { renderTemplate } from './utils/renderTemplates';
  9. import {
  10. detectSolanaVersion,
  11. generateKeypair,
  12. patchSolanaDependencies,
  13. } from './utils/solanaCli';
  14. (async function init() {
  15. logBanner();
  16. // Get arguments from CLI and prompt.
  17. const language = getLanguage();
  18. const inputs = await getInputs(language);
  19. // Create or empty the target directory.
  20. createOrEmptyTargetDirectory(
  21. language,
  22. inputs.targetDirectoryName,
  23. inputs.shouldOverride
  24. );
  25. // Detect the solana version.
  26. const solanaVersionDetected = await logStep(
  27. language.infos.detectSolanaVersion,
  28. () => detectSolanaVersion(language)
  29. );
  30. // Generate a keypair if needed.
  31. const programAddress =
  32. inputs.programAddress ??
  33. (await logStep(language.infos.generateKeypair, () => {
  34. const outfile = path.join(
  35. process.cwd(),
  36. inputs.targetDirectoryName,
  37. 'program',
  38. 'keypair.json'
  39. );
  40. return generateKeypair(language, outfile);
  41. }));
  42. // Get the args inputs, prompt inputs and computed values.
  43. const ctx = getRenderContext({
  44. language,
  45. inputs,
  46. programAddress,
  47. solanaVersionDetected,
  48. });
  49. // Render the templates.
  50. await logStep(
  51. language.infos.scaffold.replace(
  52. '$targetDirectory',
  53. inputs.targetDirectoryName
  54. ),
  55. async () => {
  56. renderTemplates(ctx);
  57. await patchSolanaDependencies(ctx.targetDirectory, ctx.solanaVersion);
  58. }
  59. );
  60. // Done.
  61. logDone(ctx);
  62. })().catch((e) => console.error(e));
  63. function renderTemplates(ctx: RenderContext) {
  64. const render = (templateName: string) => {
  65. const directory = path.resolve(ctx.templateDirectory, templateName);
  66. renderTemplate(ctx, directory, ctx.targetDirectory);
  67. };
  68. render('base');
  69. if (ctx.programFramework === 'anchor') {
  70. render('programs/counter-anchor');
  71. } else {
  72. render('programs/counter-shank');
  73. }
  74. if (ctx.clients.length > 0) {
  75. render('clients/base');
  76. }
  77. ctx.clients.forEach((client) => {
  78. render(`clients/${client}`);
  79. });
  80. }