Skip to main content

Core shared library for Viveka — config, logging, and async cache management

Project description

viveka-grantha

Core shared library for the Viveka platform — provides configuration management, structured logging, and async cache management as reusable infrastructure components.

Developed by VivekaSutra


Overview

viveka-grantha is the foundation layer that all Viveka services depend on. It solves three cross-cutting concerns so individual services don't have to:

Module What it does
viveka_common.config Reads config from config.ini and environment variables with a unified API
viveka_common.log Singleton logging manager with console and rotating file handlers
viveka_common.cache Async Redis cache with a pluggable backend interface

Installation

pip install viveka-grantha

Configuration

Structure

viveka-grantha reads from a config.ini file using section.key dot notation.

config.ini:

[app]
name    = my-service
env     = production

[logging]
level         = INFO
file_enabled  = true
file_path     = logs/app.log
console_enabled = true

[cache]
enabled     = true
backend     = redis
url         = redis://localhost:6379/0
default_ttl = 3600

Priority order

When you call config.get("database.url"), the service checks in this order:

  1. Environment variable — DATABASE_URL
  2. config.ini[database] url = ...
  3. Default value you provide

This means you can override any config value with an environment variable without touching the file — useful for Docker and cloud deployments.

Usage

from viveka_common.config import ConfigService

config = ConfigService()                          # reads config.ini from current directory
config = ConfigService("path/to/config.ini")     # custom path

# Get values
db_url  = config.get("database.url")
port    = config.get("api.port", default=8000, data_type=int)
debug   = config.get("app.debug", default=False, data_type=bool)
hosts   = config.get("app.allowed_hosts", data_type=list)  # comma-separated in ini

# Read from environment variable directly
token = config.get_env_variable("api.secret_key")  # reads API_SECRET_KEY env var

ConfigService is a singleton — calling ConfigService() anywhere in the application returns the same instance initialized at startup.

Supported data types

Type Config.ini example Result
str (default) name = viveka "viveka"
int port = 8080 8080
float timeout = 3.5 3.5
bool debug = true True
list hosts = a.com, b.com ["a.com", "b.com"]

Logging

Setup

Initialize once at application startup before any other code runs:

from viveka_common.log import VivekaLogManager, VivekaLoggingConfig

VivekaLogManager.init(VivekaLoggingConfig(
    level           = "INFO",
    console_enabled = True,
    file_enabled    = True,
    file_path       = "logs/app.log",
    file_max_bytes  = 10_485_760,   # 10 MB
    file_backup_count = 5,
))

Getting a logger

Any class or module gets its own named logger:

from viveka_common.log import VivekaLogManager

_logger = VivekaLogManager.get_instance(__name__)

class UserService:
    def create_user(self, name: str):
        _logger.info(f"Creating user: {name}")
        _logger.debug("Debug details here")
        _logger.error("Something went wrong", exc_info=True)

VivekaLoggingConfig options

Field Default Description
level "INFO" Root log level — DEBUG, INFO, WARNING, ERROR, CRITICAL
format standard format Log line format string
console_enabled True Print logs to stdout
console_level inherits level Override level for console only
file_enabled True Write logs to a rotating file
file_path "logs/viveka.log" Log file path
file_level inherits level Override level for file only
file_max_bytes 10485760 (10 MB) Max size before rotation
file_backup_count 5 Number of rotated files to keep

Notes

  • VivekaLogManager is a singleton. init() only runs once — subsequent calls are no-ops unless you pass a new config.
  • get_instance() can be called before init() — it auto-initializes with INFO level defaults.
  • Rotating file handler prevents log files from growing unbounded.

Cache

Setup

Initialize once at application startup:

from viveka_common.cache import VivekaCacheConfig, RedisCacheService, VivekaCacheManager

config = VivekaCacheConfig(
    enabled     = True,
    url         = "redis://localhost:6379/0",
    default_ttl = 3600,
)

service = RedisCacheService(config)
VivekaCacheManager.init(service)

To disable caching entirely without changing call sites:

VivekaCacheConfig(enabled=False)  # all cache ops become silent no-ops

Using the cache manager

VivekaCacheManager is the single access point for all cache operations across the application. All methods are async.

from viveka_common.cache import VivekaCacheManager

# Store a value (ttl in seconds, optional — uses default_ttl if omitted)
await VivekaCacheManager.set("user:123", {"id": 123, "name": "Arjun"}, ttl=3600)

# Retrieve a value
user = await VivekaCacheManager.get("user:123")   # returns None on miss

# Delete a single key
await VivekaCacheManager.delete("user:123")

# Delete all keys matching a pattern (used by @cache_evict)
await VivekaCacheManager.delete_pattern("user:*")

# Health check
is_alive = await VivekaCacheManager.ping()

If the cache backend is down, every operation logs an error and returns a safe default (None / False) — business logic is never interrupted.

Custom cache backend

VivekaCacheService is an abstract interface. You can implement your own backend (Memcached, in-memory, etc.) and plug it in:

from viveka_common.cache import VivekaCacheService, VivekaCacheManager

class InMemoryCacheService(VivekaCacheService):
    def __init__(self):
        self._store = {}

    async def get(self, key): return self._store.get(key)
    async def set(self, key, value, ttl=None): self._store[key] = value; return True
    async def delete(self, key): self._store.pop(key, None); return True
    async def delete_pattern(self, pattern): ...
    async def ping(self): return True

VivekaCacheManager.init(InMemoryCacheService())

Full startup example

from viveka_common.config import ConfigService
from viveka_common.log import VivekaLogManager, VivekaLoggingConfig
from viveka_common.cache import VivekaCacheConfig, RedisCacheService, VivekaCacheManager

def bootstrap():
    # 1. Config
    config = ConfigService("config.ini")

    # 2. Logging
    VivekaLogManager.init(VivekaLoggingConfig(
        level      = config.get("logging.level", default="INFO"),
        file_path  = config.get("logging.file_path", default="logs/app.log"),
    ))

    # 3. Cache
    cache_config = VivekaCacheConfig(
        enabled     = config.get("cache.enabled", default=False, data_type=bool),
        url         = config.get("cache.url", default="redis://localhost:6379/0"),
        default_ttl = config.get("cache.default_ttl", default=3600, data_type=int),
    )
    VivekaCacheManager.init(RedisCacheService(cache_config))

Dependencies

Package Role
redis Async Redis client (redis.asyncio)
hiredis High-performance Redis protocol parser
aiohttp Async HTTP client for service-to-service calls

Part of the Viveka Platform

viveka-grantha is the foundation layer of the Viveka ecosystem:

  • viveka-grantha — config, logging, cache ← you are here
  • viveka-kosha — async database / ORM layer (depends on viveka-grantha)

Developed and maintained by VivekaSutra


License

Copyright (c) 2025 VivekaSutra. All rights reserved.

This software is distributed under the VivekaSutra Proprietary Software License.

  • Free to download and use for personal or commercial purposes
  • Modification, redistribution, and reverse engineering are not permitted
  • Provided "AS IS" — no warranty of any kind
  • VivekaSutra is not liable for any damages arising from use

See LICENSE.txt for the full license text. For licensing inquiries visit vivekasutra.com

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

viveka_grantha-0.1.1.tar.gz (19.7 kB view details)

Uploaded Source

Built Distribution

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

viveka_grantha-0.1.1-py3-none-any.whl (18.9 kB view details)

Uploaded Python 3

File details

Details for the file viveka_grantha-0.1.1.tar.gz.

File metadata

  • Download URL: viveka_grantha-0.1.1.tar.gz
  • Upload date:
  • Size: 19.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.0

File hashes

Hashes for viveka_grantha-0.1.1.tar.gz
Algorithm Hash digest
SHA256 f89f18bbf3fb50ccdaf0ae56adc58b8ec038493f0b368bbc4453fd23920b455e
MD5 f9cb4699f45ded69de166773b2ec1c53
BLAKE2b-256 bb35d368511f417a8071aea65e6a7528557c55d201a376486972e7bc7c969351

See more details on using hashes here.

File details

Details for the file viveka_grantha-0.1.1-py3-none-any.whl.

File metadata

  • Download URL: viveka_grantha-0.1.1-py3-none-any.whl
  • Upload date:
  • Size: 18.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.0

File hashes

Hashes for viveka_grantha-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 3650469cebb5103f8f0892778a28aba8cded77b43564c1563216f70be81e5fb1
MD5 5b7085caaf16b657afe53df8da8b754e
BLAKE2b-256 d0bf4b6a331a9c2db340801c380d793f4471452410c4bf28b4756f1e5a88911b

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