Introduce ProviderHealthChecker which probes each configured provider
via AutowireIterator. Wire it into GraphController so /health returns
detailed per-provider status and responds 503 when any provider is
in a degraded state.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add getName() and ping() to each provider and wire ProbeTrait. Make
all classes final, add strict_types declarations, and replace generic
RuntimeException with typed HTTP exceptions so probe() can classify
auth failures and unreachable endpoints correctly.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add getName(), ping(), and probe() to ProviderInterface. Introduce
ProbeTrait to classify HTTP/transport exceptions into typed error codes,
ProviderStatus as the result value object, and ProviderStatusType /
ProviderErrorCode as backing enums.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Replace setUp() factory with direct instantiation (zero-param constructor)
- Add AAA blank-line separators to all test methods
- Consolidate theme + fallback tests behind a DataProvider
- Consolidate day-of-week label tests behind a DataProvider
- Split multi-assertion tests to one assertion per test
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Move fetchAllContributions and merge logic from GraphController into a new
ContributionAggregator service. Replace deprecated TaggedIterator with
AutowireIterator throughout.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
The PostToolUse hook called php bin/phpunit directly, which does not
work inside the Docker-based dev setup. Remove it; tests should be
run via docker compose exec graph vendor/bin/phpunit as documented.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Replace the clone-and-build workflow with a docker-compose snippet
that pulls the image directly from the Gitea container registry.
Add semver tag reference and rename steps to match the new flow.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Declare empty-string defaults for all optional env vars as Symfony
parameters so the container compiles without errors when GITHUB_USER,
GITLAB_TOKEN, GITEA_URL, etc. are not set in the environment.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Replace php:8.4-cli-alpine3.21 with dunglas/frankenphp:1-php8.4-alpine.
No Go toolchain required — the official image ships as a pre-compiled
Alpine binary.
- Drop docker-php-ext-install opcache (FrankenPHP enables it by default)
- Both dev and final stages run frankenphp run --config /etc/caddy/Caddyfile
- Dev stage bakes in Caddyfile.dev (no worker mode, Xdebug compatible)
- Final stage bakes in production Caddyfile
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Boot the Symfony kernel once at startup, then loop with
frankenphp_handle_request() to handle every incoming request without
re-bootstrapping the framework. Supports MAX_REQUESTS env var for
graceful worker restarts.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add production and dev Caddyfiles for FrankenPHP:
- Caddyfile: HTTP-only on :8080, auto_https off, worker mode
- Caddyfile.dev: same but without worker directive so Xdebug
step-debugging remains functional; Caddy debug logging enabled
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Covers testing file conventions, Red→Green→Refactor cycle with
example prompts, common anti-patterns, test runner commands, and
the auto-run hook setup.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- modify('Sunday') → modify('last Sunday') so the grid start is
reliably the prior Sunday when today is already Sunday
- Remove unused $totalW from renderLegend signature
- Remove unused GAP constant (value preserved inline as a comment on STEP)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Use GraphQLApiClientRegistryInterface to build the query via the
bundle's query builder. Keep Symfony HttpClient for the actual POST
since GitHub requires application/json (the bundle's transport sends
form_params instead).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- phpunit.xml.dist with unit suite and source coverage config
- .phpunit.cache excluded in .gitignore
- Initial SvgRendererTest as example test
- .claude/settings.json with PostToolUse hook to auto-run phpunit on edit
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- symfony/* pinned to 7.4.* (was 7.1.*)
- eightpoints/guzzle-bundle ^8.6 and idci/graphql-client-bundle ^2.0 added
- phpunit/phpunit ^11.5 and symfony/phpunit-bridge ^7.4 added as dev deps
- Bundles registered in config/bundles.php
- Guzzle and GraphQL client configured via YAML package configs
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>