GoodwattleBook a friendly call (opens in a new tab)

REPO PROVENANCE CHECK

Your repository, by the numbers.

A single file you run inside your repository. It counts history, reviewed pull requests, tests, third-party code, licences, secrets and personal information, then writes a short JSON report. Paste the report below to see how it lines up with what our buyers need.

Download the script

Download and read it

One file, no packages to install. Needs Node.js 20 or later and git. It’s plain JavaScript, so please read it before you run it.

Version 1.0.0 · SHA-256 399dc686b28d1443f3e9e55c67578ba7ac301aeddea89ddff100b54828dfd8f3. Check your copy with shasum -a 256 goodwattle-check.mjs.

Run it in your repository

Run it in a full clone

From the repository folder. It writes goodwattle-report.json where you run it and prints a summary.

cd path/to/your-repository
node ~/Downloads/goodwattle-check.mjs

To count human-reviewed pull requests, give it a read-only token through the environment. With the GitHub CLI:

GITHUB_TOKEN="$(gh auth token)" node ~/Downloads/goodwattle-check.mjs --github-token

For GitLab, create a personal access token with the read_api scope and use GITLAB_TOKEN=… node goodwattle-check.mjs --gitlab-token. Add --gitlab-url=https://gitlab.example.com for a self-managed instance, and --name=alias if you’d rather not share the folder name. Run with --help for every option.

Paste the report

Paste the report for a readout

Open goodwattle-report.json, check you’re happy with what’s in it, then paste it here or choose the file. It’s read in this page only.

The report stays in this page. We don’t upload or save it.

What each field means

Everything in the report is a count, a date, a share or a file path. The script reads file contents to count things, then forgets them.

History

commits_all_branches
Commits reachable from every branch and tag. Buyers want working history, not one squashed snapshot.
human_authors · bot_authors
Distinct author emails (after .mailmap), split into people and bots such as Dependabot. Names and emails are not included.
first_commit_date · last_commit_date
The span of the history, plus active_months with at least one commit.
root_commits · shallow_clone
More than one starting point suggests merged-in history; a shallow clone means older history is missing, so run it on a full clone.
commits_with_ai_assistant_trailers
Commits signed by an AI coding assistant (for example a Co-authored-by trailer). It only catches tools that sign their commits.

Pull and merge requests

merged_from_commit_patterns
Distinct request numbers in merge and squash commit messages from GitHub, GitLab, Bitbucket and Azure DevOps. It can undercount (rebase merges leave no trace) and says nothing about reviews.
human_reviewed
Only with a token. Merged requests with at least one review, approval or comment from a person other than the author, excluding bots. Also reports whether the host says the repository is private or a fork.

Files

test_to_source_ratio
Test files divided by other source files, using common naming conventions (tests/, *.test.ts, *_test.go, FooTest.java and so on), ignoring vendored and generated code.
vendored · generated share_of_bytes
How much of the repository is third-party or machine-made, from paths like vendor/, ThirdParty/, dist/, lockfiles and .min.js, linguist- attributes and “do not edit” headers. Top folders are listed.
first_party_source_lines
Lines in your own source files, by language.

Licences

licence_files
Paths of LICENSE, LICENCE and COPYING files and the licence family each looks like.
spdx_identifiers
Counts of SPDX-License-Identifier tags near the top of files.
copyleft_paths
Files carrying GPL, AGPL, LGPL, MPL or EPL markers. Usually third-party code that can be left out, but worth knowing early.

Clean-up before any delivery

pattern_matches
Likely secrets: private keys, cloud and API keys, tokens, webhook URLs, connection strings and hard-coded passwords. Counts and paths only, never the value. Rotate anything real.
high_entropy_strings
Long random-looking strings that might be keys. Many are harmless hashes or IDs.
emails · phone_numbers
Personal email addresses and Australian or New Zealand phone numbers in your own files. Example and no-reply addresses are ignored.
au_tax_file_numbers · nz_ird_numbers
Numbers in TFN or IRD format that also pass the official checksum.

The seal

integrity
A SHA-256 of the rest of the report in a fixed, sorted form. The readout recomputes it to show whether the report was edited after it was made. It catches accidental edits; it isn’t a signature.

How the readout scores it

The readout is an illustrative first look against the screen our buyers use today. It isn’t diligence, a rights check or an offer, and briefs change.

ScreenMeetsGap or unknownOutside
250+ human-reviewed PRs250 or more with a tokenFewer, or not checked—
Intact git history20+ commits, one root, full cloneSeveral roots or an upstream remoteShallow clone or under 20 commits
Private, never publicPrivate on the hostNot checkedPublic or a fork
Owned rightsNo licence files or copyleft markersOpen-source licence file or copyleft markers—
Mostly human-authored10% or fewer commits with AI trailersOver 10%Over half, or no human authors
Never licensed for AIOnly you can say. Tell us in your overview.

Secrets and personal information never rule a repository out. They’re listed so they can be rotated, removed or redacted before anything is supplied.

Limits worth knowing

  • Path and pattern heuristics miss some things and flag others wrongly. Treat the counts as a starting point.
  • Secrets and personal information are scanned in files at your current checkout, not in older commits.
  • Files over 2 MB and binary files are counted but not read.
  • Tokens are only sent to your code host, in read-only queries, and are never written to the report or the screen.

Never share the report if you’re not comfortable with it. It contains file paths, a commit hash and counts. Use --name to replace the folder name, and edit or delete anything you’d rather keep private (the readout will show the hash no longer matches, which is fine).