GV

GeezerVison

The World Wide Web, restored to 800 pixels of glory.

Home|About|Gaming cabinet|Archives|How it works|Starter sites

On this site

  • Sign in
  • ActionsCI/CD and automation
  • CodespacesCloud development environments
  • All Features
  • Documentation
  • Training
  • Certifications
  • Build with Copilot
  • Customize Copilot
  • Integrations
  • Trending repos
  • GitHub Sponsors
  • Developer articles
  • Enterprises

This view

  • Original page
  • New address

GeezerVison is showing github.com โ€” GitHub - codeAesthetic/twinscope: Compare anything. Understand what changed. A local-first desktop diff tool for files, folders, JSON and images. Docs: https://codeaesthetic.github.io/twinscope-website/

BranchesTags
Open more actions menu

Latest commit

 

History

87 Commits
87 Commits

Folders and files

NameName
Last commit message
Last commit date
.github/workflows
.github/workflows
 
 
build
build
 
 
docs
docs
 
 
e2e
e2e
 
 
integrations
integrations
 
 
scripts
scripts
 
 
src
src
 
 
.gitignore
.gitignore
 
 
.nvmrc
.nvmrc
 
 
.prettierignore
.prettierignore
 
 
.prettierrc.json
.prettierrc.json
 
 
CHANGELOG.md
CHANGELOG.md
 
 
LICENSE
LICENSE
 
 
README.md
README.md
 
 
electron-builder.yml
electron-builder.yml
 
 
electron.vite.config.ts
electron.vite.config.ts
 
 
eslint.config.mjs
eslint.config.mjs
 
 
package-lock.json
package-lock.json
 
 
package.json
package.json
 
 
playwright.capture.config.ts
playwright.capture.config.ts
 
 
playwright.config.ts
playwright.config.ts
 
 
tsconfig.base.json
tsconfig.base.json
 
 
tsconfig.e2e.json
tsconfig.e2e.json
 
 
tsconfig.json
tsconfig.json
 
 
tsconfig.node.json
tsconfig.node.json
 
 
tsconfig.web.json
tsconfig.web.json
 
 
vite.cli.config.ts
vite.cli.config.ts
 
 
vitest.config.ts
vitest.config.ts
 
 

Repository files navigation

TwinScope

Compare anything. Understand what changed.

๐Ÿ“– Documentation ยท Download ยท Changelog

A local-first universal comparison tool for developers. Drop two files, folders, images or clipboard contents โ€” TwinScope detects what they are, picks the right diff engine, and shows what changed.

Your files never leave your machine: no telemetry, no uploads, no account.

Status: 0.3.9 released. Sixteen engines, a twinscope command line, projects, saved comparisons, shareable reports and an opt-in update check. 0.3.9 is a fix release over 0.3.8, whose macOS and Linux arm64 builds compare real PDFs as binaries โ€” take 0.3.9 if you compare PDFs. The macOS builds are unsigned โ€” macOS will refuse to open the app until you right-click โ†’ Open โ†’ Open. See docs/release.md and the install guide.

Structural JSON comparison


What it does

Text and code Side-by-side, unified and inline. Edited lines pair up and are marked word by word rather than appearing as unrelated deletes and adds. Long unchanged runs fold.
JSON A structural tree, not a line diff โ€” reformat a file and nothing changes. Arrays match by identity, objects compare as key sets, type changes get their own row.
Folders Recursive, with per-file status, rename pairing, filters, and drill-in to any file pair.
Images Side-by-side, overlay, blink and difference, with changed regions boxed and an adjustable threshold.
Binary A verdict from sizes and a SHA-256, instead of pages of mojibake.

Every comparison opens with counts, then the detail. Normalisation is explainable and reversible: anything hidden is counted, named, and one click from coming back.

More screenshots

Text diff Folder comparison Image comparison Command palette


Requirements

Node 24 (LTS) โ€” nvm use picks it up from .nvmrc
npm 11+ (ships with Node 24)
OS macOS, Windows or Linux. macOS is the primary development target.

Getting started

nvm use          # or: nvm install 24
npm install      # postinstall also fetches the Electron binary
npm run dev      # opens the app with hot reload

That's the whole setup. If npm run dev complains that Electron is missing, re-run npm install โ€” see Troubleshooting.

Scripts

Command What it does
npm run dev Electron + Vite with hot reload
npm run build Production build into out/
npm run verify Builds, boots the app, and checks it really works (Playwright)
npm run typecheck TypeScript across three projects: main/preload, renderer, e2e
npm test Unit tests (vitest)
npm run lint ESLint, including the import-boundary rules
npm run format Prettier
npm run gate Everything above, in the order CI runs it
npm run package:mac Builds release/TwinScope-<version>.dmg
npm run verify:packaged Boots the packaged app and compares in it
npm run icon Regenerates build/icon.png from scripts/make-icon.mjs

Layout

src/
โ”œโ”€โ”€ main/       Electron main process โ€” windows, security, IPC
โ”œโ”€โ”€ preload/    the only bridge between renderer and main
โ”œโ”€โ”€ renderer/   React UI
โ”œโ”€โ”€ shared/     cross-process contracts (channel names, types)
โ””โ”€โ”€ engines/    comparison engines โ€” pure logic, no Electron, no DOM
e2e/            verification harness (see below)

Three boundaries are enforced by ESLint rather than convention:

  • The renderer cannot import node:* or electron. It talks to the main process only through window.twinscope, exposed by the preload script.
  • Engines cannot import electron, so the planned CLI can reuse them unchanged.
  • src/shared/channels.ts stays dependency-free, because the sandboxed preload imports it.

Verifying changes

npm run verify is a harness, not a test suite. It builds the app, boots it in Electron, and gives you a real page to drive:

const harness = await launchApp();
await harness.page.getByTestId('โ€ฆ').click();
await harness.screenshot('what-i-changed');
expect(harness.errors).toEqual([]);

Screenshots land in e2e/.artifacts/screenshots/. Keep e2e/verify.spec.ts small โ€” its security assertions are permanent; for one-off checks, write a throwaway spec and delete it after.

Security posture

The renderer is treated as untrusted. src/main/security.ts enables the sandbox and context isolation, disables node integration, sets a Content-Security-Policy, and denies navigation, new windows, <webview> embedding and every permission request. npm run verify asserts these hold โ€” a regression there is a remote-code-execution bug, not a UI bug.

Troubleshooting

"Electron failed to install correctly" / no window opens. npm gates dependency install scripts, so Electron's own postinstall never runs and the binary is missing. scripts/ensure-electron.mjs handles this from the root postinstall; run npm install, or node scripts/ensure-electron.mjs directly.

Don't bump Vite past 7 or TypeScript past 6.0. electron-vite peers on Vite ^5 || ^6 || ^7, and typescript-eslint peers on TypeScript <6.1.0 โ€” TypeScript 7 is the native compiler and has no lint support yet. These are the newest versions the whole toolchain agrees on.

License

MIT

Documentation

Full documentation lives at codeaesthetic.github.io/twinscope-website โ€” every engine, every keyboard shortcut, what is stored and what never is, and a screenshot or GIF of each feature captured from the running app.

Its source is codeAesthetic/twinscope-website. The screenshots are produced from this repo by npm run capture, so re-run it after any UI change rather than editing images by hand.

About

Compare anything. Understand what changed. A local-first desktop diff tool for files, folders, JSON and images. Docs: https://codeaesthetic.github.io/twinscope-website/

codeaesthetic.github.io/twinscope-website/

Topics

clideveloper-toolsdiffdiff-toolelectronjson-difflocal-firstpdf-difftypescriptvisual-regression

Resources

Readme
MIT license
Activity

Stars

12 stars

Watchers

0 watching

Forks

0 forks
Report repository

Releases

Packages

Contributors

Languages

You are visitor 01402503 โ€” GeezerVison does not store the pages you look up.
Best viewed with Netscape Navigator 4.7 or Internet Explorer 6 at 800ร—600. No cookies required.