Project Detection
Project Detection
Section titled “Project Detection”The @xtarterize/core package provides the detectProject() function — the foundation of Xtarterize’s context-aware behavior.
Overview
Section titled “Overview”Project detection is the first step in every Xtarterize command. It analyzes your project directory to build a ProjectProfile that drives which conformance tasks are applicable.
detectProject Function
Section titled “detectProject Function”import { detectProject } from '@xtarterize/core'
const profile = await detectProject('/path/to/project')ProjectProfile Schema
Section titled “ProjectProfile Schema”The detection returns a ProjectProfile object:
interface ProjectProfile { // Framework framework: 'react' | 'react-native' | 'vue' | 'svelte' | 'solid' | 'node' | null frameworkVersion: string | null
// Bundler bundler: 'vite' | 'nextjs' | 'tanstack-start' | 'expo' | 'webpack' | 'rspack' | 'none' | null
// Router router: 'tanstack-router' | 'react-router' | 'next' | 'expo-router' | 'vue-router' | null
// Styling styling: ('tailwind' | 'css-modules' | 'styled-components' | 'vanilla-extract' | 'nativewind' | 'vanilla')[]
// Language & Runtime typescript: boolean runtime: 'browser' | 'node' | 'edge' | 'native' | 'universal'
// Package manager packageManager: 'npm' | 'pnpm' | 'yarn' | 'bun'
// Repo structure monorepo: boolean monorepoTool: 'turbo' | 'nx' | 'lerna' | null workspaceRoot: boolean
// Git hasGitHub: boolean hasGit: boolean
// Existing config presence existing: { biome: boolean tsconfig: boolean renovate: boolean commitlint: boolean knip: boolean plop: boolean turbo: boolean vscodeSettings: boolean agentsMd: boolean githubWorkflows: string[] }}Detection Logic
Section titled “Detection Logic”flowchart TD
A[package.json] --> B{Dependencies}
B --> C[detectFramework]
B --> D[detectBundler]
B --> E[detectRouter]
B --> F[detectStyling]
B --> G[detectVitePlus]
C --> H{Framework?}
H -->|react-native + react| I[Ambiguous → prompt user]
H -->|react| J[Framework: react]
H -->|vue| K[Framework: vue]
H -->|svelte| L[Framework: svelte]
H -->|solid| M[Framework: solid]
H -->|node| N[Framework: node]
D --> O{Bundler?}
O -->|@tanstack/start| P[TanStack Start]
O -->|next| Q[Next.js]
O -->|expo| R[Expo]
O -->|vite| S[Vite]
O -->|webpack| T[Webpack]
O -->|@rspack/core| U[Rspack]
O -->|none| V[None]
E --> W{Router?}
W -->|nextjs bundler| X[Next Router]
W -->|expo bundler| Y[Expo Router]
W -->|@tanstack/react-router| Z[TanStack Router]
W -->|react-router| AA[React Router]
W -->|vue-router| AB[Vue Router]
style A fill:#6366f1,color:#fff
style C fill:#22c55e,color:#fff
style D fill:#22c55e,color:#fff
Detection Sources
Section titled “Detection Sources”| Signal | Source |
|---|---|
| Framework | package.json dependencies (react, vue, react-native, etc.) |
| Bundler | vite, next, expo, webpack, @rspack/core in deps |
| Router | @tanstack/react-router, react-router-dom, vue-router in deps |
| Styling | tailwindcss, styled-components, nativewind in deps |
| Signal | Source |
|---|---|
| TypeScript | tsconfig.json existence, typescript in deps |
| Package manager | Lockfile presence (pnpm-lock.yaml, yarn.lock, etc.) |
| Monorepo | pnpm-workspace.yaml, turbo.json, packages/ + apps/ dirs |
| GitHub | .github/ directory presence |
Ambiguity Handling
Section titled “Ambiguity Handling”Example
Section titled “Example”const profile = await detectProject('/path/to/project')
if (profile.bundler === 'vite' && profile.typescript) { // Vite plugin tasks will be applicable}
if (profile.monorepo && profile.monorepoTool === 'turbo') { // Turbo task may be skip if already configured}