Documentation Technique et FonctionnelleTechnical and Functional Documentation

Version : server.py + index.html  ·  2026-06-09

1. Vue d'ensemble1. Overview

Portfolio Manager est une application web monopage de gestion de portefeuille boursier. Elle est entièrement autonome : le serveur est écrit en Python pur (aucune dépendance externe) et le front-end est un fichier HTML unique avec JavaScript vanilla (Bootstrap 5, Chart.js chargés via CDN).
Portfolio Manager is a single-page web application for stock portfolio management. It is fully self-contained: the server is written in pure Python (no external dependencies) and the front-end is a single HTML file with vanilla JavaScript (Bootstrap 5, Chart.js loaded via CDN).

Ce que fait l'applicationWhat the application does

DomaineDomainFonctionnalitésFeatures
Suivi de portefeuillePortfolio trackingTable de positions avec cotations temps réel, P&L, KPIs agrégés, graphique d'allocationPosition table with live quotes, P&L, aggregated KPIs, allocation chart
Gestion des positionsPosition managementCRUD, import CSV, saisie en masse, édition inlineCRUD, CSV import, bulk paste, inline editing
Analyse quantitativeQuantitative analysisContribution à la performance, VaR Monte Carlo (100 000 scénarios), CVaR, attribution BHBPerformance contribution, Monte Carlo VaR (100,000 scenarios), CVaR, BHB attribution
Modèle IAAI modelScore composite 4 critères (potentiel analyste, alpha secteur/pays, point d'entrée), optionnellement DCFComposite score 4 criteria (analyst target, sector/country alpha, entry point), optionally DCF
Valorisation DCFDCF valuationMode simplifié (données Yahoo Finance) et mode complet (projections FCF manuelles). Onglet Scores DCF dédié.Simple mode (Yahoo Finance data) and complete mode (manual FCF projections). Dedicated DCF Scores tab.
ArbitrageSimulation avec 7 modèles prédéfinis ou portefeuilles cibles personnalisésSimulation with 7 predefined models or custom target portfolios
Gestion clientsClient managementCRUD clients, association portefeuilles, rapport valorisé en EURClient CRUD, portfolio association, EUR-valued report
ComparaisonComparisonAnalyse What If, comparaison de benchmarks sur 5 périodesWhat If analysis, benchmark comparison over 5 periods
ESGScore ESG/E/S/G issu d'un fichier Excel externeESG/E/S/G score from an external Excel file

Stack techniqueTechnical stack

ComposantComponentTechnologieTechnology
Serveur HTTPHTTP serverPython 3 stdlib — http.server.HTTPServer / BaseHTTPRequestHandler
PersistencePersistenceFichiers JSON locauxLocal JSON files
Données marchéMarket dataYahoo Finance API (spark, chart, quoteSummary, search) via urllib.request
IdentificationIdentificationOpenFIGI API v3 (mapping TICKER → ISIN)
ESGFichier Excel .xlsx lu via zipfile + xml.etree.ElementTreeExcel .xlsx file read via zipfile + xml.etree.ElementTree
Front-endHTML5 + CSS3 + JavaScript ES2020 vanilla
UI frameworkBootstrap 5.3.2 (CDN) + Bootstrap Icons 1.11.3 (CDN)
GraphiquesChartsChart.js 4.4.0 (CDN)

Architecture

Navigateur                  Serveur Python (port 5000)               Sources externes
──────────                  ──────────────────────────               ────────────────
index.html     ←── GET / ── Handler.do_GET                          Yahoo Finance API
JavaScript     ←──REST API── Handler.do_POST/PUT/DELETE             OpenFIGI API
fetch()        ─────────────► Calculs : VaR, BHB, DCF, arbitrage    ESG Excel (local)
Chart.js                     Cache mémoire (_cache dict)
Bootstrap                    Fichiers JSON (portfolio, arb, dcf, clients)Browser                     Python server (port 5000)                External sources
──────────                  ──────────────────────────               ────────────────
index.html     ←── GET / ── Handler.do_GET                          Yahoo Finance API
JavaScript     ←──REST API── Handler.do_POST/PUT/DELETE             OpenFIGI API
fetch()        ─────────────► Calcs: VaR, BHB, DCF, arbitrage       ESG Excel (local)
Chart.js                     In-memory cache (_cache dict)
Bootstrap                    JSON files (portfolio, arb, dcf, clients)

Le serveur est single-threaded (pas de ThreadingMixIn) ; les calculs longs (VaR Monte Carlo) bloquent donc le serveur le temps du calcul. Un verrou threading.Lock protège le cache partagé contre les accès concurrents potentiels.

The server is single-threaded (no ThreadingMixIn); long calculations (Monte Carlo VaR) therefore block the server during computation. A threading.Lock protects the shared cache against potential concurrent access.

2. Installation et démarrage2. Installation and startup

PrérequisPrerequisites

Fichiers nécessairesRequired files

portfolio_app/
├── server.py                  # Serveur + toute la logique backendServer + all backend logic
├── start.bat                  # Lanceur Windows (détection Python automatique)Windows launcher (auto Python detection)
├── templates/
│   ├── index.html             # Application front-end SPASPA front-end application
│   ├── documentation.html     # Cette documentationThis documentation
│   └── data_model.html        # Modèle de donnéesData model
├── portfolio.json             # Créé automatiquement au premier ajoutAuto-created on first add
├── arb_portfolios.json        # Créé automatiquementAuto-created
├── dcf_params.json            # Créé automatiquementAuto-created
└── clients.json               # Créé automatiquementAuto-created

DémarrageStartup

# Option 1 : double-clic sur start.bat (Windows)
# Option 2 : ligne de commande# Option 1: double-click start.bat (Windows)
# Option 2: command line
cd H:\portfolio_app
python server.py

Au démarrage, le programme :

On startup, the program:

  1. Charge les données ESG depuis le fichier Excel (si présent)
  2. Loads ESG data from the Excel file (if present)
  3. Demande interactivement la configuration du proxy :
    • Entrée vide → proxy par défaut
    • - → pas de proxy (connexion directe)
    • host:port → proxy personnalisé
  4. Interactively asks for proxy configuration:
    • Empty enter → default proxy
    • - → no proxy (direct connection)
    • host:port → custom proxy
  5. Demande optionnellement un login/mot de passe proxy
  6. Optionally asks for proxy login/password
  7. Démarre le serveur sur http://127.0.0.1:5000
  8. Starts the server on http://127.0.0.1:5000
Ouvrir un navigateur à l'adresse : http://localhost:5000  —  Arrêt : Ctrl+C
Open a browser at: http://localhost:5000  —  Stop: Ctrl+C

3. Structure des fichiers3. File structure

FichierFileRôleRole
server.pyPoint d'entrée unique. Contient : serveur HTTP, toutes les routes REST, les calculs quantitatifs (VaR, BHB, DCF, contribution, arbitrage, what-if), les référentiels de données, le chargement ESG, la gestion du cache et du proxy.Single entry point. Contains: HTTP server, all REST routes, quantitative calculations (VaR, BHB, DCF, contribution, arbitrage, what-if), data references, ESG loading, cache and proxy management.
templates/index.htmlApplication front-end SPA. Contient : le HTML des 8 onglets, tous les styles CSS inline, et ~4 000 lignes de JavaScript vanilla gérant l'état, les appels REST, le rendu des tableaux, les graphiques Chart.js, la logique DCF Scores et la gestion clients.SPA front-end. Contains: HTML for 8 tabs, all inline CSS, ~4,000 lines of vanilla JavaScript managing state, REST calls, table rendering, Chart.js graphs, DCF Scores logic and client management.
portfolio.jsonPortefeuille principal — liste des positions de l'utilisateur.Main portfolio — list of user positions.
arb_portfolios.jsonPortefeuilles secondaires (arbitrage, stratégie, simulation, watchlist).Secondary portfolios (arbitrage, strategy, simulation, watchlist).
dcf_params.jsonParamètres DCF complets sauvegardés par ticker.Full DCF parameters saved per ticker.
clients.jsonDonnées clients (CRUD, associations portefeuilles).Client data (CRUD, portfolio associations).
etf_constituants_…xlsxSource ESG externe (lecture seule). Chemin codé en dur.External ESG source (read-only). Hard-coded path.

4. Données persistées4. Persisted data

4.1 portfolio.json

{
  "positions": [
    {
      "isin":       "FR0000131104",
      "name":       "BNP Paribas",
      "ticker":     "BNP.PA",
      "quantity":   10,
      "pru":        45.50,
      "currency":   "EUR",
      "entry_date": "2024-01-15",
      "category":   "Stock",
      "potentiel":  15.0,
      "secteur":    "Finance",
      "pays":       "FR",
      "frais":      12.50
    }
  ]
}

4.2 arb_portfolios.json

[
  {
    "id":          "arb_1700000000000",
    "name":        "Tech Growth",
    "created":     "2024-01-15",
    "type":        "target",
    "description": "Portefeuille cible tech",
    "positions":   [ ... ]
  }
]

4.3 dcf_params.json

{
  "AAPL": {
    "current_price":      185.0,
    "shares_outstanding": 15500000000,
    "total_debt":         111000000000,
    "total_cash":         65000000000,
    "wacc":               0.09,
    "terminal_growth":    0.025,
    "fcf_projections":    [90000000000, 95000000000, 100000000000],
    "currency":           "USD",
    "last_updated":       "2024-06-01"
  }
}

4.4 clients.json

[
  {
    "id":            "client_1700000000000",
    "name":          "Jean Dupont",
    "email":         "jean.dupont@example.com",
    "phone":         "+33 6 00 00 00 00",
    "risk_profile":  "Moderate",
    "portfolio_ids": ["arb_1700000000001"],
    "notes":         "Client depuis 2022",
    "created":       "2024-01-15"
  }
]
ChampFieldTypeDescriptionDescription
idstringIdentifiant unique généré (client_ + timestamp)Generated unique ID (client_ + timestamp)
namestringNom complet du clientClient full name
emailstringAdresse emailEmail address
phonestringNuméro de téléphonePhone number
risk_profilestringConservative, Moderate, Aggressive
portfolio_idsstring[]IDs des portefeuilles arbitrage associésIDs of associated arbitrage portfolios
notesstringNotes libresFree-form notes
createdstringYYYY-MM-DD

5. API REST complète5. Full REST API

Portefeuille principalMain portfolio

MethodPathDescriptionDescription
GET/api/portfolioRetourne toutes les positionsReturns all positions
POST/api/portfolioAjoute une positionAdds a position
PUT/api/portfolio/<isin>Met à jour une positionUpdates a position
DELETE/api/portfolio/<isin>Supprime une positionDeletes a position
POST/api/portfolio/bulkImporte plusieurs positions (CSV ou JSON)Imports multiple positions (CSV or JSON)
GET/api/portfolio/exportExporte en CSVExports to CSV

Cotations & analyseQuotes & analysis

MethodPathDescriptionDescription
GET/api/quotes?tickers=A,BCotations temps réel Yahoo FinanceReal-time Yahoo Finance quotes
GET/api/performance?period=1yDonnées de performance historiqueHistorical performance data
GET/api/contributionContribution de chaque position au P&LEach position's P&L contribution
GET/api/var?simulations=100000VaR + CVaR Monte CarloMonte Carlo VaR + CVaR
POST/api/bhbAttribution BHB (Brinson-Hood-Beebower)BHB attribution (Brinson-Hood-Beebower)
GET/api/whatifSimulation What IfWhat If simulation
GET/api/benchmark?period=1yComparaison benchmarksBenchmark comparison

ESG

MethodPathDescriptionDescription
GET/api/esg?isin=FR…Score ESG pour un ISINESG score for an ISIN
GET/api/esg/portfolioScores ESG de tout le portefeuilleESG scores for the whole portfolio

DCF

MethodPathDescriptionDescription
GET/api/dcf/simple?ticker=AAPLDCF simplifié — données Yahoo Finance uniquementSimple DCF — Yahoo Finance data only
GET/api/dcf/complete?ticker=AAPLDCF complet avec projections FCF sauvegardéesFull DCF with saved FCF projections
GET/api/dcf/params?ticker=AAPLCharge les paramètres DCF sauvegardésLoads saved DCF parameters
POST/api/dcf/paramsSauvegarde les paramètres DCFSaves DCF parameters
GET/api/dcf/portfolio?portfolio_id=…Scores DCF pour toutes les positions d'un portefeuilleDCF scores for all positions in a portfolio
Le paramètre portfolio_id est optionnel pour /api/dcf/portfolio : si absent, utilise le portefeuille principal.
The portfolio_id parameter is optional for /api/dcf/portfolio: if absent, uses the main portfolio.

ArbitrageArbitrage

MethodPathDescriptionDescription
GET/api/arbitrage/modelsListe des 7 modèles d'arbitrageList of 7 arbitrage models
GET/api/arbitrage/simulate?portfolio_id=…&model=momentum&target_portfolio_id=…Lance la simulation d'arbitrageRuns arbitrage simulation
GET/api/arb-portfoliosListe des portefeuilles secondairesList of secondary portfolios
POST/api/arb-portfoliosCrée un portefeuille secondaireCreates a secondary portfolio
PUT/api/arb-portfolios/<id>Met à jour un portefeuille secondaireUpdates a secondary portfolio
DELETE/api/arb-portfolios/<id>Supprime un portefeuille secondaireDeletes a secondary portfolio

Paramètres DCF additionnels pour model=dcf :

Additional DCF parameters for model=dcf:

ParamètreParameterDéfautDefaultDescriptionDescription
dcf_mrp5.5Prime de risque marché (%)Market risk premium (%)
dcf_terminal_g2.5Taux de croissance terminal (%)Terminal growth rate (%)
dcf_rf_eur3.5Taux sans risque EUR (%)Risk-free rate EUR (%)
dcf_rf_usd4.3Taux sans risque USD (%)Risk-free rate USD (%)
dcf_sell_thresh-5.0Seuil vente : upside < X% → vendreSell threshold: upside < X% → sell
dcf_buy_thresh5.0Seuil achat : upside > X% → acheterBuy threshold: upside > X% → buy

ClientsClients

MethodPathDescriptionDescription
GET/api/clientsListe de tous les clients avec détails portefeuillesList all clients with portfolio details
POST/api/clientsCrée un nouveau clientCreates a new client
PUT/api/clients/<id>Met à jour un clientUpdates a client
DELETE/api/clients/<id>Supprime un clientDeletes a client
GET/api/clients/<id>/reportRapport client : valeur totale en EUR, positions par portefeuilleClient report: total EUR value, positions per portfolio

UtilitairesUtilities

MethodPathDescriptionDescription
GET/api/search?q=appleRecherche ticker Yahoo FinanceYahoo Finance ticker search
GET/api/isin-lookup?ticker=AAPLRésolution ISIN via OpenFIGIISIN resolution via OpenFIGI
GET/api/cache/clearVide le cache en mémoireClears the in-memory cache

6. Modules fonctionnels6. Functional modules

6.1 Onglet Portfolio principal6.1 Main Portfolio tab

L'onglet principal affiche une table de toutes les positions du portefeuille, enrichie en temps réel par des cotations Yahoo Finance. Chaque ligne montre :

The main tab displays a table of all portfolio positions, enriched in real-time by Yahoo Finance quotes. Each row shows:

KPIs agrégés (en haut) : valeur totale du portefeuille, P&L global, meilleure/pire position.

Aggregated KPIs (top): total portfolio value, overall P&L, best/worst position.

Graphique d'allocation : camembert Chart.js par secteur ou par pays.

Allocation chart: Chart.js pie chart by sector or country.

6.2 Import CSV6.2 CSV import

Deux méthodes d'import en masse :

Two bulk import methods:

6.3 Cotations temps réel6.3 Real-time quotes

Les cotations sont récupérées via l'API non-officielle Yahoo Finance. Le serveur maintient un cache en mémoire (_yf_cache) avec une durée de vie de 5 minutes. Le crumb et les cookies de session sont gérés automatiquement.

Quotes are fetched via the unofficial Yahoo Finance API. The server maintains an in-memory cache (_yf_cache) with a 5-minute TTL. The crumb and session cookies are managed automatically.

Yahoo Finance peut retourner des erreurs 429 (rate limit) ou bloquer les requêtes en environnement d'entreprise. Configurer un proxy le cas échéant.
Yahoo Finance may return 429 errors (rate limiting) or block requests in corporate environments. Configure a proxy if needed.

6.4 Onglet Performances6.4 Performance tab

Graphique de performance normalisée (base 100) comparant le portefeuille à ses benchmarks sur la période sélectionnée (1j, 1s, 1m, 3m, 6m, 1an, 3ans). Inclut la contribution par position et les métriques de risque (VaR, CVaR) via simulation Monte Carlo.

Normalized performance chart (base 100) comparing the portfolio to its benchmarks over the selected period (1d, 1w, 1m, 3m, 6m, 1y, 3y). Includes contribution per position and risk metrics (VaR, CVaR) via Monte Carlo simulation.

6.5 Scores ESGESG Scores

Le fichier Excel .xlsx est parsé au démarrage sans dépendance externe : le fichier est ouvert comme un ZIP, les feuilles XML extraites et parsées avec ElementTree. Les scores E, S, G et global sont affichés dans la table principale et dans l'onglet Modèle.

The .xlsx Excel file is parsed at startup without external dependencies: the file is opened as a ZIP, XML sheets extracted and parsed with ElementTree. E, S, G and global scores are displayed in the main table and the Model tab.

6.6 Valorisation DCFDCF Valuation

Deux modes de calcul :

Two calculation modes:

Le résultat clé est l'upside_pct : (valeur_intrinsèque / cours_actuel - 1) × 100. Positif = sous-évalué, négatif = sur-évalué.

The key result is upside_pct: (intrinsic_value / current_price - 1) × 100. Positive = undervalued, negative = overvalued.

6.7 Onglet ArbitrageArbitrage tab

Simule un rééquilibrage de portefeuille selon 7 modèles prédéfinis :

Simulates a portfolio rebalancing according to 7 predefined models:

#ModèleModelLogique de venteSell logicLogique d'achatBuy logic
1MomentumPerformance 6m < 0Meilleure perf. sectorielle 6mSell: 6m perf < 0Best sector 6m perf
2Mean ReversionRSI > 70 (surachat)RSI < 30 (survente)Sell: RSI > 70 (overbought)Buy: RSI < 30 (oversold)
3Sector RotationSecteurs sous-performants vs indiceSecteurs surperformantsSell: underperforming sectors vs indexBuy: outperforming sectors
4Quality GrowthFaible score IA (<40) ou fort P/EScore IA élevé + croissance CASell: low AI score (<40) or high P/EBuy: high AI score + revenue growth
5Risk ParityPositions sur-pondérées vs risquePositions sous-pondéréesSell: over-weighted vs riskBuy: under-weighted
6ESG TiltMauvais score ESG (<40)Meilleur score ESG du portefeuille cibleSell: poor ESG score (<40)Buy: best ESG score in target
7DCF Valuationupside DCF < seuil (défaut -5%)upside DCF > seuil (défaut +5%)Sell: DCF upside < threshold (default -5%)Buy: DCF upside > threshold (default +5%)

Pour le modèle DCF (n°7), des paramètres additionnels sont exposés dans l'interface : MRP, taux terminal, Rf EUR, Rf USD, seuil vente, seuil achat. Ces paramètres écrasent temporairement les valeurs globales via un mécanisme try/finally.

For the DCF model (#7), additional parameters are exposed in the UI: MRP, terminal rate, Rf EUR, Rf USD, sell threshold, buy threshold. These parameters temporarily override the global values via a try/finally mechanism.

6.8 Onglet Scores DCFDCF Scores tab

Cet onglet calcule et affiche les scores DCF (upside %) pour toutes les positions d'un portefeuille sélectionné. Pour chaque ticker :

This tab calculates and displays DCF scores (upside %) for all positions of a selected portfolio. For each ticker:

  1. Si des paramètres FCF complets sont sauvegardés → utilise dcf_complete
  2. If complete FCF parameters are saved → uses dcf_complete
  3. Sinon → utilise dcf_simple (données Yahoo Finance)
  4. Otherwise → uses dcf_simple (Yahoo Finance data)

L'onglet affiche des KPI (moyenne upside, nb sous-évalués/sur-évalués), un tableau trié par upside, et un graphique à barres de distribution.

The tab shows KPIs (average upside, nb undervalued/overvalued), a table sorted by upside, and a bar distribution chart.

6.9 Onglet ClientsClients tab

Gestion complète des clients :

Full client management:

La conversion FX utilise les taux EURUSD, EURGBP, EURCHF récupérés en temps réel sur Yahoo Finance au moment de la génération du rapport.

FX conversion uses EURUSD, EURGBP, EURCHF rates fetched in real-time from Yahoo Finance at report generation time.

6.10 Onglet AnalyseAnalysis tab

Fournit l'attribution de performance BHB (Brinson-Hood-Beebower) : décomposition de l'alpha en effets allocation, sélection et interaction, par secteur et par pays.

Provides BHB (Brinson-Hood-Beebower) performance attribution: decomposition of alpha into allocation, selection and interaction effects, by sector and country.

6.11 What If

Simule l'impact sur le portefeuille de scénarios hypothétiques : changement de prix d'un actif, ajout/suppression de position, variation de taux de change. Recalcule les KPIs en temps réel sans modifier le portefeuille réel.

Simulates the portfolio impact of hypothetical scenarios: asset price change, position add/remove, FX rate variation. Recalculates KPIs in real-time without modifying the real portfolio.

6.12 Benchmark

Compare la performance du portefeuille à des indices de référence (CAC 40, S&P 500, MSCI World, etc.) sur 5 périodes prédéfinies. Les benchmarks sont construits de façon composite, pondérés par l'allocation géographique et sectorielle du portefeuille.

Compares portfolio performance against reference indices (CAC 40, S&P 500, MSCI World, etc.) over 5 predefined periods. Benchmarks are built compositionally, weighted by the portfolio's geographic and sector allocation.

7. Calculs quantitatifs7. Quantitative calculations

7.1 VaR Monte Carlo

La VaR (Value at Risk) est calculée par simulation Monte Carlo sur 100 000 scénarios :

VaR (Value at Risk) is calculated by Monte Carlo simulation with 100,000 scenarios:

  1. Récupération des rendements journaliers historiques sur 1 an pour chaque position (endpoint /api/performance)
  2. Fetch daily historical returns over 1 year for each position (endpoint /api/performance)
  3. Calcul de la matrice de covariance des rendements
  4. Calculate the return covariance matrix
  5. Génération de 100 000 scénarios par décomposition de Cholesky
  6. Generate 100,000 scenarios via Cholesky decomposition
  7. Calcul du P&L simulé pour chaque scénario
  8. Calculate simulated P&L for each scenario
  9. VaR 95% = 5e percentile de la distribution des P&L simulés
  10. VaR 95% = 5th percentile of the simulated P&L distribution

7.2 CVaR (Expected Shortfall)

La CVaR est la moyenne des pertes au-delà de la VaR :

CVaR is the average of losses beyond VaR:

CVaR_95% = E[P&L | P&L < VaR_95%]
         = moyenne des scénarios sous le 5e percentile

7.3 Attribution BHBBHB Attribution

La méthode Brinson-Hood-Beebower décompose l'alpha en trois effets :

The Brinson-Hood-Beebower method decomposes alpha into three effects:

Effet allocation  = (wp - wb) × rb
Effet sélection   = wb × (rp - rb)
Effet interaction = (wp - wb) × (rp - rb)

où : wp = poids portefeuille, wb = poids benchmark,
     rp = rendement portefeuille, rb = rendement benchmarkwhere: wp = portfolio weight, wb = benchmark weight,
       rp = portfolio return, rb = benchmark return

7.4 DCF — FormulesFormulas

DCF simplifié (données Yahoo Finance) :

Simple DCF (Yahoo Finance data):

FCF_0      = Free Cash Flow TTM (Yahoo Finance)
FCF_t      = FCF_0 × (1 + g_court_terme)^t    [t = 1..5]
VT         = FCF_5 × (1 + g_terminal) / (WACC - g_terminal)
Valeur     = Σ(FCF_t / (1+WACC)^t) + VT / (1+WACC)^5
Intrinsic  = (Valeur + Cash - Dette) / Actions
upside_pct = (Intrinsic / Prix_actuel - 1) × 100

DCF complet (projections manuelles) :

Complete DCF (manual projections):

FCF_t      = projection_t  [saisie par l'utilisateur / entered by user]
VT         = FCF_last × (1 + g_terminal) / (WACC - g_terminal)
Reste identique au mode simplifiéRest identical to simple mode

7.5 WACC

Le WACC est calculé automatiquement par le serveur :

WACC is calculated automatically by the server:

Ke  = Rf + β × MRP                        # coût des fonds propres# cost of equity
Kd  = Kd_brut × (1 - taux_imposition)     # coût de la dette après impôt# after-tax cost of debt
E/V = Equity / (Equity + Debt)
D/V = Debt   / (Equity + Debt)
WACC = (E/V) × Ke + (D/V) × Kd           # borné [4%, 25%]# clamped [4%, 25%]

Valeurs par défaut (modifiables via paramètres DCF) :Default values (overridable via DCF parameters):
MRP          = 5.5%
g_terminal   = 2.5%
Rf par devise / by currency:
  EUR → 3.5%   USD → 4.3%   GBP → 4.2%
  CHF → 1.0%   JPY → 0.5%   HKD → 3.5%

7.6 Benchmark compositeComposite benchmark

Le benchmark est construit dynamiquement en fonction du portefeuille :

The benchmark is built dynamically based on the portfolio:

  1. Pour chaque pays représenté dans le portefeuille, récupère l'indice de référence (PAYS_TO_BENCH)
  2. For each country in the portfolio, fetch the reference index (PAYS_TO_BENCH)
  3. Pondère chaque indice par le poids du pays dans le portefeuille
  4. Weight each index by the country's weight in the portfolio
  5. Calcule la performance composite journalière
  6. Calculate daily composite performance

8. Référentiels de données8. Data references

Secteurs canoniquesCanonical sectors

Le serveur normalise les noms de secteurs via un dictionnaire SECTOR_CANONICAL qui mappe les variantes Yahoo Finance vers 12 secteurs normalisés :

The server normalizes sector names via a SECTOR_CANONICAL dictionary that maps Yahoo Finance variants to 12 normalized sectors:

Secteur normaliséNormalized sectorExemples de variantesExample variants
TechnologyInformation Technology, Tech, Technologie
FinanceFinancial Services, Financials, Banks
HealthcareHealth Care, Pharma, Biotech
IndustrialsIndustriels, Industrial, Capital Goods
ConsumerConsumer Discretionary, Consumer Staples, Retail
EnergyEnergie, Oil & Gas, Utilities
MaterialsMatériaux, Basic Materials, Mining
Real EstateImmobilier, REIT
CommunicationTelecom, Media, Communication Services
OtherTout ce qui ne correspond pasAnything not matching

Indices par paysIndices by country

Le dictionnaire PAYS_TO_BENCH associe un code ISO 2 lettres à un ticker Yahoo Finance :

The PAYS_TO_BENCH dictionary maps a 2-letter ISO code to a Yahoo Finance ticker:

ISOPaysCountryTicker
FRFrance^FCHI (CAC 40)
USUSA^GSPC (S&P 500)
DEGermany / Deutschland^GDAXI (DAX)
GBUK^FTSE (FTSE 100)
JPJapan^N225 (Nikkei)
CHSwitzerland^SSMI (SMI)
Monde / GlobalWorld / GlobalURTH (iShares MSCI World)

9. Gestion des erreurs et cache9. Error handling and cache

Cache mémoireIn-memory cache

Le serveur utilise un dictionnaire _cache protégé par un threading.Lock. Les entrées sont stockées avec un timestamp et expirées automatiquement :

The server uses a _cache dictionary protected by a threading.Lock. Entries are stored with a timestamp and automatically expired:

Type de donnéesData typeTTL
Cotations Yahoo FinanceYahoo Finance quotes5 min
Données historiquesHistorical data15 min
Simulation arbitrageArbitrage simulation10 min
Calculs VaRVaR calculations30 min

Gestion des erreurs HTTPHTTP error handling

CodeCauseCause
400Corps JSON invalide ou paramètre manquantInvalid JSON body or missing parameter
404Ressource introuvable (ISIN, client ID, etc.)Resource not found (ISIN, client ID, etc.)
500Erreur interne (exception Python non gérée)Internal error (unhandled Python exception)
Toutes les réponses d'erreur ont le format {"error": "message"}. Le frontend affiche un toast d'alerte rouge pour les erreurs 4xx/5xx.
All error responses have the format {"error": "message"}. The frontend displays a red alert toast for 4xx/5xx errors.