Comprehensive Pydantic validators and custom types for Netrun Systems portfolio applications
Project description
netrun-validation
Comprehensive Pydantic validators and custom types for Netrun Systems portfolio applications.
Features
- Generic Validators: Reusable validators for common patterns (enum values, ranges, non-empty strings, etc.)
- Environment Validators: Validate environment names, log levels, and provider selections
- Security Validators: Password strength, secret keys, API keys, JWT tokens with entropy calculation
- Network Validators: URLs, database URLs, IP addresses, ports, CORS origins
- DateTime Validators: ISO timestamps, timezones, date ranges, future/past dates
- Custom Pydantic Types: Auto-validated types for Email, URLs, Passwords, Secrets, and more
- Decorators: Function input/output validation and sanitization
Installation
pip install netrun-validation
Quick Start
Using Custom Types (Auto-Validated)
from pydantic import BaseModel
from netrun.validation import Email, SecureURL, StrongPassword, PortNumber
class User(BaseModel):
email: Email
website: SecureURL
password: StrongPassword
class ServerConfig(BaseModel):
port: PortNumber
allowed_origins: list[str]
# Auto-validation on instantiation
user = User(
email="user@example.com",
website="https://example.com", # Must be HTTPS
password="P@ssw0rd123" # Must meet strength requirements
)
config = ServerConfig(
port=8080, # Must be 1-65535
allowed_origins=["https://app.example.com"]
)
Using Validators with Field Validators
from pydantic import BaseModel, field_validator
from netrun.validation import validate_environment, validate_database_url
class Settings(BaseModel):
environment: str
database_url: str
@field_validator("environment")
@classmethod
def check_environment(cls, v):
return validate_environment(v)
@field_validator("database_url")
@classmethod
def check_database_url(cls, v):
return validate_database_url(v)
# Valid instantiation
settings = Settings(
environment="production", # Validates against allowed environments
database_url="postgresql://user:pass@localhost:5432/db"
)
Custom Types Reference
| Type | Description | Example |
|---|---|---|
Email |
Valid email address | user@example.com |
SecureURL |
HTTPS-only URL | https://api.example.com |
HttpURL |
HTTP/HTTPS URL | http://example.com |
DatabaseURL |
Database connection URL | postgresql://... |
StrongPassword |
8+ chars, upper, lower, digit | P@ssw0rd123 |
SecretKey |
32+ character secret | abcdef... (32+ chars) |
JWTSecret |
JWT secret key (32+ chars) | abcdef... (32+ chars) |
EncryptionKey |
Encryption key (32+ chars) | abcdef... (32+ chars) |
PortNumber |
Network port (1-65535) | 8080 |
IPAddress |
IPv4/IPv6 address | 192.168.1.1 |
PositiveInt |
Integer >= 1 | 10 |
NonNegativeInt |
Integer >= 0 | 0 |
Environment |
Literal environment type | "production" |
LogLevel |
Literal log level type | "INFO" |
Validators Reference
Generic Validators
from netrun.validation import (
validate_enum_value,
validate_range,
validate_non_empty,
validate_list_from_csv,
validate_positive_int,
validate_percentage,
)
# Enum validation
env = validate_enum_value("production", ["dev", "staging", "production"], "environment")
# Range validation
temperature = validate_range(0.7, 0.0, 2.0, "temperature")
# Non-empty string
name = validate_non_empty("John Doe", "name")
# CSV to list
origins = validate_list_from_csv("http://localhost:3000,https://example.com")
# Returns: ['http://localhost:3000', 'https://example.com']
# Positive integer
pool_size = validate_positive_int(10, "pool_size")
# Percentage
completion = validate_percentage(75.5, "completion")
Environment Validators
from netrun.validation import (
validate_environment,
validate_log_level,
validate_llm_provider,
validate_voice_provider,
)
env = validate_environment("production") # Validates against standard environments
log_level = validate_log_level("INFO") # Validates against Python log levels
llm = validate_llm_provider("openai") # Validates LLM provider
voice = validate_voice_provider("azure") # Validates voice provider
Security Validators
from netrun.validation import (
validate_secret_key,
validate_password_strength,
validate_api_key_format,
calculate_entropy,
)
# Secret key (32+ characters)
secret = validate_secret_key("a" * 32)
# Password strength
password = validate_password_strength(
"P@ssw0rd123",
min_length=8,
require_uppercase=True,
require_lowercase=True,
require_digit=True,
require_special=False,
)
# API key format
api_key = validate_api_key_format("sk-" + "a" * 20, prefix="sk-", min_length=20)
# Calculate password entropy
entropy = calculate_entropy("P@ssw0rd123") # Returns float (bits per character)
Network Validators
from netrun.validation import (
validate_url,
validate_database_url,
validate_redis_url,
validate_ip_address,
validate_port,
validate_cors_origins,
)
# URL validation
url = validate_url("https://api.example.com", require_https=True)
# Database URL
db_url = validate_database_url("postgresql://user:pass@localhost:5432/db")
# Redis URL
redis_url = validate_redis_url("redis://localhost:6379/0")
# IP address
ip = validate_ip_address("192.168.1.1")
# Port number
port = validate_port(8080)
# CORS origins
origins = validate_cors_origins("http://localhost:3000,https://example.com")
# Returns: ['http://localhost:3000', 'https://example.com']
DateTime Validators
from datetime import datetime
from netrun.validation import (
validate_iso_timestamp,
validate_timezone,
validate_date_range,
validate_future_date,
validate_past_date,
)
# ISO timestamp
dt = validate_iso_timestamp("2025-01-15T10:30:00Z")
# Timezone
tz = validate_timezone("America/New_York")
# Date range
dt = validate_date_range(
datetime(2025, 1, 15),
min_date=datetime(2025, 1, 1),
max_date=datetime(2025, 12, 31)
)
# Future date
future = validate_future_date(datetime(2026, 1, 1))
# Past date
past = validate_past_date(datetime(2024, 1, 1))
Decorators
Function Input Validation
from netrun.validation import validate_input, validate_non_empty
@validate_input(validate_non_empty)
def greet(name: str) -> str:
return f"Hello, {name}!"
greet("Alice") # OK
greet("") # Raises ValueError
Output Sanitization
from netrun.validation import sanitize_output
@sanitize_output(["password", "secret"])
def get_user() -> dict:
return {
"name": "Alice",
"password": "secret123",
"email": "alice@example.com"
}
result = get_user()
# Returns: {"name": "Alice", "password": "***REDACTED***", "email": "alice@example.com"}
Type Validation
from netrun.validation import validate_type
@validate_type(name=str, age=int)
def create_user(name: str, age: int) -> dict:
return {"name": name, "age": age}
create_user(name="Alice", age=30) # OK
create_user(name="Alice", age="30") # Raises TypeError
Real-World Example
from pydantic import BaseModel, field_validator
from netrun.validation import (
Email,
SecureURL,
DatabaseURL,
JWTSecret,
PortNumber,
PositiveInt,
Environment,
LogLevel,
validate_cors_origins,
)
class WilburSettings(BaseModel):
# Application Configuration
app_name: str = "Wilbur AI Assistant"
app_environment: Environment = "development"
app_port: PortNumber = 8080
# Security
app_secret_key: JWTSecret
jwt_secret_key: JWTSecret
# Database
database_url: DatabaseURL
database_pool_size: PositiveInt = 10
# API Configuration
api_endpoint: SecureURL
admin_email: Email
# CORS
cors_origins: list[str]
# Logging
log_level: LogLevel = "INFO"
@field_validator("cors_origins", mode="before")
@classmethod
def validate_cors(cls, v):
return validate_cors_origins(v)
# Usage
settings = WilburSettings(
app_environment="production",
app_port=8000,
app_secret_key="a" * 32,
jwt_secret_key="b" * 32,
database_url="postgresql://user:pass@localhost:5432/wilbur",
database_pool_size=20,
api_endpoint="https://api.wilbur.ai",
admin_email="admin@wilbur.ai",
cors_origins="https://app.wilbur.ai,https://admin.wilbur.ai",
log_level="INFO",
)
Testing
Run tests with pytest:
cd /data/workspace/github/Netrun_Service_Library_v2/packages/netrun-validation
pytest tests/ -v --cov=netrun.validation --cov-report=term-missing
Development
# Install in development mode
pip install -e ".[dev]"
# Run tests with coverage
pytest tests/ -v --cov=netrun.validation --cov-report=html
# Format code
black src/ tests/
# Lint code
ruff check src/ tests/
License
MIT License - see LICENSE file for details.
Author
Daniel Garza Netrun Systems daniel@netrunsystems.com
Links
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file netrun_validation-1.0.0.tar.gz.
File metadata
- Download URL: netrun_validation-1.0.0.tar.gz
- Upload date:
- Size: 23.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
9eb14021041db7d6f880470bb3d28c5baa979aeedd823b11eb5c1bfe0d6a7f51
|
|
| MD5 |
a16bf5ee5c03ebf93696300efd646050
|
|
| BLAKE2b-256 |
a6f514d8fcae448c335185726363e234501267664d534d62e9cf71cf4aa32012
|
File details
Details for the file netrun_validation-1.0.0-py3-none-any.whl.
File metadata
- Download URL: netrun_validation-1.0.0-py3-none-any.whl
- Upload date:
- Size: 19.6 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
af5e3bca8c13f2b17142bf5d3203eda430a5bfbe55329a9e44596e0c3fa134f2
|
|
| MD5 |
07fd4f34e9c0dc3d7cfba74b33c1a8ed
|
|
| BLAKE2b-256 |
98a3e65ecb86d7a0aa93e699f595d002e0db417a816f8a8f261f20f2cffb9f22
|