A TypeScript library that automatically detects project root directories by analyzing file patterns and project indicators.
This library scans file system paths to find the root directory of software projects. It looks for common project files like package.json
, tsconfig.json
, go.mod
, and many others to determine where a project actually begins.
npm install @neabyte/project-root
import { findProjectRoot } from '@neabyte/project-root'
// Find the project root from a file path
const projectRoot = findProjectRoot('/path/to/some/file.ts')
console.log(projectRoot) // '/path/to/project/root'
import { findProjectDeep } from '@neabyte/project-root'
// Find all projects in a directory tree
const projects = findProjectDeep('/path/to/directory', 5, false)
console.log(projects)
// [
// { path: '/path/to/directory/project1', score: 45, depth: 0, relativePath: '.' },
// { path: '/path/to/directory/project2', score: 32, depth: 1, relativePath: 'subfolder' }
// ]
Searches upward from the given path to find the project root.
Parameters:
startPath
- The file system path to begin searching from
Returns:
- The absolute path of the project root, or
null
if none found
findProjectDeep(startPath: string, maxDepth?: number, includeSubdirectories?: boolean): ProjectDiscovery[]
Recursively scans a directory tree to find all project roots.
Parameters:
startPath
- The root directory to begin scanningmaxDepth
- Maximum depth to scan (default: 10, use -1 for unlimited)includeSubdirectories
- Whether to include subdirectories of found projects (default: false)
Returns:
- Array of discovered projects with metadata
The library detects projects based on common configuration files and patterns:
- JavaScript/TypeScript:
package.json
,tsconfig.json
,yarn.lock
- Go:
go.mod
,go.sum
- Rust:
Cargo.toml
,Cargo.lock
- Java:
pom.xml
,build.gradle
- Python:
pyproject.toml
,requirements.txt
- PHP:
composer.json
,composer.lock
- Ruby:
Gemfile
,Gemfile.lock
- Dart/Flutter:
pubspec.yaml
,pubspec.lock
- Swift:
Package.swift
- Elixir:
mix.exs
,mix.lock
- Clojure:
project.clj
,deps.edn
- Haskell:
stack.yaml
,package.yaml
- Julia:
Project.toml
,Manifest.toml
- Crystal:
shard.yml
,shard.lock
- Lua:
rockspec
,luarocks.lock
- CMake:
CMakeLists.txt
- Make:
Makefile
- Zig:
build.zig
- D:
dub.json
,dub.sdl
- V:
v.mod
,vpkg.json
- Scala:
build.sbt
- OCaml:
dune-project
,opam
- Erlang:
rebar.config
,erlang.mk
- Git:
.git/
- Mercurial:
.hg/
- Subversion:
.svn/
- Bazaar:
.bzr/
- Fossil:
.fossil
- Perforce:
.p4config
- Darcs:
_darcs/
- Monotone:
_MTN/
- Jujutsu:
.jj/
- Pijul:
.pijul/
- VSCode:
.vscode/
,*.code-workspace
- Webpack:
webpack.config.js
- Vite:
vite.config.js
- Rollup:
rollup.config.js
- Babel:
babel.config.js
- Jest:
jest.config.js
The library uses a scoring system to determine project roots:
- Scans directories for known project indicator files
- Calculates confidence scores based on found indicators
- Filters out common directories like
node_modules
,dist
,build
- Returns the highest scoring directory as the project root
Each indicator has a different score weight. For example:
package.json
has a score of 20yarn.lock
has a score of 60.git/
has a score of 25
The library automatically excludes common build and cache directories:
node_modules/
,vendor/
,bower_components/
target/
,build/
,dist/
,out/
,bin/
,obj/
.idea/
,.vs/
,.cache/
,.npm/
,.yarn/
coverage/
,.nyc_output/
,.jest/
__pycache__/
,.pytest_cache/
tmp/
,temp/
,.tmp/
,.temp/
logs/
,log/
- And many more...
The library is written in TypeScript and provides full type definitions:
interface ProjectDiscovery {
path: string
score: number
depth: number
relativePath: string
}
interface BestMatch {
path: string
score: number
}
interface Indicator extends BestMatch {
name: string
}
This project is licensed under the MIT license. See the LICENSE file for more info.