Skip to solution
easyFrontend

What is `create-react-app` and when would you use it?

121 views
01

Understand the problem

Question presented to candidate: "What is create-react-app, and when would you reach for it to start a new project today?"

What a strong answer should cover:

  • CRA was the officially blessed zero-configuration starter: one command produced a working React app with Babel, webpack, ESLint, and a dev server pre-wired.
  • Its value was hiding the build configuration, with eject as the escape hatch.
  • The key fact: the React team officially sunset CRA in February 2025. It is deprecated and unmaintained, kept alive only in maintenance mode.
  • Why: it had no active maintainers, and it solved none of the problems real production apps have — routing, data fetching, code splitting.
  • The current recommendation: a framework (Next.js, React Router, Expo) for most apps, or a build tool (Vite, Parcel, Rsbuild) if you want a plain SPA.
  • Secondary problems that made it untenable: slow cold starts and rebuilds versus modern esbuild/Rollup-based tooling, and a large transitive dependency tree with persistent audit noise.
  • So the answer to "when would you use it" is: for a new project, never — only when maintaining an existing CRA app, where the real discussion is migration.

Clarifying questions expected:

  • "Is this a new project, or are we maintaining an existing CRA app?"
  • "Do we need server rendering and SEO, or is a client-only SPA fine?"

Code / implementation expected: No. This is a tooling and judgement question; naming the right replacement command matters more than code.

toolingsetupcreate-react-appstarter kit
02

Attempt it yourself

Sketch your approach before reading the solution — that's what interviews test.

Nudge consolestandby

Stuck? Beam a request up — the console returns a conceptual nudge that guides your logic without spoiling the implementation.

03

Study the solution

Target Audience: Engineers preparing for React interviews — assumes you have started a React project before. Difficulty: Easy

How to read this doc: Concepts are explained in plain language first, then tagged with 📌 Interview term:. The deprecation status below was checked against the React

Solution ready — 2 min read

Classified // press E to declassify

04

Explore the playground snippets

Reading a project's tooling at runtime — CRA versus Vite conventions
Run Playground
import { useState } from "react";

// The two toolchains leave different fingerprints in a codebase. This is the
// checklist you would actually run through when inheriting an unfamiliar app.
const SIGNALS = [
  { area: "package.json dependency", cra: "react-scripts", vite: "vite + @vitejs/plugin-react" },
  { area: "scripts.start / dev",     cra: "react-scripts start", vite: "vite" },
  { area: "index.html lives in",     cra: "public/", vite: "project root" },
  { area: "env var prefix",          cra: "REACT_APP_", vite: "VITE_" },
  { area: "env access",              cra: "process.env.REACT_APP_X", vite: "import.meta.env.VITE_X" },
  { area: "test runner",             cra: "Jest, preconfigured", vite: "Vitest, added separately" },
  { area: "config escape hatch",     cra: "eject (one-way)", vite: "vite.config.js (always yours)" },
  { area: "status",                  cra: "sunset Feb 2025", vite: "actively maintained" },
];

export default function App() {
  const [show, setShow] = useState(false);

  // import.meta.env exists under Vite-family tooling (this playground included).
  const hasViteEnv = typeof import.meta !== "undefined" && Boolean(import.meta.env);

  const th = { textAlign: "left", padding: "6px 12px 6px 0", borderBottom: "1px solid #ddd" };
  const td = { padding: "5px 12px 5px 0", verticalAlign: "top" };

  return (
    <div style={{ padding: 24, fontFamily: "system-ui", lineHeight: 1.5 }}>
      <h3>Which toolchain is this project on?</h3>
      <p style={{ background: "#eef6ff", padding: 10, borderRadius: 6, fontSize: 14 }}>
        <code>import.meta.env</code> is {hasViteEnv ? "available" : "not available"} here —
        {hasViteEnv
          ? " a Vite-family bundler. CRA exposed process.env.REACT_APP_* instead."
          : " so this is not a Vite build."}
      </p>

      <button onClick={() => setShow((s) => !s)}>
        {show ? "Hide" : "Show"} the migration checklist
      </button>

      {show && (
        <table style={{ borderCollapse: "collapse", marginTop: 16, fontSize: 13 }}>
          <thead>
            <tr><th style={th}>What to check</th><th style={th}>CRA</th><th style={th}>Vite</th></tr>
          </thead>
          <tbody>
            {SIGNALS.map((s) => (
              <tr key={s.area}>
                <td style={td}>{s.area}</td>
                <td style={{ ...td, color: "#a33" }}><code>{s.cra}</code></td>
                <td style={{ ...td, color: "#161" }}><code>{s.vite}</code></td>
              </tr>
            ))}
          </tbody>
        </table>
      )}
    </div>
  );
}
05

Join the discussion

Discussion (0)

Sign in to join the discussion.

No responses yet. Be the first to share what you think.

Transmission complete // awaiting log

KEEP THE
STREAK ALIVE.

Dossier 25 of 119 decoded in the React.js track. One more won't hurt.

Back to track