Initial Commit
This commit is contained in:
@@ -0,0 +1,57 @@
|
||||
"""Runtime configuration, all from the environment."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import os
|
||||
from dataclasses import dataclass, field
|
||||
|
||||
|
||||
def _int(name: str, default: int) -> int:
|
||||
try:
|
||||
return int(os.getenv(name, "") or default)
|
||||
except ValueError:
|
||||
return default
|
||||
|
||||
|
||||
def _opt(name: str) -> str | None:
|
||||
# Compose passes unset optionals through as empty strings rather than
|
||||
# omitting them, so "" has to mean "absent" here.
|
||||
return (os.getenv(name) or "").strip() or None
|
||||
|
||||
|
||||
@dataclass(frozen=True)
|
||||
class Settings:
|
||||
auth_token: str = field(default_factory=lambda: os.environ["OWUITOOLS_AUTH_TOKEN"])
|
||||
egress_proxy: str = field(default_factory=lambda: os.getenv("OWUITOOLS_EGRESS_PROXY", "http://owuitools-egress:3128"))
|
||||
searxng_url: str = field(default_factory=lambda: os.getenv("OWUITOOLS_SEARXNG_URL", "http://owuitools-searxng:8080").rstrip("/"))
|
||||
valkey_url: str = field(default_factory=lambda: os.getenv("OWUITOOLS_VALKEY_URL", "redis://owuitools-valkey:6379/0"))
|
||||
contact: str = field(default_factory=lambda: os.getenv("OWUITOOLS_CONTACT", "owuitools@localhost"))
|
||||
# Optional. Goes in the User-Agent so a site that wants to know who is
|
||||
# fetching can look you up. Leave it unset if this is not reachable
|
||||
# from outside, which is the normal case.
|
||||
public_url: str | None = field(default_factory=lambda: _opt("OWUITOOLS_PUBLIC_URL"))
|
||||
|
||||
max_response_chars: int = field(default_factory=lambda: _int("OWUITOOLS_MAX_RESPONSE_CHARS", 12000))
|
||||
probe_rate_per_hour: int = field(default_factory=lambda: _int("OWUITOOLS_PROBE_RATE_PER_HOUR", 30))
|
||||
log_level: str = field(default_factory=lambda: os.getenv("OWUITOOLS_LOG_LEVEL", "INFO").upper())
|
||||
|
||||
github_token: str | None = field(default_factory=lambda: _opt("OWUITOOLS_GITHUB_TOKEN"))
|
||||
stackexchange_key: str | None = field(default_factory=lambda: _opt("OWUITOOLS_STACKEXCHANGE_KEY"))
|
||||
nvd_key: str | None = field(default_factory=lambda: _opt("OWUITOOLS_NVD_KEY"))
|
||||
|
||||
@property
|
||||
def user_agent(self) -> str:
|
||||
# Wikimedia hard-blocks requests with no User-Agent (verified: 403)
|
||||
# and its policy explicitly disallows generic ones like "curl/8.5.0",
|
||||
# which pass today and may not tomorrow. OpenAlex and Crossref read
|
||||
# the same string to decide whether you get the polite pool.
|
||||
#
|
||||
# The URL is included only if there is one to give. It used to be
|
||||
# one deployment's address, hardcoded - which every other
|
||||
# deployment would then have been announcing as its own to every
|
||||
# site it fetched from.
|
||||
site = f"+{self.public_url}; " if self.public_url else ""
|
||||
return f"owuitools/1.0 ({site}{self.contact})"
|
||||
|
||||
|
||||
settings = Settings()
|
||||
Reference in New Issue
Block a user