create-nextblock 0.8.2 → 0.8.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.
@@ -795,14 +795,15 @@ async function runSetupWizard(projectDir, projectName) {
795
795
  // access token so no browser login is required.
796
796
  const supabaseBin = await getSupabaseBinary(projectPath);
797
797
  const command = supabaseBin === 'npx' ? 'npx' : supabaseBin;
798
- const sbArgs = (args) => (supabaseBin === 'npx' ? ['supabase', ...args] : args);
798
+ // `--yes` skips npx's "Ok to proceed?" install prompt if it ever falls back to npx
799
+ // (i.e. the supabase devDependency somehow isn't installed) so it can't hang the wizard.
800
+ const sbArgs = (args) =>
801
+ supabaseBin === 'npx' ? ['--yes', 'supabase', ...args] : args;
799
802
  const supabaseEnv = {
800
803
  ...process.env,
801
804
  SUPABASE_ACCESS_TOKEN: supabase.accessToken,
802
805
  SUPABASE_DB_PASSWORD: dbPassword,
803
806
  POSTGRES_URL: postgresUrl,
804
- // Available for env() substitution in supabase config.toml during `config push`.
805
- NEXT_PUBLIC_URL: siteUrl,
806
807
  };
807
808
 
808
809
  const applySchema = await clack.confirm({
@@ -814,8 +815,9 @@ async function runSetupWizard(projectDir, projectName) {
814
815
  handleWizardCancel('Setup cancelled.');
815
816
  }
816
817
 
817
- const dbSpinner = clack.spinner();
818
- dbSpinner.start('Linking to your Supabase project...');
818
+ // Stream the Supabase CLI's own output (stdio: inherit) instead of hiding it behind a
819
+ // spinner link/push are long-running and a spinner over inherited output looks frozen.
820
+ clack.log.step('Linking to your Supabase project...');
819
821
  try {
820
822
  await execa(
821
823
  command,
@@ -824,7 +826,9 @@ async function runSetupWizard(projectDir, projectName) {
824
826
  );
825
827
 
826
828
  if (applySchema) {
827
- dbSpinner.message('Pushing database schema...');
829
+ clack.log.step(
830
+ 'Applying the database schema — this can take a minute on a fresh project...',
831
+ );
828
832
  await execa(command, sbArgs(['db', 'push', '--include-all']), {
829
833
  stdio: ['pipe', 'inherit', 'inherit'],
830
834
  cwd: projectPath,
@@ -832,21 +836,14 @@ async function runSetupWizard(projectDir, projectName) {
832
836
  env: supabaseEnv,
833
837
  });
834
838
 
835
- dbSpinner.message('Pushing Supabase config (auth settings)...');
836
- await execa(command, sbArgs(['config', 'push']), {
837
- stdio: ['pipe', 'inherit', 'inherit'],
838
- cwd: projectPath,
839
- env: supabaseEnv,
840
- });
841
-
842
- dbSpinner.stop('Database schema and config applied.');
839
+ clack.log.success('Database schema applied.');
843
840
  } else {
844
- dbSpinner.stop(
841
+ clack.log.info(
845
842
  'Linked. Skipped schema push — run `npx supabase db push --include-all` when ready.',
846
843
  );
847
844
  }
848
845
  } catch (error) {
849
- dbSpinner.stop(
846
+ clack.log.warn(
850
847
  'Database setup failed. You can run `npx supabase db push --include-all` manually.',
851
848
  );
852
849
  if (error instanceof Error) {
@@ -854,10 +851,11 @@ async function runSetupWizard(projectDir, projectName) {
854
851
  }
855
852
  }
856
853
 
857
- // 7. Sync hosted Supabase Auth: custom SMTP + branded email templates. SMTP and the
858
- // access token are required, so this always runs (matching setup.mjs). This is what
859
- // lets Supabase email your first admin their confirmation link.
860
- await enableSupabaseSmtpConfig(projectPath);
854
+ // 7. Configure hosted Supabase Auth via the Management API: site URL + custom SMTP +
855
+ // branded email templates. This is the same mechanism as `npm run configure:supabase-auth`
856
+ // in the monorepo, and it's what lets Supabase email your first admin's confirmation link.
857
+ // (We deliberately do NOT `supabase config push` the whole config.toml — that pushes
858
+ // local-only/unset values like env(TARGET_URL) and isn't what the monorepo does.)
861
859
  await configureHostedSupabaseAuth(projectPath, {
862
860
  projectId,
863
861
  siteUrl,
@@ -900,48 +898,6 @@ async function runSetupWizard(projectDir, projectName) {
900
898
  );
901
899
  }
902
900
 
903
- async function enableSupabaseSmtpConfig(projectDir) {
904
- const configPath = resolve(projectDir, 'supabase', 'config.toml');
905
-
906
- if (!(await fs.pathExists(configPath))) {
907
- return;
908
- }
909
-
910
- const smtpBlock = `# [auth.email.smtp]
911
- # host = "env(SMTP_HOST)"
912
- # port = 587
913
- # user = "env(SMTP_USER)"
914
- # pass = "env(SMTP_PASS)"
915
- # admin_email = "env(SMTP_FROM_EMAIL)"
916
- # sender_name = "env(SMTP_FROM_NAME)"`;
917
-
918
- const enabledSmtpBlock = `[auth.email.smtp]
919
- host = "env(SMTP_HOST)"
920
- port = 587
921
- user = "env(SMTP_USER)"
922
- pass = "env(SMTP_PASS)"
923
- admin_email = "env(SMTP_FROM_EMAIL)"
924
- sender_name = "env(SMTP_FROM_NAME)"`;
925
-
926
- const configContents = await fs.readFile(configPath, 'utf8');
927
-
928
- if (configContents.includes(enabledSmtpBlock)) {
929
- return;
930
- }
931
-
932
- if (!configContents.includes(smtpBlock)) {
933
- throw new Error(
934
- `Could not find the SMTP placeholder block in ${configPath}.`,
935
- );
936
- }
937
-
938
- await fs.writeFile(
939
- configPath,
940
- configContents.replace(smtpBlock, enabledSmtpBlock),
941
- 'utf8',
942
- );
943
- }
944
-
945
901
  async function configureHostedSupabaseAuth(
946
902
  projectDir,
947
903
  { projectId, siteUrl, accessToken, smtpValues },
@@ -1830,17 +1786,31 @@ async function transformPackageJson(projectDir) {
1830
1786
  keygrip: 'npm:keygrip@latest',
1831
1787
  };
1832
1788
  let rootOverrides = FALLBACK_OVERRIDES;
1789
+ let supabaseCliVersion = '^2.95.6'; // keep in sync with the repo root devDependency
1833
1790
  try {
1834
1791
  const rootPkg = await fs.readJSON(resolve(REPO_ROOT, 'package.json'));
1835
1792
  if (rootPkg?.overrides && Object.keys(rootPkg.overrides).length > 0) {
1836
1793
  rootOverrides = rootPkg.overrides;
1837
1794
  }
1795
+ const rootSupabase =
1796
+ rootPkg?.devDependencies?.supabase ?? rootPkg?.dependencies?.supabase;
1797
+ if (rootSupabase) {
1798
+ supabaseCliVersion = rootSupabase;
1799
+ }
1838
1800
  } catch {
1839
- // Published CLI: repo root package.json not present — keep the baked-in fallback.
1801
+ // Published CLI: repo root package.json not present — keep the baked-in fallbacks.
1840
1802
  }
1841
1803
  // Project-specific overrides (if any) win over the inherited defaults.
1842
1804
  packageJson.overrides = { ...rootOverrides, ...(packageJson.overrides ?? {}) };
1843
1805
 
1806
+ // Ship the Supabase CLI as a devDependency so setup / link / db push use a locally-installed
1807
+ // binary. Without it, `npx supabase` downloads the CLI (~40MB) and shows an "Ok to proceed?"
1808
+ // prompt mid-wizard that looks like a hang.
1809
+ packageJson.devDependencies = packageJson.devDependencies ?? {};
1810
+ if (!packageJson.devDependencies.supabase) {
1811
+ packageJson.devDependencies.supabase = supabaseCliVersion;
1812
+ }
1813
+
1844
1814
  // npm throws EOVERRIDE when a package is BOTH a direct dependency and has an override with a
1845
1815
  // different spec (e.g. dependencies.uuid ^11.0.4 vs overrides.uuid ^11.1.1). Align any such
1846
1816
  // direct (dev)dependency to the override value so they share the exact same spec — which is
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "create-nextblock",
3
- "version": "0.8.2",
3
+ "version": "0.8.5",
4
4
  "description": "",
5
5
  "main": "index.js",
6
6
  "bin": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nextblock-cms/template",
3
- "version": "0.8.2",
3
+ "version": "0.8.5",
4
4
  "private": true,
5
5
  "scripts": {
6
6
  "dev": "next dev",