This project provides a comprehensive data collection and analysis system for French municipalities and their inter-municipal organizations (EPCIs). It combines financial data from the OFGL (Observatoire des Finances et de la Gestion publique Locales) API with AI-powered web research to create detailed municipality profiles.

Click here for a Demo on YouTube.
To test the App go to https://aws-deployment.d5glcpyeyb6n5.amplifyapp.com/
Detailed financial metrics for both municipalities and EPCIs including:
- Budget analysis and debt metrics
- Savings ratios and operating costs
- Per capita financial indicators
- Comparative analysis with similar municipalities
- OFGL API for official financial data (https://www.ofgl.fr/)
- Perplexity API for web research (https://www.perplexity.ai/)
- RAG (Retrieval Augmented Generation) for document analysis
- Custom reference database of similar municipalities
- Backend: FastAPI server with AI agent system
- Frontend: Vue.js web application
- AI: Claude 3.5 Sonnet (via Amazon Bedrock) as the main LLM
- Database: DynamoDB for data persistence
- Structured JSON data
- PDF reports
- Interactive web interface
- Comparative visualizations
The system is designed to help financial analysts, municipal administrators, and researchers access and analyze comprehensive municipal data through an intuitive interface while leveraging AI to enrich the data with contextual information.
The project is organized into two main components:
agent/
(/server/agent): Core AI agent systemagents.py
(/server/agent/agents.py): Agent implementationsorchestrator.py
(/server/agent/orchestrator.py): Coordination of data collectiontools.py
(/server/agent/tools.py): Tool implementations for agentsprompt.py
(/server/agent/prompt.py): LLM prompt templatesrag_pipeline.py
(/server/agent/rag_pipeline.py): Document retrieval systemutil.py
(/server/agent/util.py): Utility functions for querying the OFGL API
api/
(/server/api): FastAPI server implementationtemplate/
(/server/template): PDF report templatestests/
(/server/tests): Test suitenotebooks/
(/server/notebooks): Development and testing notebooks
src/
(/web-app/src): Source codecomponents/
(/web-app/src/components): Vue.js componentsstores/
(/web-app/src/stores): State managementassets/
(/web-app/src/assets): Static assetslib/
(/web-app/src/lib): Utility functions
public/
(/web-app/public): Static files
-
Notebooks and scripts for data preprocessing and exploration:
explore_ofgl_api.ipynb
(/data/explore_ofgl_api.ipynb): Exploration of the OFGL API endpoints and available datasetspp_ofgl_data.ipynb
(/data/pp_ofgl_data.ipynb): Data preprocessing pipeline for municipality data including:- Deduplication of municipality entries
- Population data normalization
- Reference municipality selection
- JSON data structure formatting
-
Processed Data Files:
populations-ofgl-communes-postprocessed.json
: Processed municipality dataset containing:- Basic municipality info (SIREN, codes, names)
- Administrative hierarchy (commune, EPCI, department, region)
- Population metrics (current and projected)
- Reference municipalities for comparisons
- Structured for easy API consumption
The data processing workflow:
- Fetches raw data from OFGL API (https://www.data.gouv.fr/fr/dataservices/explore-api-v2-50/)
- Removes duplicate entries keeping most recent data
- Adds reference municipalities based on:
- Same region
- Similar population size
- Administrative status
- Outputs standardized JSON format for the application
- Python 3.11+
- Node.js 18+
- Docker
- AWS Account with Bedrock access
- API keys for Perplexity and OFGL
- Clone the repository
- Set up environment variables in
.env
files for both server and web-app - Install dependencies:
- Server:
poetry install
- Web-app:
npm install
- Server:
- Start development servers:
- Server:
poetry run uvicorn main:app --reload
- Web-app:
npm run dev
- Server:
- Server:
docker build -t h-genai-server .
- Web-app:
npm run build
Sample command:
cd server && docker build -t h-genai-server . && docker tag h-genai-server:latest 140023381458.dkr.ecr.us-west-2.amazonaws.com/
h-genai-server:latest && docker push 140023381458.dkr.ecr.us-west-2.amazonaws.com/h-genai-server:latest && aws lambda
update-function-code --function-name h-genai-server --image-uri 140023381458.dkr.ecr.us-west-2.amazonaws.com/h-genai-server:latest
The project uses GitHub Actions for continuous integration and deployment, configured in .github/workflows/aws-deployment.yml
.
The pipeline consists of three main jobs:
- Test Server:
- Runs on every push to
main
that changes files in/server
- Sets up Python 3.11 environment
- Installs dependencies using Poetry
- Runs pytest suite
- Caches dependencies for faster builds
- Runs on every push to
- Deploy Server (runs after successful tests):
- Builds Docker image for Lambda deployment
- Pushes to Amazon ECR
- Updates Lambda function
- Configures provisioned concurrency
- Creates production alias
- Deploy Web App (on
web-app
branch):- Sets up Node.js environment
- Runs tests and builds application
- Deploys to AWS Amplify
Required secrets in GitHub:
AWS_ACCESS_KEY_ID
AWS_SECRET_ACCESS_KEY
AWS_ECR_REGISTRY
AWS_AMPLIFY_APP_ID
The server component uses pytest for testing. Tests are located in /server/tests/
.
- Unit Tests:
cd server
poetry run pytest
- Local Lambda Testing:
# Build and run container
docker build -t h-genai-server:local .
docker run -p 8080:8080 h-genai-server:local
# Test endpoints
curl -X POST "http://localhost:8080/2015-03-31/functions/function/invocations" \
-H "Content-Type: application/json" \
-d '{
"version": "2.0",
"routeKey": "GET /health",
"rawPath": "/health",
"requestContext": {
"http": {
"method": "GET",
"path": "/health"
}
}
}'
- Integration Tests:
- Test script available at
test_local.sh
- Automates container lifecycle and endpoint testing
- Provides detailed test results
The web application uses Vitest for testing:
cd web-app
npm run test
-
Server Tests:
- Add test files in
/server/tests/
- Follow existing patterns for API and agent tests
- Use pytest fixtures from
conftest.py
- Add test files in
-
Web App Tests:
- Add test files alongside components
- Use Vue Test Utils for component testing
- Follow Vue's testing best practices