Skip to main content

Reactive file state management for Python.

Project description

NestWatch

Python

License

PyPI

NestWatch is a Python package that allows applications to react to meaningful file changes instead of raw filesystem events.

Rather than repeatedly polling files and risking cache desynchronization, NestWatch instantly notifies your application whenever a file changes and provides both its previous and new state.

Why NestWatch?

Many applications update caches using polling tasks.

@tasks.loop(minutes=1)
async def update_cache():
        ...

While this works, it introduces a delay between when data changes and when applications become aware of those changes.

This becomes problematic when multiple applications depend on the same data source.

For example:

  • Application A updates "config.json"
  • Application B continues using outdated cached data
  • Application B must wait for its polling task to run
  • Both applications become temporarily out of sync

NestWatch solves this by allowing applications to react to changes instantly.

Features

  • ⚡ Instant file change detection
  • 🧠 Returns both old and new state
  • ➕ Detects added keys
  • ➖ Detects removed keys
  • 🔄 Detects changed values
  • 📍 Dot-path support
  • 🧩 Extensible architecture
  • 📄 JSON support built in
  • 🏗️ Create custom watchers for your own file formats

Installation

pip install nestwatch

Quick Start

from nestwatch.watchers import JSONWatcher


class ConfigCache:

    def __init__(self):

        self.watcher = JSONWatcher("data/config.json")

        self.watcher.on_change(
            self.update_cache
        )

    async def update_cache(self, event):

        # Affected changes only
        print(event.added)
        print(event.removed)
        print(event.changed)

        # Reconstructed views)
        print(event.old)
        print(event.new)
        print(event.updated)

    async def startup(self):

        await self.watcher.start()

Event Object

NestWatch emits an Event object containing:

Property Description
event.added Keys that were added (dot-path → value)
event.removed Keys that were removed (dot-path → old value)
event.changed Keys that were modified (old + new)
event.old Partial reconstruction of only affected old values
event.new Partial reconstruction of only affected new values
event.updated_state Final state after applying the event to the old data

Event Examples

Suppose this file:

{
    "BOT_STATUS": {
        "presence": "online",
        "activity": {
            "type": "playing",
            "name": "Roblox"
        }
    }
}

becomes:

{
    "BOT_STATUS": {
        "presence": "idle",
        "custom": "Watching NestWatch 👀"
    },
    "API": {
        "enabled": true
    }
}

Then:

event.added

{
    "BOT_STATUS.custom": "Watching NestWatch 👀",
    "API.enabled": True
}

event.removed

{
    "BOT_STATUS.activity.type": "playing",
    "BOT_STATUS.activity.name": "Roblox"
}

event.changed

{
    "BOT_STATUS.presence": {
        "old": "online",
        "new": "idle"
    }
}

event.old

{
    "BOT_STATUS": {
        "presence": "online",
        "activity": {
            "type": "playing",
            "name": "Roblox"
        }
    }
}

event.new

{
    "BOT_STATUS": {
        "presence": "idle",
        "custom": "Watching NestWatch 👀"
    },
    
    "API": {
        "enabled": True
    }
}

event.updated_state

{
    "BOT_STATUS": {
        "presence": "idle",
        "custom": "Watching NestWatch 👀"
    },
    "API": {
        "enabled": True
    }
}

IMPORTANT NOTE: “These are partial reconstructions of only affected regions, not full file snapshots.”


Creating Custom Watchers

NestWatch is designed to be extensible.

You can support any file format by subclassing "Watcher".

from nestwatch.watchers import Watcher


class MyCustomWatcher(Watcher):

    def _serialize(self):

        return my_language.load(
            self.file_path
        )

The Watcher class supports asynchronous serializers as well.

This allows you to perform asynchronous file reads before NestWatch processes the data.

import aiofiles
from nestwatch.watchers import Watcher

class MyCustomWatcher(Watcher):

    async def _serialize(self):
        async with aiofiles.open(self.file_path) as f:
            content = await f.read()
            return my_language.load(content)

That's it.

NestWatch will automatically handle:

  • Watching the file
  • Detecting changes
  • Comparing states
  • Generating events
  • Calling your listeners

Use Cases

NestWatch works especially well for:

  • 🤖 Discord bots
  • 🌐 FastAPI applications
  • 📦 Shared caches
  • ⚙️ Configuration files
  • 🔄 Runtime reload systems
  • 🧠 Multi-application projects

Philosophy

Traditional file watchers answer:

"Did the file change?"

NestWatch answers:

"What changed inside the file?"


NestWatch's Dependency

Package Version Usage
watchdog >=6.0.0 Listens for file changes
aiofiles >=25.1.0 For reading files in async for internal asynchronous serializers.

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

nestwatch-0.0.8.tar.gz (9.2 kB view details)

Uploaded Source

Built Distribution

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

nestwatch-0.0.8-py3-none-any.whl (8.3 kB view details)

Uploaded Python 3

File details

Details for the file nestwatch-0.0.8.tar.gz.

File metadata

  • Download URL: nestwatch-0.0.8.tar.gz
  • Upload date:
  • Size: 9.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.14

File hashes

Hashes for nestwatch-0.0.8.tar.gz
Algorithm Hash digest
SHA256 73a8500605fa0ec413315ebfdc865834a975638b82c21851e6e1b07953a44d03
MD5 7e072a028875100118931421a14aee72
BLAKE2b-256 be96236af84045010a5ac2ef9983c489cfe30ab7204e341e1948ada19543070f

See more details on using hashes here.

File details

Details for the file nestwatch-0.0.8-py3-none-any.whl.

File metadata

  • Download URL: nestwatch-0.0.8-py3-none-any.whl
  • Upload date:
  • Size: 8.3 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.14

File hashes

Hashes for nestwatch-0.0.8-py3-none-any.whl
Algorithm Hash digest
SHA256 36001ce6b1a3f02061d1afb36ca7f545a3bf440120afd69e0acb43736b102a23
MD5 2f174472c307d77d890f1c67b1382078
BLAKE2b-256 4f4916d0403c3f883843af984b5ad418a6ffe8c3a551f8a4266cd832afa3fa60

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