Sloc (Source Lines Of Code) is a .NET global command-line tool for counting lines of source code. It analyzes files individually, distinguishing code lines, comment lines, and blank lines, then aggregates results by programming language. It supports 63 auto-detected languages, five output formats (table, JSON, HTML, CSV, Markdown), per-file detail view, and comment health indicators.
- Count code / comment / blank / total lines
- Correctly handles single-line comments, block comments, and multi-line block comments
- Built-in comment rules for 63 common languages (auto-detected by file extension or name, e.g.
Makefile,Dockerfile,CMakeLists.txt) - Recursive directory scanning with
--include/--excludeglob filters - Automatically excludes
bin,obj,artifacts,.git,.vs,.vscode,.idea,node_modules, and similar directories by default - Five output formats: colored table (default), JSON, HTML, CSV, and Markdown
- Comment Health column in table output showing comment-density indicator (None / Low / Fair / Good / High / Dense)
- Format auto-detected from the
--outputfile extension (.json→ JSON,.html/.htm→ HTML) - Honors
.gitignorefiles (including nested ones) by default;--no-gitignoredisables it - Parallel analysis across CPU cores (
--jobs), with deterministic output - CI-friendly: JSON to stdout for piping (e.g.
| jq), meaningful exit codes, and a--min-comment-pctthreshold gate - Compare against a saved JSON report with
--baselineto see how line counts changed - Sort and limit the language summary with
--sort/--top - Files or directories that cannot be read, and binary files (detected by NUL bytes), are skipped gracefully; a summary of skipped paths and reasons is shown at the end (in every format except
Csv, which stays a single machine-parsable table)
Install via winget (Windows):
winget install coldhighsun.slocOr install as a .NET global tool (requires .NET 8 SDK):
dotnet tool install --global SlocUpdate or uninstall:
winget upgrade coldhighsun.sloc
winget uninstall coldhighsun.sloc
dotnet tool update --global Sloc
dotnet tool uninstall --global Slocsloc <path> [options]# Count current directory (recursive)
sloc
# Count a specific directory
sloc ./src
# Count a single file
sloc ./src/Program.cs
# Only count C# files
sloc ./src --include "**/*.cs"
# Exclude test directories
sloc . --exclude "**/tests/**"
# Show per-file details
sloc ./src --by-file
# Output as JSON
sloc ./src --format json
# Save results as an HTML report (opens in a browser)
sloc ./src --format html --output report.html
# HTML printed to stdout (default when --output is omitted)
sloc ./src --format html
# Auto-detect format from file extension
sloc ./src --output sloc-report.json
# Include files with unknown extensions
sloc . --all
# Do not recurse into subdirectories
sloc ./src --no-recursive
# Pipe JSON to jq
sloc . --format json | jq .total
# Fail CI if comments are below 10% of lines
sloc . --min-comment-pct 10
# Save a baseline, then diff a later run against it
sloc . --format json --output baseline.json
sloc . --baseline baseline.json
# Sort by comment lines and show only the top 5 languages
sloc . --sort comment --top 5
# Markdown report with both language summary and per-file breakdown, printed to stdout
sloc . --format markdown --detailed -o -| Option | Short | Description |
|---|---|---|
path (argument) |
File or directory to analyze, defaults to current directory . |
|
--list-file |
Analyze exactly the files listed one-per-line in this file instead of scanning path; use - to read the list from stdin |
|
--include |
-i |
File glob pattern to include, can be specified multiple times |
--exclude |
-e |
File glob pattern to exclude, can be specified multiple times |
--exclude-dir |
Directory name to exclude at any depth (e.g. vendor); shorthand for --exclude "**/<name>/**", can be specified multiple times |
|
--include-lang |
Language display name to include (e.g. "C#"), matched case-insensitively; can be specified multiple times |
|
--exclude-lang |
Language display name to exclude, matched case-insensitively; can be specified multiple times | |
--unique |
Count byte-identical files only once; later duplicates are reported as skipped | |
--format |
-f |
Output format: Table (default), Json, Html, Csv, or Markdown |
--output |
-o |
Output file path for Json / Html / Csv / Markdown formats; use - to write to stdout; format is inferred from the file extension when --format is not specified |
--no-recursive |
Do not recurse into subdirectories | |
--no-health |
Hide the Comment Health column and percentage breakdowns | |
--by-file |
Show per-file details in addition to the language summary | |
--detailed |
In Json / Html / Markdown output, include both the language summary and the per-file breakdown. In Csv output it selects the language summary only (a single well-formed table) |
|
--paged |
-p |
Show paged output |
--all |
Include files with unknown extensions (grouped as Other) |
|
--quiet |
-q |
Suppress the banner, progress UI, and Saved to message |
--no-progress |
Suppress the live table and progress bar | |
--min-comment-pct |
Fail (exit code 2) if the overall comment percentage is below this value |
|
--jobs |
-j |
Max files to analyze in parallel (default: processor count; 1 = sequential) |
--no-gitignore |
Do not honor .gitignore files (they are respected by default) |
|
--follow-symlinks |
Include symlinked/junctioned directories and symlinked files instead of skipping them; a directory symlink that loops back to one of its own ancestors is still skipped | |
--baseline |
Compare against a previously saved JSON report and show the line-count diff | |
--sort |
Order the language summary by Total (default), Code, Comment, Blank, Files, or Name |
|
--top |
Show only the top N languages in the summary | |
--no-update-check |
Do not check GitHub for a newer release (checked by default, with a 2 second timeout) | |
--help |
-h |
Show help |
--version |
Show version |
Supported language display names (for --include-lang/--exclude-lang):
Assembly, Astro, BASIC, Batch, Bazel/Starlark, C, C#, C++, Clojure, CMake, Crystal, CSS, D, Dart, Dockerfile, Elixir, Elm, Erlang, F#, Go, GraphQL, Groovy, Haskell, HTML, INI, Java, JavaScript, JSON, Julia, Jupyter Notebook, Kotlin, Lua, Makefile, Markdown, MDX, Nim, Nix, Objective-C, OCaml, Pascal, Perl, PHP, PowerShell, Protobuf, Python, R, Ruby, Rust, Scala, SCSS/Less, Shell, Solidity, SQL, Svelte, Swift, Terraform, TOML, TypeScript, Visual Basic, Vue, XML, YAML, Zig
All non-table formats (Json, Html, Csv, Markdown) are written to stdout by default (so they can be piped, e.g. sloc . -f json | jq); pass --output <path> to write a file instead.
.gitignore files (including nested ones) are honored by default; pass --no-gitignore to disable. Save a JSON report and pass it to --baseline on a later run to see how line counts changed. Baseline diff output is only rendered as a console table or as JSON (-f json); other formats fall back to the table.
| Code | Meaning |
|---|---|
0 |
Success |
1 |
Path not found or unreadable, or invalid command-line arguments |
2 |
A threshold (e.g. --min-comment-pct) was not met |
3 |
Unexpected error |
With --by-file (tree view per file):
- Programming languages: C#, C, C++, Java, Kotlin, Swift, JavaScript, TypeScript, Python, Go, Rust, PHP, Ruby, F#, Visual Basic, Scala, Dart, R, Lua, Perl, Elixir, Haskell, Objective-C, Groovy, Julia, Clojure, BASIC, Pascal, Zig, Nim, OCaml, Erlang, Elm, D, Crystal, Solidity
- Web & templates: HTML, CSS, SCSS/Less, Vue, Svelte, Astro, MDX
- Data & config formats: JSON, YAML, XML, TOML, INI, Markdown, Protobuf, GraphQL
- Shell, build & infra: Shell, PowerShell, Batch, SQL, Makefile, Dockerfile, CMake, Terraform, Bazel/Starlark, Nix
- Other: Assembly, Jupyter Notebook
Files without an extension (e.g. Makefile, Dockerfile, CMakeLists.txt, Rakefile, Gemfile) are recognized by name.
Files with unknown extensions are grouped as
Otherwhen using--all, with only code lines and blank lines distinguished.
# Restore and build
dotnet build
# Run tests
dotnet test
# Pack as a NuGet tool package (output to ./nupkg)
dotnet pack src/Sloc.Cli/Sloc.Cli.csproj -c Release -o ./nupkg
# Install from local package and verify
dotnet tool install --global --add-source ./nupkg Sloc
sloc ./src- Line classification is based on text matching of comment symbols, not a full lexer.
- String literals are recognized for most languages, so comment markers inside strings (e.g.
"// not a comment") are counted as code, and escaped quotes are handled, including C# verbatim strings (@"…""…") and Rust raw strings (r"…",r#"…"#). Rust raw strings with more than one#are not modeled, and interpolation expressions inside strings are not analyzed. - Python triple-quoted strings are counted as comments only when they begin a statement (docstrings); used as a value (e.g.
x = """…""") they are counted as code.
This project is released under the MIT License.
Sloc(Source Lines Of Code)是一个用于统计源代码行数的 .NET 全局命令行工具。它会逐文件分析代码,区分代码行、注释行和空行,并按编程语言进行聚合汇总,支持 63 种语言自动识别、五种输出格式(表格、JSON、HTML、CSV、Markdown)、逐文件明细视图以及注释健康度指标。
- 统计代码行 / 注释行 / 空行 / 总行数
- 正确处理单行注释、块注释以及跨多行的块注释
- 内置 63 种常见语言的注释规则(按文件扩展名或文件名自动识别,如
Makefile、Dockerfile、CMakeLists.txt) - 递归扫描目录,支持
--include/--excludeglob 过滤 - 默认排除
bin、obj、artifacts、.git、.vs、.vscode、.idea、node_modules等目录 - 五种输出格式:彩色表格(默认)、JSON、HTML、CSV 与 Markdown
- 表格输出新增注释健康度列,显示注释密度指标(无 / 低 / 一般 / 良好 / 较高 / 过密)
- 未指定
--format时,可根据--output文件扩展名自动推断格式(.json→ JSON,.html/.htm→ HTML) - 默认遵循
.gitignore文件(含子目录中的);--no-gitignore可禁用 - 跨 CPU 核心并行分析(
--jobs),输出保持确定性 - 适配 CI:JSON 可输出到标准输出便于管道处理(例如
| jq)、提供有意义的退出码、以及--min-comment-pct阈值门禁 - 通过
--baseline与已保存的 JSON 报告对比,查看行数变化 - 通过
--sort/--top对语言汇总排序和限制条数 - 无法读取的文件或目录,以及二进制文件(通过 NUL 字节检测),会被自动跳过,并在最终结果中列出所有跳过的路径及原因(除
Csv外的所有格式;CSV 保持为单张可机器解析的表格)
通过 winget 安装(Windows):
winget install coldhighsun.sloc或作为 .NET 全局工具安装(需要 .NET 8 SDK):
dotnet tool install --global Sloc更新或卸载:
winget upgrade coldhighsun.sloc
winget uninstall coldhighsun.sloc
dotnet tool update --global Sloc
dotnet tool uninstall --global Slocsloc <path> [options]# 统计当前目录(递归)
sloc
# 统计指定目录
sloc ./src
# 统计单个文件
sloc ./src/Program.cs
# 仅统计 C# 文件
sloc ./src --include "**/*.cs"
# 排除测试目录
sloc . --exclude "**/tests/**"
# 显示逐文件明细
sloc ./src --by-file
# 以 JSON 格式输出
sloc ./src --format json
# 保存为 HTML 报告(可在浏览器中打开)
sloc ./src --format html --output report.html
# HTML 输出到标准输出(省略 --output 时的默认行为)
sloc ./src --format html
# 根据文件扩展名自动推断格式
sloc ./src --output sloc-report.json
# 包含未知扩展名的文件
sloc . --all
# 不递归子目录
sloc ./src --no-recursive
# 将 JSON 通过管道传给 jq
sloc . --format json | jq .total
# 若注释占比低于 10% 则让 CI 失败
sloc . --min-comment-pct 10
# 保存基线,之后与后续运行对比
sloc . --format json --output baseline.json
sloc . --baseline baseline.json
# 按注释行排序,仅显示前 5 种语言
sloc . --sort comment --top 5
# 生成同时包含语言汇总和逐文件明细的 Markdown 报告,输出到标准输出
sloc . --format markdown --detailed -o -| 选项 | 简写 | 说明 |
|---|---|---|
path(参数) |
要分析的文件或目录,默认为当前目录 . |
|
--list-file |
分析该文件中逐行列出的文件列表,而不是扫描 path;用 - 表示从标准输入读取列表 |
|
--include |
-i |
要包含的文件 glob 模式,可多次指定 |
--exclude |
-e |
要排除的文件 glob 模式,可多次指定 |
--exclude-dir |
要在任意深度排除的目录名(如 vendor);等价于 --exclude "**/<name>/**",可多次指定 |
|
--include-lang |
要包含的语言显示名称(如 "C#"),大小写不敏感匹配;可多次指定 |
|
--exclude-lang |
要排除的语言显示名称,大小写不敏感匹配;可多次指定 | |
--unique |
内容字节完全相同的文件只计一次;后出现的重复文件计入跳过列表 | |
--format |
-f |
输出格式:Table(默认)、Json、Html、Csv 或 Markdown |
--output |
-o |
Json / Html / Csv / Markdown 格式的输出文件路径;用 - 表示写到标准输出;未指定 --format 时根据文件扩展名自动推断格式 |
--no-recursive |
不递归扫描子目录 | |
--no-health |
隐藏注释健康度列及百分比数据 | |
--by-file |
在语言汇总之外额外显示逐文件明细 | |
--detailed |
在 Json / Html / Markdown 输出中同时包含语言汇总和逐文件明细;在 Csv 输出中仅选择语言汇总(保持单张规范表格) |
|
--paged |
-p |
显示分页输出 |
--all |
包含扩展名未知的文件(归入 Other) |
|
--quiet |
-q |
抑制横幅、进度 UI 和 Saved to 提示 |
--no-progress |
抑制实时表格和进度条 | |
--min-comment-pct |
若整体注释占比低于该值,则失败(退出码 2) |
|
--jobs |
-j |
并行分析的最大文件数(默认为处理器核数;1 表示串行) |
--no-gitignore |
不遵循 .gitignore 文件(默认遵循) |
|
--follow-symlinks |
包含符号链接/联接目录以及符号链接文件,而不是跳过它们;指向自身祖先目录的循环链接目录仍会被跳过 | |
--baseline |
与之前保存的 JSON 报告对比,显示行数增减 | |
--sort |
语言汇总排序依据:Total(默认)、Code、Comment、Blank、Files 或 Name |
|
--top |
仅显示汇总中排名前 N 的语言 | |
--no-update-check |
不检查 GitHub 上是否有新版本(默认检查,超时时间为 2 秒) | |
--help |
-h |
显示帮助 |
--version |
显示版本 |
支持的语言显示名称(用于 --include-lang/--exclude-lang):
Assembly, Astro, BASIC, Batch, Bazel/Starlark, C, C#, C++, Clojure, CMake, Crystal, CSS, D, Dart, Dockerfile, Elixir, Elm, Erlang, F#, Go, GraphQL, Groovy, Haskell, HTML, INI, Java, JavaScript, JSON, Julia, Jupyter Notebook, Kotlin, Lua, Makefile, Markdown, MDX, Nim, Nix, Objective-C, OCaml, Pascal, Perl, PHP, PowerShell, Protobuf, Python, R, Ruby, Rust, Scala, SCSS/Less, Shell, Solidity, SQL, Svelte, Swift, Terraform, TOML, TypeScript, Visual Basic, Vue, XML, YAML, Zig
所有非表格格式(Json、Html、Csv、Markdown)默认都会输出到标准输出(便于管道处理,例如 sloc . -f json | jq);传入 --output <路径> 则写入文件。
默认遵循 .gitignore 文件(含子目录中的);传入 --no-gitignore 可禁用。先保存一份 JSON 报告,之后用 --baseline 传入即可查看行数变化。baseline 差异仅支持控制台表格或 JSON(-f json)输出;其它格式会回退为表格。
| 码 | 含义 |
|---|---|
0 |
成功 |
1 |
路径不存在或不可读,或命令行参数无效 |
2 |
未达到阈值(如 --min-comment-pct) |
3 |
意外错误 |
使用 --by-file 选项(按文件树形展示):
- 编程语言:C#、C、C++、Java、Kotlin、Swift、JavaScript、TypeScript、Python、Go、Rust、PHP、Ruby、F#、Visual Basic、Scala、Dart、R、Lua、Perl、Elixir、Haskell、Objective-C、Groovy、Julia、Clojure、BASIC、Pascal、Zig、Nim、OCaml、Erlang、Elm、D、Crystal、Solidity
- 前端与模板:HTML、CSS、SCSS/Less、Vue、Svelte、Astro、MDX
- 数据与配置格式:JSON、YAML、XML、TOML、INI、Markdown、Protobuf、GraphQL
- 脚本、构建与基础设施:Shell、PowerShell、Batch、SQL、Makefile、Dockerfile、CMake、Terraform、Bazel/Starlark、Nix
- 其他:Assembly、Jupyter Notebook
无扩展名的文件(如 Makefile、Dockerfile、CMakeLists.txt、Rakefile、Gemfile)按文件名识别。
扩展名未知的文件在使用
--all时会被归入Other类别,仅区分代码行与空行。
# 还原与构建
dotnet build
# 运行测试
dotnet test
# 打包为 NuGet 工具包(输出到 ./nupkg)
dotnet pack src/Sloc.Cli/Sloc.Cli.csproj -c Release -o ./nupkg
# 从本地包安装并验证
dotnet tool install --global --add-source ./nupkg Sloc
sloc ./src- 行的分类基于注释符号的文本匹配,不是完整的词法分析器。
- 大多数语言已识别字符串字面量,因此字符串内部的注释符号(例如
"// 这不是注释")会被计为代码,转义引号也能正确处理,包括 C# 逐字字符串(@"…""…")和 Rust 原始字符串(r"…"、r#"…"#)。带多个#的 Rust 原始字符串暂不支持,字符串内的插值表达式也不做分析。 - Python 三引号字符串仅在作为语句开头(docstring)时计为注释;作为值使用时(例如
x = """…""")计为代码。
本项目基于 MIT 许可证 发布。

