Skip to main content

JSON editor with vim-style keybindings

Project description

jvim

JSON editor with vim-style keybindings, built with Textual.

한국어

Screenshots

Editor

jvim

Diff Viewer

jvimdiff

Features

  • Vim-style modal editing - Normal, Insert, Command, and Search modes
  • Syntax highlighting - JSON-aware colorization
  • JSON validation - Real-time validation with error reporting
  • JSONPath search - Search using JSONPath expressions ($.foo.bar)
  • JSONL support - Edit JSON Lines files with smart formatting
  • Embedded JSON editing - Edit JSON strings within JSON with nested level support
  • Visual mode - Character-wise (v) and line-wise (V) selection with d/y/c operators
  • Folding - Collapse/expand JSON blocks and long string values
  • Bracket matching - Jump to matching brackets with %
  • Undo/Redo - Full undo history
  • Substitute - Vim-style :s/old/new/g with regex, range, and flags support

Installation

pip install jvim

Usage

# Open a file
jvim data.json

# Open in read-only mode
jvim -R data.json

# Create new file
jvim newfile.json

Also available as jvi and jv shortcuts.

JSONL Support

jvim provides special handling for JSON Lines (.jsonl) files:

  • Pretty-printed editing: Each JSONL record is automatically formatted with indentation for easy reading and editing
  • Compact saving: When you save, each record is minified back to a single line, preserving the JSONL format
  • Record numbers: A second column shows the record number (1, 2, 3...) for easy navigation
  • Floating header: When scrolling through a multi-line record, the physical line number stays visible at the top

Example: A JSONL file with two records:

{"name": "Alice", "age": 30}
{"name": "Bob", "age": 25}

Opens in jvim as:

{
    "name": "Alice",
    "age": 30
}
{
    "name": "Bob",
    "age": 25
}

And saves back to the original compact format.

JSONPath Search

jvim supports powerful JSONPath searching with value filtering.

Basic JSONPath

Search patterns starting with $. or $[ are automatically recognized as JSONPath:

/$.name              # Find the "name" field
/$..email            # Find all "email" fields (recursive)
/$.users[0]          # First user
/$.users[*].name     # All user names

Value Filtering

You can filter search results by value using comparison operators:

Operator Description Example
= Equals $.status="active"
!= Not equals $.status!=null
> Greater than $.age>18
< Less than $.price<100
>= Greater or equal $.count>=5
<= Less or equal $.count<=10
~ Regex match $.email~@gmail\.com$

Examples

/$.users[*].age>30           # Users older than 30
/$.items[*].status="active"  # Items with active status
/$..name~^J                  # All names starting with J
/$.price<=1000               # Price 1000 or less
/$.config.enabled=true       # Enabled configs

Search Modifiers

Suffix Description
\j Force JSONPath mode for ambiguous patterns
\c Case insensitive (for regex text search)
\C Case sensitive (for regex text search)

History

Search and command history is automatically saved to ~/.jvim/history.json and restored on next launch. Use arrow keys (/) to navigate history in search (/) and command (:) modes.

Embedded JSON Editing

JSON files often contain escaped JSON strings as values. jvim lets you edit these nested JSON structures naturally.

How it works

  1. Position your cursor on a line containing a JSON string value
  2. Type ej in normal mode
  3. A new editor panel opens with the parsed and formatted JSON
  4. Edit the embedded JSON with full syntax highlighting and validation
  5. Save with :w to update the parent document (minified) or :q to cancel

Nested levels

You can edit embedded JSON within embedded JSON:

  • The panel title shows the current nesting level: Edit Embedded JSON (level 1)
  • A [+] indicator appears when you have unsaved changes
  • :w saves to the parent document and continues editing
  • :wq saves and returns to the previous level
  • :q! discards changes and returns to the previous level

Example

Given this JSON:

{
    "config": "{\"host\": \"localhost\", \"port\": 8080}"
}

Using ej on the config line opens:

{
    "host": "localhost",
    "port": 8080
}

After editing and saving, the parent is updated with the minified result.

Substitute

jvim supports vim-style substitute commands for find-and-replace.

Command Description
:s/old/new/ Replace first match on current line
:s/old/new/g Replace all matches on current line
:%s/old/new/g Replace all matches in entire file
:N,Ms/old/new/g Replace all matches in lines N to M

Features

  • Custom delimiters - Use any character as delimiter: :s#old#new#g, :s|old|new|g
  • Flags - g (global/all matches), i (case insensitive)
  • Regex support - Full regular expressions with group capture (\1, \2)
  • Undo - All substitutions can be undone with u

Examples

:s/foo/bar/           # Replace first "foo" with "bar" on current line
:%s/TODO/DONE/g       # Replace all "TODO" with "DONE" in file
:s/(\w+)/[\1]/g       # Wrap each word in brackets
:%s/old/new/gi        # Case-insensitive replace in entire file
:2,10s/from/to/g      # Replace in lines 2 through 10

JSONPath Substitute

When the find pattern starts with $. or $[, substitute operates on JSON structure. The trailing = determines the mode:

Pattern Mode Description
:s/$.key/newkey/g Key rename Rename JSON keys
:s/$.key=/value/g Value replace Replace all values at path
:s/$.key="old"/new/g Filtered value Replace values matching filter

Key rename

:s/$.name/username/g             # Rename "name" key to "username"
:s/$..name/label/g               # Rename all "name" keys recursively

Value replace

:s/$.name=/Bob/g                 # Replace "name" value with "Bob"
:s/$..status=/active/g           # Replace all "status" values recursively
:s/$.users[*].age=/0/g          # Reset all user ages to 0
:s/$..enabled=/true/g            # Set all "enabled" to true
:s/$..status="draft"/review/g   # Replace only "draft" statuses (filter)

Replacement values are auto-detected: numbers (42), booleans (true/false), null stay as-is; everything else is JSON-encoded as a string.

Keybindings

Use :help inside jvim to see the full keybinding reference.

License

MIT

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

jvim-0.4.0.tar.gz (186.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

jvim-0.4.0-py3-none-any.whl (48.7 kB view details)

Uploaded Python 3

File details

Details for the file jvim-0.4.0.tar.gz.

File metadata

  • Download URL: jvim-0.4.0.tar.gz
  • Upload date:
  • Size: 186.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.2

File hashes

Hashes for jvim-0.4.0.tar.gz
Algorithm Hash digest
SHA256 6c5287a457bdd7efe9533e95b9f0167ff531f37a04feb8b10d999d20453a5e52
MD5 c7bfedb8d8dd163ea9e0bf85c91944a7
BLAKE2b-256 e39a1c11e77a131b9fc8fc6acbac951ac1d8a3c12f83d6ee27d3d36fd24b2582

See more details on using hashes here.

File details

Details for the file jvim-0.4.0-py3-none-any.whl.

File metadata

  • Download URL: jvim-0.4.0-py3-none-any.whl
  • Upload date:
  • Size: 48.7 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.2

File hashes

Hashes for jvim-0.4.0-py3-none-any.whl
Algorithm Hash digest
SHA256 9f88a494fd03642c71374cbe838014fc79cd61699fccfb080e0a5d75895588a9
MD5 7d3446be4ecf730d8c494f01779a868a
BLAKE2b-256 dd357459a39add2a8623f582f7ea120ef430f5465af3ccd39268d3d5f1a708d3

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page