- Settings: All hardcoded timeouts across modules are now configurable through Pydantic settings, organized per module (
settings.<module>.timeouts.<operation>). Affected modules:utils,audit,versions,clean,backport,cache_clean,tests,pull_request,patch.
- Breaking:
settings.audit_timeoutsmoved tosettings.audit.timeouts. Environment variables change fromGHCI__AUDIT_TIMEOUTS__*toGHCI__AUDIT__TIMEOUTS__*.
- Queue: Added step logs in the job preamble (
Get GitHub application,Get GitHub project,Get GitHub rate limit,Get dashboard issue,Get project configuration, check run creation/update), to identify where a job hangs when it never reaches the module processing.
- Versions module: The subprocesses (
git ls-files,renovate-graph) are now killed when their timeout expires, instead of being left running. - Queue: The job selection now only locks the picked row (
LIMIT 1added to theFOR UPDATE SKIP LOCKEDquery), instead of locking all the jobs of the current priority level for the whole selection transaction, which could make the other workers see no available job. - Database: The SQLAlchemy connection pools now test the connections before using them (
pool_pre_pingenabled by default, can be disabled withGHCI__SQLALCHEMY__POOL_PRE_PING=false), to not hang on dead connections (for example after a database restart).
- Modules & Queue: Replaced blocking synchronous file I/O calls (
pathlib.Path.exists(),pathlib.Path.mkdir(),open(),shutil.rmtree(),tempfile.mkdtemp(),os.chdir(),c2cciutils.get_config()) with async equivalents (anyio.Path,anyio.to_thread.run_sync) across all modules. This prevents the event loop from being blocked, allowing theasyncio.timeout()(50 min) to properly fire and cancel stuck jobs instead of leaving them inPENDINGstatus permanently. - Queue: Added explicit task cleanup after
asyncio.timeout()fires to ensure the inner processing task is cancelled and its resources are released.
- Patch module: When
git pushfails, the module now returnsProcessOutput(success=False)instead of raisingPatchError. This marks the job asREPORT_ERROR(yellow warning) instead ofFAIL(red danger), distinguishing a push failure from a system error.
- Audit module: Added configurable
dashboard-severity-threshold(default:medium) andadvisory-severity-threshold(default:high) tosnykconfiguration. - Audit module: Added
excluded-filesconfiguration option to exclude specific files (regex patterns) from the dashboard and advisory creation. - Audit module: Vulnerabilities in the issue dashboard are now grouped by file with
==== <file_name>headers under=== <version>section titles. - Audit module: The module now automatically creates GitHub Security Advisories for vulnerabilities meeting the
advisory-severity-threshold(requiressecurity_advisories: writepermission). - Audit module: Added
_VulnerabilityDatastructured data class andSEVERITY_ORDERordering,ECOSYSTEM_MAPfor Snyk-to-GitHub ecosystem mapping.
- Admin access: GitHub OAuth users can now be granted admin status based on their repository permissions. Configured via
C2C__AUTH__GITHUB__REPOSITORYandC2C__AUTH__GITHUB__ACCESS_TYPE(default:pull). SetC2C__AUTH__GITHUB__ACCESS_TYPE=adminto require admin permissions on the repository.
- Framework migration: replaced Pyramid WSGI +
c2cwsgiutilswith FastAPI ASGI +c2casgiutils. - Web server: replaced
waitress+gunicornwithuvicorn. - Templates: converted all Mako templates to Jinja2.
- Configuration: environment variables are now centralized via
pydantic-settingswith theGHCI__prefix.- All application-specific settings are grouped under
GHCI__APPLICATION__<name>__<property>(e.g.GHCI__APPLICATION__TEST__GITHUB_APP_ID). - Old flat env vars (
LOG_LEVEL,SQL_LOG_LEVEL,SERVICE_URL,VISIBLE_ENTRY_POINT,TEST_APPLICATION,TEST_USER,GHCI_APPLICATIONS,GHCI_TEST_*) are removed or replaced. - The
C2C_AUTH_GITHUB_*vars have been updated toC2C__AUTH__GITHUB__*format. C2C_PROMETHEUS_PORT→C2C__PROMETHEUS__PORT.SQLALCHEMY_URL→GHCI__SQLALCHEMY__URL(now usespostgresql+asyncpg://).- Duration fields now accept ISO 8601 format (
PT3H,P30D,PT600S) and combined short formats (2h30,2m30,1w2d). - Redis settings are now under
settings.redis.*. - Webhook settings are under
settings.webhook.*. - Module-specific settings are grouped:
settings.audit.*,settings.versions.*,settings.dispatch_publishing.*,settings.process_queue.*. settings.application_settingsproperty removed; usesettings.application_configsdirectly.
- All application-specific settings are grouped under
- Dependencies:
itsdangerousadded as explicit dependency (required bySessionMiddleware). - Security:
- Authentication types are now an
AuthTypeenum. X-Hub-Signature-256validation is now handled exclusively insecurity.py.- CSP headers are enforced via
ArmorHeaderMiddleware; inline scripts and styles useCSP_NONCE. - All inline styles moved to CSS classes.
- ANSI log messages now use CSS classes instead of inline styles.
- Repository-level permission checks (
has_repo_access) restored forlogs_view,output_view, andproject_view.
- Authentication types are now an
- Database:
JobLogEntrygained acss_stylecolumn to store ANSI CSS styles alongside log entries. - Logging: root logger level is temporarily set to
DEBUGduring job processing so that INFO/DEBUG messages are captured in the job log. - Duration parsing: consolidated in
settings.py; supports ISO 8601 and combined short formats (e.g.2h30,2m30). _AppConfigmodel now properly passestitle,description,github_app.url,github_app.admin_url,github_app.webhook_secretfrom environment variables.- The
colorfield in_DependencyBaseand_Dependenciesmodels was renamed tocss_classand now holds CSS class names instead of CSS variable names.
- Health checks: SQLAlchemy and Redis health checks registered via
c2casgiutils.health_checks. - Prometheus: metrics instrumentation via
prometheus_fastapi_instrumentator.Instrumentatorand Prometheus HTTP server. - Sentry: error tracking initialized if DSN is configured.
- Logging:
_LOGGERmodule-level logger convention documented inAGENTS.md. - Debug log of all settings at application startup (
LOG_LEVEL=DEBUG). - Tests for
merge_css_blocksand_to_html_cssfunctions.
c2cwsgiutilsdependency completely replaced byc2casgiutils.production.iniandgunicorn.conf.pyconfiguration files.requirements.txtrestored (was deleted during migration).app.state.settingsandapp.state.db_url— usesettingsdirectly.attrdictdependency removed.pkg_resourcesreplaced withimportlib.metadata.entry_points.
- Jinja2 operator precedence: parenthesize
(a - b) | filterto avoida - (b | filter). - Template filter registration:
markdown,sanitizer,pprint_date,pprint_short_date,pprint_full_date,pprint_durationare now registered as Jinja2 filters (not just globals). pprint_dateandmarkdownnow returnMarkupobjects to avoid double-escaping.markdownfilter handlesNoneinput.- Dark mode
data-bs-themeattribute now works thanks to CSP nonce support. test_pprint_durationusestimedeltaobjects instead of string literals.- Acceptance test reference images updated to match Jinja2 rendering.
- Database: After deploying this version, run the following SQL to add the
css_stylecolumn tojob_log:ALTER TABLE job_log ADD COLUMN css_style TEXT;
- Environment variables: See the updated
README.mdfor the new environment variable format.