mori

module
v0.7.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 8, 2026 License: MIT

README

Mori

CI

Mori finds source fragments that look alike, including functions written in different programming languages and top-level SQL queries.

Use it to find possible duplicate logic before you copy, refactor, or review code. Mori gives you a shortlist to inspect. It cannot prove that two functions or queries do the same thing.

What It Does

Mori reads your source code locally and compares individual functions or SQL queries within compatible comparison domains. It ignores details such as formatting, comments, most variable names, and literal values so it can focus on structural shape.

For example, it can flag a JavaScript function and a Go function that both:

  • check an input;
  • split it into parts;
  • loop over those parts; and
  • return early when something is wrong.

Each result groups every retained source occurrence with the same normalized content-pair identity. It includes a percentage, a shared-shape summary, and the code locations to review. A higher percentage means the functions have more structural overlap, not that they have identical behavior.

Install

Download a prebuilt binary for Linux, macOS, or Windows from the latest release.

Or install from source. You need Go 1.23 or newer and a C compiler.

go install github.com/Cyberlane/mori/cmd/mori@latest
mori version

Source-built installations can report the module version while leaving the source revision and date as unknown when Go does not embed VCS settings. They remain suitable for exploratory local review, but use an official release binary when a report needs complete, independently verifiable provenance.

Start Here

Run this from the root of a project:

mori scan --threshold 0.85 --min-tokens 40 .

This looks for reasonably sized functions that are very similar. Start at 0.85 to reduce noise. If you want more possible matches, lower the threshold gradually.

To look only for matches between different languages:

mori scan --cross-language-only --threshold 0.65 .

TypeScript and TSX are one language family. To compare only Go with that family, use:

mori scan --language-pair go,typescript --threshold 0.65 .

To try Mori against this repository's example files:

mori scan --threshold 0.70 --cross-language-only examples/email-validation

Example output:

1. 71.0% structural similarity · 1 location pair(s)
   A  fingerprint 1d4f4194cc92c56c · 1 occurrence(s)
      - validator.go:5-8  [go] LooksLikeEmail
   B  fingerprint 6d2ab0d68af9fb96 · 1 occurrence(s)
      - validator.js:1-4  [javascript] looksLikeEmail
      shared shape: 3 calls, 1 return, 1 binding

Read both fragments before acting on a match. Mori does not understand runtime values, external calls, side effects, query plans, schemas, or all language-specific behavior.

To review structurally similar SQL queries:

mori scan --threshold 0.70 --min-tokens 12 examples/sql-queries

SQL queries are compared only with SQL queries, never with code functions. Mori extracts top-level SELECT and set-operation queries plus INSERT, UPDATE, and DELETE statements. It uses exact, immediately adjacent SQLC -- name: Name :mode comments for display names and otherwise reports query@<line>. DDL and nested queries are not independent comparison units; nested query structure remains part of its top-level query. Common SQLite and SQLC pagination parameters and SQLite ON CONFLICT column targets are parsed without weakening diagnostics for malformed nearby syntax.

Common Uses

Mori honors nested .gitignore and .moriignore files during directory scans. An explicitly requested file is still scanned. Add command-line exclusions for additional policy:

mori scan --exclude '**/*_test.go' --exclude '**/*.test.ts' .

Store repeatable project settings in .mori.json:

{
  "threshold": 0.85,
  "min_tokens": 40,
  "max_groups": 250,
  "language_pairs": ["go,typescript"],
  "exclude": ["**/*_test.go"]
}

Mori searches the current directory and its parents for .mori.json. Use --config <path>, --no-config, or --no-ignore to control discovery. See Project configuration for the complete contract.

Write results as JSON for a script or CI system:

mori scan --format json .

Schema-5 reports embed deterministic tool build provenance, comparison domain and fragment-kind metadata, and exact focus metadata. They do not include a scan timestamp, hostname, username, source body, diff, or Git remote.

Fail a CI job when Mori finds a match at your threshold:

mori scan --threshold 0.85 --fail-on-match .

With --fail-on-match, Mori exits with status 3 when it finds a match.

For change review, keep the full repository comparison universe while putting groups that touch changed files first:

mori scan --changed-since origin/main --threshold 0.85 .

The revision must already exist locally. Mori uses the merge base through the current working tree, including staged, unstaged, and untracked non-ignored files; it never fetches a remote. Add repeatable --focus-path <path> values for explicit paths. --fail-on-focused-match exits with status 3 only when an unsuppressed focused group exists and is mutually exclusive with --fail-on-match.

To record intentional candidates and use Mori as a stable CI gate:

mori baseline update --baseline mori-baseline.json --threshold 0.85 .
mori scan --baseline mori-baseline.json --threshold 0.85 --fail-on-match .
mori baseline prune --baseline mori-baseline.json --check .

baseline update accepts every candidate in the current untruncated scan, so review its file diff before committing it. Baselines are opt-in, and a suppressed candidate is reported as both a content-identity count and a location-pair count. The default content scope follows identical normalized content into new locations. Use baseline update --baseline-scope path when a copy in a new file must appear for review. The conventional file name is mori-baseline.json; pass it explicitly with --baseline.

Supported Languages

Parser language Review family Comparison domain File types
Go Go code .go
JavaScript and JSX JavaScript code .js, .jsx, .mjs, .cjs
TypeScript TypeScript code .ts, .mts, .cts
TSX TypeScript code .tsx
Python Python code .py, .pyi
Rust Rust code .rs
SQL queries SQL sql-query .sql

Run mori languages to see the languages in your installed version.

Known Parser Limits

Tree-sitter recovery is visible in report warnings, and any comparison fragment containing a parse error is skipped. SQL dialect extensions outside Mori's pinned grammar and Mori's bounded SQLite/SQLC adaptations may therefore produce diagnostics or incomplete coverage. Mori also applies a bounded, byte-preserving repair for recognized cases of the upstream raw-ampersand JSX text grammar issue. Other JavaScript and TSX parse errors remain visible and invalidate affected function fragments.

For AI Coding Tools

Mori includes an optional skill for compatible coding agents. It helps an agent use Mori results as review leads rather than treating a score as proof.

Install it in the current project:

mori skill install --project .

Install it for your user account instead:

mori skill install --global

More Detail

Development

make check

License

Mori is available under the MIT License.

Directories

Path Synopsis
cmd
mori command
examples
internal
agentskill
Package agentskill installs Mori's embedded Agent Skill safely and deterministically.
Package agentskill installs Mori's embedded Agent Skill safely and deterministically.
analyzer
Package analyzer orchestrates parsing, comparison, and deterministic results.
Package analyzer orchestrates parsing, comparison, and deterministic results.
baseline
Package baseline stores reviewed-and-accepted Mori match candidates.
Package baseline stores reviewed-and-accepted Mori match candidates.
buildinfo
Package buildinfo holds immutable build provenance from linker flags or Go module build information.
Package buildinfo holds immutable build provenance from linker flags or Go module build information.
cli
Package cli implements the mori command-line interface.
Package cli implements the mori command-line interface.
cmd/releasepack command
Command releasepack creates one native release archive.
Command releasepack creates one native release archive.
cmd/skillpack command
Command skillpack creates Mori's portable Agent Skill release archive.
Command skillpack creates Mori's portable Agent Skill release archive.
config
Package config loads Mori's strict project scan configuration.
Package config loads Mori's strict project scan configuration.
diagnostic
Package diagnostic formats errors without exposing private filesystem paths.
Package diagnostic formats errors without exposing private filesystem paths.
fingerprint
Package fingerprint creates stable content identities for normalized fragments and pairs of fragments.
Package fingerprint creates stable content identities for normalized fragments and pairs of fragments.
language
Package language owns supported Tree-sitter grammars and fragment boundaries.
Package language owns supported Tree-sitter grammars and fragment boundaries.
model
Package model defines the analyzer's stable internal and output models.
Package model defines the analyzer's stable internal and output models.
normalize
Package normalize converts grammar-specific trees into shared feature bags.
Package normalize converts grammar-specific trees into shared feature bags.
parser
Package parser turns supported source files into normalized fragments.
Package parser turns supported source files into normalized fragments.
release
Package release creates deterministic native release archives.
Package release creates deterministic native release archives.
report
Package report renders stable machine-readable and human-readable reports.
Package report renders stable machine-readable and human-readable reports.
similarity
Package similarity scores normalized AST feature bags.
Package similarity scores normalized AST feature bags.
source
Package source discovers supported source files without following symlinks.
Package source discovers supported source files without following symlinks.
vcs
Package vcs resolves bounded, local version-control state for review focus.
Package vcs resolves bounded, local version-control state for review focus.
Package skills embeds the official Agent Skills distributed with Mori.
Package skills embeds the official Agent Skills distributed with Mori.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL