Diagram: IoT sensors connect to all brokers + OpenRemote UI linked (ORM->UI)
This commit is contained in:
@@ -1,464 +1,453 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="fr">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml" lang="" xml:lang="">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Smart City Digital Twin - Flux de Données</title>
|
||||
<link href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@400;500;600;700&display=swap" rel="stylesheet">
|
||||
<meta charset="utf-8" />
|
||||
<meta name="generator" content="pandoc" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=yes" />
|
||||
<title>data-flow-diagram</title>
|
||||
<style>
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
/* Default styles provided by pandoc.
|
||||
** See https://pandoc.org/MANUAL.html#variables-for-html for config info.
|
||||
*/
|
||||
html {
|
||||
color: #1a1a1a;
|
||||
background-color: #fdfdfd;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'JetBrains Mono', monospace;
|
||||
background: #020617;
|
||||
min-height: 100vh;
|
||||
padding: 2rem;
|
||||
color: white;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 1400px;
|
||||
margin: 0 auto;
|
||||
max-width: 36em;
|
||||
padding-left: 50px;
|
||||
padding-right: 50px;
|
||||
padding-top: 50px;
|
||||
padding-bottom: 50px;
|
||||
hyphens: auto;
|
||||
overflow-wrap: break-word;
|
||||
text-rendering: optimizeLegibility;
|
||||
font-kerning: normal;
|
||||
}
|
||||
|
||||
.header {
|
||||
margin-bottom: 2rem;
|
||||
@media (max-width: 600px) {
|
||||
body {
|
||||
font-size: 0.9em;
|
||||
padding: 12px;
|
||||
}
|
||||
h1 {
|
||||
font-size: 1.8em;
|
||||
}
|
||||
}
|
||||
|
||||
.header-row {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 1rem;
|
||||
margin-bottom: 0.5rem;
|
||||
@media print {
|
||||
html {
|
||||
background-color: white;
|
||||
}
|
||||
body {
|
||||
background-color: transparent;
|
||||
color: black;
|
||||
font-size: 12pt;
|
||||
}
|
||||
p, h2, h3 {
|
||||
orphans: 3;
|
||||
widows: 3;
|
||||
}
|
||||
h2, h3, h4 {
|
||||
page-break-after: avoid;
|
||||
}
|
||||
}
|
||||
|
||||
.pulse-dot {
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
background: #22d3ee;
|
||||
border-radius: 50%;
|
||||
animation: pulse 2s infinite;
|
||||
p {
|
||||
margin: 1em 0;
|
||||
}
|
||||
|
||||
@keyframes pulse {
|
||||
0%, 100% { opacity: 1; }
|
||||
50% { opacity: 0.5; }
|
||||
a {
|
||||
color: #1a1a1a;
|
||||
}
|
||||
|
||||
h1 {
|
||||
font-size: 1.5rem;
|
||||
font-weight: 700;
|
||||
letter-spacing: -0.025em;
|
||||
a:visited {
|
||||
color: #1a1a1a;
|
||||
}
|
||||
|
||||
.subtitle {
|
||||
color: #94a3b8;
|
||||
font-size: 0.875rem;
|
||||
margin-left: 1.75rem;
|
||||
img {
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.diagram-container {
|
||||
background: rgba(15, 23, 42, 0.5);
|
||||
border-radius: 1rem;
|
||||
border: 1px solid #1e293b;
|
||||
padding: 1.5rem;
|
||||
overflow-x: auto;
|
||||
}
|
||||
|
||||
svg {
|
||||
height: auto;
|
||||
max-width: 100%;
|
||||
}
|
||||
h1, h2, h3, h4, h5, h6 {
|
||||
margin-top: 1.4em;
|
||||
}
|
||||
h5, h6 {
|
||||
font-size: 1em;
|
||||
font-style: italic;
|
||||
}
|
||||
h6 {
|
||||
font-weight: normal;
|
||||
}
|
||||
ol, ul {
|
||||
padding-left: 1.7em;
|
||||
margin-top: 1em;
|
||||
}
|
||||
li > ol, li > ul {
|
||||
margin-top: 0;
|
||||
}
|
||||
blockquote {
|
||||
margin: 1em 0 1em 1.7em;
|
||||
padding-left: 1em;
|
||||
border-left: 2px solid #e6e6e6;
|
||||
color: #606060;
|
||||
}
|
||||
code {
|
||||
font-family: Menlo, Monaco, Consolas, 'Lucida Console', monospace;
|
||||
font-size: 85%;
|
||||
margin: 0;
|
||||
hyphens: manual;
|
||||
}
|
||||
pre {
|
||||
margin: 1em 0;
|
||||
overflow: auto;
|
||||
}
|
||||
pre code {
|
||||
padding: 0;
|
||||
overflow: visible;
|
||||
overflow-wrap: normal;
|
||||
}
|
||||
.sourceCode {
|
||||
background-color: transparent;
|
||||
overflow: visible;
|
||||
}
|
||||
hr {
|
||||
border: none;
|
||||
border-top: 1px solid #1a1a1a;
|
||||
height: 1px;
|
||||
margin: 1em 0;
|
||||
}
|
||||
table {
|
||||
margin: 1em 0;
|
||||
border-collapse: collapse;
|
||||
width: 100%;
|
||||
min-width: 1200px;
|
||||
overflow-x: auto;
|
||||
display: block;
|
||||
font-variant-numeric: lining-nums tabular-nums;
|
||||
}
|
||||
|
||||
.cards {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
|
||||
gap: 1rem;
|
||||
margin-top: 2rem;
|
||||
table caption {
|
||||
margin-bottom: 0.75em;
|
||||
}
|
||||
|
||||
.card {
|
||||
background: rgba(15, 23, 42, 0.5);
|
||||
border-radius: 0.75rem;
|
||||
border: 1px solid #1e293b;
|
||||
padding: 1.25rem;
|
||||
tbody {
|
||||
margin-top: 0.5em;
|
||||
border-top: 1px solid #1a1a1a;
|
||||
border-bottom: 1px solid #1a1a1a;
|
||||
}
|
||||
|
||||
.card-header {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.5rem;
|
||||
margin-bottom: 0.75rem;
|
||||
th {
|
||||
border-top: 1px solid #1a1a1a;
|
||||
padding: 0.25em 0.5em 0.25em 0.5em;
|
||||
}
|
||||
|
||||
.card-dot {
|
||||
width: 8px;
|
||||
height: 8px;
|
||||
border-radius: 50%;
|
||||
td {
|
||||
padding: 0.125em 0.5em 0.25em 0.5em;
|
||||
}
|
||||
|
||||
.card-dot.cyan { background: #22d3ee; }
|
||||
.card-dot.emerald { background: #34d399; }
|
||||
.card-dot.violet { background: #a78bfa; }
|
||||
.card-dot.amber { background: #fbbf24; }
|
||||
.card-dot.rose { background: #fb7185; }
|
||||
.card-dot.orange { background: #fb923c; }
|
||||
|
||||
.card h3 {
|
||||
font-size: 0.875rem;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
.card ul {
|
||||
list-style: none;
|
||||
color: #94a3b8;
|
||||
font-size: 0.75rem;
|
||||
}
|
||||
|
||||
.card li {
|
||||
margin-bottom: 0.375rem;
|
||||
}
|
||||
|
||||
.footer {
|
||||
header {
|
||||
margin-bottom: 4em;
|
||||
text-align: center;
|
||||
margin-top: 1.5rem;
|
||||
color: #475569;
|
||||
font-size: 0.75rem;
|
||||
}
|
||||
#TOC li {
|
||||
list-style: none;
|
||||
}
|
||||
#TOC ul {
|
||||
padding-left: 1.3em;
|
||||
}
|
||||
#TOC > ul {
|
||||
padding-left: 0;
|
||||
}
|
||||
#TOC a:not(:hover) {
|
||||
text-decoration: none;
|
||||
}
|
||||
code{white-space: pre-wrap;}
|
||||
span.smallcaps{font-variant: small-caps;}
|
||||
div.columns{display: flex; gap: min(4vw, 1.5em);}
|
||||
div.column{flex: auto; overflow-x: auto;}
|
||||
div.hanging-indent{margin-left: 1.5em; text-indent: -1.5em;}
|
||||
/* The extra [class] is a hack that increases specificity enough to
|
||||
override a similar rule in reveal.js */
|
||||
ul.task-list[class]{list-style: none;}
|
||||
ul.task-list li input[type="checkbox"] {
|
||||
font-size: inherit;
|
||||
width: 0.8em;
|
||||
margin: 0 0.8em 0.2em -1.6em;
|
||||
vertical-align: middle;
|
||||
}
|
||||
.display.math{display: block; text-align: center; margin: 0.5rem auto;}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div class="container">
|
||||
<!-- Header -->
|
||||
<div class="header">
|
||||
<div class="header-row">
|
||||
<div class="pulse-dot"></div>
|
||||
<h1>Smart City Digital Twin — Flux de Données</h1>
|
||||
</div>
|
||||
<p class="subtitle">Martinique • Simulator → Brokers → Context Brokers → Visualization</p>
|
||||
</div>
|
||||
<nav id="TOC" role="doc-toc">
|
||||
<ul>
|
||||
<li><a href="#smart-city-digital-twin-diagramme-des-flux-de-données"
|
||||
id="toc-smart-city-digital-twin-diagramme-des-flux-de-données">Smart
|
||||
City Digital Twin — Diagramme des Flux de Données</a>
|
||||
<ul>
|
||||
<li><a href="#vue-densemble" id="toc-vue-densemble">Vue
|
||||
d’ensemble</a></li>
|
||||
<li><a href="#diagramme-mermaid" id="toc-diagramme-mermaid">Diagramme
|
||||
Mermaid</a></li>
|
||||
<li><a href="#description-des-flux"
|
||||
id="toc-description-des-flux">Description des flux</a>
|
||||
<ul>
|
||||
<li><a href="#génération-des-données-simulator"
|
||||
id="toc-génération-des-données-simulator">1. <strong>Génération des
|
||||
données (Simulator)</strong></a></li>
|
||||
<li><a href="#ingestion-mqtt-brokers" id="toc-ingestion-mqtt-brokers">2.
|
||||
<strong>Ingestion MQTT (Brokers)</strong></a></li>
|
||||
<li><a href="#context-brokers-ngsi-ld-sensorthings"
|
||||
id="toc-context-brokers-ngsi-ld-sensorthings">3. <strong>Context Brokers
|
||||
(NGSI-LD & SensorThings)</strong></a></li>
|
||||
<li><a href="#plateforme-iot-openremote"
|
||||
id="toc-plateforme-iot-openremote">4. <strong>Plateforme IoT
|
||||
(OpenRemote)</strong></a></li>
|
||||
<li><a href="#stockage-métriques" id="toc-stockage-métriques">5.
|
||||
<strong>Stockage & Métriques</strong></a></li>
|
||||
<li><a href="#visualisation-analyse" id="toc-visualisation-analyse">6.
|
||||
<strong>Visualisation & Analyse</strong></a></li>
|
||||
</ul></li>
|
||||
<li><a href="#technologies-clés" id="toc-technologies-clés">Technologies
|
||||
clés</a></li>
|
||||
<li><a href="#fichiers-associés" id="toc-fichiers-associés">Fichiers
|
||||
associés</a></li>
|
||||
</ul></li>
|
||||
</ul>
|
||||
</nav>
|
||||
<h1 id="smart-city-digital-twin-diagramme-des-flux-de-données">Smart
|
||||
City Digital Twin — Diagramme des Flux de Données</h1>
|
||||
<h2 id="vue-densemble">Vue d’ensemble</h2>
|
||||
<p>Ce diagramme illustre le flux complet des données IoT du simulateur
|
||||
vers les différentes couches de traitement, de stockage et de
|
||||
visualisation.</p>
|
||||
<hr />
|
||||
<h2 id="diagramme-mermaid">Diagramme Mermaid</h2>
|
||||
<pre class="mermaid"><code>graph TB
|
||||
SIM[Smart City Simulator]
|
||||
SENS[Capteurs IoT Reels]
|
||||
EMQ[EMQX]
|
||||
MOS[Mosquitto]
|
||||
BUN[BunkerM]
|
||||
ORI[Orion-LD]
|
||||
STE[Stellio]
|
||||
FRO[FROST-Server]
|
||||
ORM[OpenRemote Manager]
|
||||
KC[Keycloak]
|
||||
INF[InfluxDB]
|
||||
PRO[Prometheus]
|
||||
GEO[GeoServer]
|
||||
GRA[Grafana]
|
||||
MAP[MapStore]
|
||||
UI[OpenRemote UI]
|
||||
|
||||
<!-- Main Diagram -->
|
||||
<div class="diagram-container">
|
||||
<svg viewBox="0 0 1300 750">
|
||||
<!-- Definitions -->
|
||||
<defs>
|
||||
<marker id="arrowhead" markerWidth="10" markerHeight="7" refX="9" refY="3.5" orient="auto">
|
||||
<polygon points="0 0, 10 3.5, 0 7" fill="#64748b" />
|
||||
</marker>
|
||||
<marker id="arrowhead-cyan" markerWidth="10" markerHeight="7" refX="9" refY="3.5" orient="auto">
|
||||
<polygon points="0 0, 10 3.5, 0 7" fill="#22d3ee" />
|
||||
</marker>
|
||||
<marker id="arrowhead-emerald" markerWidth="10" markerHeight="7" refX="9" refY="3.5" orient="auto">
|
||||
<polygon points="0 0, 10 3.5, 0 7" fill="#34d399" />
|
||||
</marker>
|
||||
<marker id="arrowhead-orange" markerWidth="10" markerHeight="7" refX="9" refY="3.5" orient="auto">
|
||||
<polygon points="0 0, 10 3.5, 0 7" fill="#fb923c" />
|
||||
</marker>
|
||||
<pattern id="grid" width="40" height="40" patternUnits="userSpaceOnUse">
|
||||
<path d="M 40 0 L 0 0 0 40" fill="none" stroke="#1e293b" stroke-width="0.5"/>
|
||||
</pattern>
|
||||
</defs>
|
||||
|
||||
<!-- Background Grid -->
|
||||
<rect width="100%" height="100%" fill="url(#grid)" />
|
||||
|
||||
<!-- ===== LAYER 1: Data Sources ===== -->
|
||||
<text x="30" y="30" fill="#94a3b8" font-size="12" font-weight="600">📡 COUCHE 1 : SOURCES DE DONNÉES</text>
|
||||
|
||||
<!-- Smart City Simulator -->
|
||||
<rect x="30" y="50" width="180" height="70" rx="6" fill="#0f172a"/>
|
||||
<rect x="30" y="50" width="180" height="70" rx="6" fill="rgba(251, 146, 60, 0.3)" stroke="#fb923c" stroke-width="1.5"/>
|
||||
<text x="120" y="80" fill="white" font-size="12" font-weight="600" text-anchor="middle">Smart City Simulator</text>
|
||||
<text x="120" y="96" fill="#94a3b8" font-size="9" text-anchor="middle">Python • 10 capteurs</text>
|
||||
<text x="120" y="112" fill="#fb923c" font-size="8" text-anchor="middle">MQTT + REST API</text>
|
||||
|
||||
<!-- ===== LAYER 2: MQTT BROKERS ===== -->
|
||||
<text x="30" y="170" fill="#94a3b8" font-size="12" font-weight="600">📡 COUCHE 2 : MQTT BROKERS</text>
|
||||
|
||||
<!-- EMQX -->
|
||||
<rect x="30" y="190" width="140" height="60" rx="6" fill="#0f172a"/>
|
||||
<rect x="30" y="190" width="140" height="60" rx="6" fill="rgba(34, 211, 238, 0.3)" stroke="#22d3ee" stroke-width="1.5"/>
|
||||
<text x="100" y="215" fill="white" font-size="11" font-weight="600" text-anchor="middle">EMQX</text>
|
||||
<text x="100" y="231" fill="#94a3b8" font-size="9" text-anchor="middle">Port 11883 (MQTT)</text>
|
||||
|
||||
<!-- Mosquitto -->
|
||||
<rect x="190" y="190" width="140" height="60" rx="6" fill="#0f172a"/>
|
||||
<rect x="190" y="190" width="140" height="60" rx="6" fill="rgba(34, 211, 238, 0.3)" stroke="#22d3ee" stroke-width="1.5"/>
|
||||
<text x="260" y="215" fill="white" font-size="11" font-weight="600" text-anchor="middle">Mosquitto</text>
|
||||
<text x="260" y="231" fill="#94a3b8" font-size="9" text-anchor="middle">Port 1883 (MQTT)</text>
|
||||
|
||||
<!-- BunkerM -->
|
||||
<rect x="350" y="190" width="140" height="60" rx="6" fill="#0f172a"/>
|
||||
<rect x="350" y="190" width="140" height="60" rx="6" fill="rgba(34, 211, 238, 0.3)" stroke="#22d3ee" stroke-width="1.5"/>
|
||||
<text x="420" y="215" fill="white" font-size="11" font-weight="600" text-anchor="middle">BunkerM</text>
|
||||
<text x="420" y="231" fill="#94a3b8" font-size="9" text-anchor="middle">Port 1900 (MQTTS)</text>
|
||||
|
||||
<!-- ===== LAYER 3: CONTEXT BROKERS ===== -->
|
||||
<text x="30" y="290" fill="#94a3b8" font-size="12" font-weight="600">🔄 COUCHE 3 : CONTEXT BROKERS (NGSI-LD)</text>
|
||||
|
||||
<!-- Orion-LD -->
|
||||
<rect x="30" y="310" width="160" height="80" rx="6" fill="#0f172a"/>
|
||||
<rect x="30" y="310" width="160" height="80" rx="6" fill="rgba(52, 211, 153, 0.3)" stroke="#34d399" stroke-width="1.5"/>
|
||||
<text x="110" y="335" fill="white" font-size="11" font-weight="600" text-anchor="middle">Orion-LD</text>
|
||||
<text x="110" y="351" fill="#94a3b8" font-size="9" text-anchor="middle">NGSI-LD</text>
|
||||
<text x="110" y="367" fill="#94a3b8" font-size="8" text-anchor="middle">Port 1026</text>
|
||||
<text x="110" y="383" fill="#34d399" font-size="8" text-anchor="middle">Entities: Traffic, Air</text>
|
||||
|
||||
<!-- Stellio -->
|
||||
<rect x="210" y="310" width="160" height="80" rx="6" fill="#0f172a"/>
|
||||
<rect x="210" y="310" width="160" height="80" rx="6" fill="rgba(52, 211, 153, 0.3)" stroke="#34d399" stroke-width="1.5"/>
|
||||
<text x="290" y="335" fill="white" font-size="11" font-weight="600" text-anchor="middle">Stellio</text>
|
||||
<text x="290" y="351" fill="#94a3b8" font-size="9" text-anchor="middle">NGSI-LD</text>
|
||||
<text x="290" y="367" fill="#94a3b8" font-size="8" text-anchor="middle">Port 8080</text>
|
||||
<text x="290" y="383" fill="#34d399" font-size="8" text-anchor="middle">14 payloads entities</text>
|
||||
|
||||
<!-- FROST-Server -->
|
||||
<rect x="390" y="310" width="160" height="80" rx="6" fill="#0f172a"/>
|
||||
<rect x="390" y="310" width="160" height="80" rx="6" fill="rgba(52, 211, 153, 0.3)" stroke="#34d399" stroke-width="1.5"/>
|
||||
<text x="470" y="335" fill="white" font-size="11" font-weight="600" text-anchor="middle">FROST-Server</text>
|
||||
<text x="470" y="351" fill="#94a3b8" font-size="9" text-anchor="middle">SensorThings API</text>
|
||||
<text x="470" y="367" fill="#94a3b8" font-size="8" text-anchor="middle">21k+ observations</text>
|
||||
<text x="470" y="383" fill="#34d399" font-size="8" text-anchor="middle">PostgreSQL+Timescale</text>
|
||||
|
||||
<!-- ===== LAYER 4: IOT PLATFORM ===== -->
|
||||
<text x="30" y="430" fill="#94a3b8" font-size="12" font-weight="600">🏠 COUCHE 4 : PLATEFORME IOT (OpenRemote)</text>
|
||||
|
||||
<!-- OpenRemote Manager -->
|
||||
<rect x="30" y="450" width="200" height="90" rx="6" fill="#0f172a"/>
|
||||
<rect x="30" y="450" width="200" height="90" rx="6" fill="rgba(167, 139, 250, 0.3)" stroke="#a78bfa" stroke-width="1.5"/>
|
||||
<text x="130" y="478" fill="white" font-size="12" font-weight="600" text-anchor="middle">OpenRemote Manager</text>
|
||||
<text x="130" y="494" fill="#94a3b8" font-size="9" text-anchor="middle">Realm: Smart City</text>
|
||||
<text x="130" y="510" fill="#94a3b8" font-size="8" text-anchor="middle">33 assets IoT</text>
|
||||
<text x="130" y="526" fill="#a78bfa" font-size="8" text-anchor="middle">Port 8080 + Keycloak</text>
|
||||
|
||||
<!-- Keycloak -->
|
||||
<rect x="250" y="465" width="120" height="60" rx="6" fill="#0f172a"/>
|
||||
<rect x="250" y="465" width="120" height="60" rx="6" fill="rgba(251, 113, 133, 0.3)" stroke="#fb7185" stroke-width="1.5"/>
|
||||
<text x="310" y="490" fill="white" font-size="10" font-weight="600" text-anchor="middle">Keycloak</text>
|
||||
<text x="310" y="506" fill="#94a3b8" font-size="8" text-anchor="middle">Auth OpenID</text>
|
||||
|
||||
<!-- ===== LAYER 5: STORAGE & METRICS ===== -->
|
||||
<text x="30" y="570" fill="#94a3b8" font-size="12" font-weight="600">💾 COUCHE 5 : STOCKAGE & MÉTRIQUES</text>
|
||||
|
||||
<!-- InfluxDB -->
|
||||
<rect x="30" y="590" width="140" height="60" rx="6" fill="#0f172a"/>
|
||||
<rect x="30" y="590" width="140" height="60" rx="6" fill="rgba(120, 53, 15, 0.3)" stroke="#fbbf24" stroke-width="1.5"/>
|
||||
<text x="100" y="615" fill="white" font-size="11" font-weight="600" text-anchor="middle">InfluxDB</text>
|
||||
<text x="100" y="631" fill="#94a3b8" font-size="9" text-anchor="middle">IoT Data Bucket</text>
|
||||
|
||||
<!-- Prometheus -->
|
||||
<rect x="190" y="590" width="140" height="60" rx="6" fill="#0f172a"/>
|
||||
<rect x="190" y="590" width="140" height="60" rx="6" fill="rgba(120, 53, 15, 0.3)" stroke="#fbbf24" stroke-width="1.5"/>
|
||||
<text x="260" y="615" fill="white" font-size="11" font-weight="600" text-anchor="middle">Prometheus</text>
|
||||
<text x="260" y="631" fill="#94a3b8" font-size="9" text-anchor="middle">Metrics + Alerting</text>
|
||||
|
||||
<!-- GeoServer -->
|
||||
<rect x="350" y="590" width="140" height="60" rx="6" fill="#0f172a"/>
|
||||
<rect x="350" y="590" width="140" height="60" rx="6" fill="rgba(120, 53, 15, 0.3)" stroke="#fbbf24" stroke-width="1.5"/>
|
||||
<text x="420" y="615" fill="white" font-size="11" font-weight="600" text-anchor="middle">GeoServer</text>
|
||||
<text x="420" y="631" fill="#94a3b8" font-size="9" text-anchor="middle">WMS/WFS + PostGIS</text>
|
||||
|
||||
<!-- ===== LAYER 6: VISUALIZATION ===== -->
|
||||
<text x="650" y="170" fill="#94a3b8" font-size="12" font-weight="600">📊 COUCHE 6 : VISUALISATION & ANALYSE</text>
|
||||
|
||||
<!-- Grafana -->
|
||||
<rect x="650" y="190" width="160" height="80" rx="6" fill="#0f172a"/>
|
||||
<rect x="650" y="190" width="160" height="80" rx="6" fill="rgba(8, 51, 68, 0.4)" stroke="#22d3ee" stroke-width="1.5"/>
|
||||
<text x="730" y="218" fill="white" font-size="12" font-weight="600" text-anchor="middle">Grafana</text>
|
||||
<text x="730" y="234" fill="#94a3b8" font-size="9" text-anchor="middle">Dashboards</text>
|
||||
<text x="730" y="250" fill="#94a3b8" font-size="8" text-anchor="middle">Datasources:</text>
|
||||
<text x="730" y="266" fill="#22d3ee" font-size="8" text-anchor="middle">InfluxDB, FROST, Orion</text>
|
||||
|
||||
<!-- MapStore -->
|
||||
<rect x="830" y="190" width="160" height="80" rx="6" fill="#0f172a"/>
|
||||
<rect x="830" y="190" width="160" height="80" rx="6" fill="rgba(8, 51, 68, 0.4)" stroke="#22d3ee" stroke-width="1.5"/>
|
||||
<text x="910" y="218" fill="white" font-size="12" font-weight="600" text-anchor="middle">MapStore</text>
|
||||
<text x="910" y="234" fill="#94a3b8" font-size="9" text-anchor="middle">Cartographie</text>
|
||||
<text x="910" y="250" fill="#94a3b8" font-size="8" text-anchor="middle">Sources:</text>
|
||||
<text x="910" y="266" fill="#22d3ee" font-size="8" text-anchor="middle">GeoServer WMS</text>
|
||||
|
||||
<!-- OpenRemote UI -->
|
||||
<rect x="650" y="310" width="160" height="80" rx="6" fill="#0f172a"/>
|
||||
<rect x="650" y="310" width="160" height="80" rx="6" fill="rgba(8, 51, 68, 0.4)" stroke="#22d3ee" stroke-width="1.5"/>
|
||||
<text x="730" y="338" fill="white" font-size="12" font-weight="600" text-anchor="middle">OpenRemote UI</text>
|
||||
<text x="730" y="354" fill="#94a3b8" font-size="9" text-anchor="middle">Manager Interface</text>
|
||||
<text x="730" y="370" fill="#22d3ee" font-size="8" text-anchor="middle">Realm: Smart City</text>
|
||||
|
||||
<!-- ===== ARROWS: Data Flows ===== -->
|
||||
|
||||
<!-- Simulator → MQTT Brokers -->
|
||||
<line x1="120" y1="120" x2="100" y2="188" stroke="#fb923c" stroke-width="2" marker-end="url(#arrowhead-orange)"/>
|
||||
<text x="95" y="150" fill="#fb923c" font-size="8">MQTT</text>
|
||||
|
||||
<line x1="120" y1="120" x2="260" y2="188" stroke="#fb923c" stroke-width="2" marker-end="url(#arrowhead-orange)"/>
|
||||
|
||||
<line x1="120" y1="120" x2="420" y2="188" stroke="#fb923c" stroke-width="2" marker-end="url(#arrowhead-orange)"/>
|
||||
|
||||
<!-- MQTT Brokers → Context Brokers -->
|
||||
<line x1="100" y1="252" x2="110" y2="308" stroke="#22d3ee" stroke-width="2" marker-end="url(#arrowhead-cyan)"/>
|
||||
<text x="85" y="280" fill="#22d3ee" font-size="8">NGSI-LD</text>
|
||||
|
||||
<line x1="260" y1="252" x2="290" y2="308" stroke="#22d3ee" stroke-width="2" marker-end="url(#arrowhead-cyan)"/>
|
||||
|
||||
<line x1="420" y1="252" x2="470" y2="308" stroke="#22d3ee" stroke-width="2" marker-end="url(#arrowhead-cyan)"/>
|
||||
|
||||
<!-- Simulator → OpenRemote (REST) -->
|
||||
<line x1="180" y1="85" x2="130" y2="448" stroke="#a78bfa" stroke-width="2" stroke-dasharray="5,5" marker-end="url(#arrowhead-emerald)"/>
|
||||
<text x="160" y="250" fill="#a78bfa" font-size="8">REST API</text>
|
||||
|
||||
<!-- Simulator → InfluxDB -->
|
||||
<line x1="180" y1="100" x2="100" y2="588" stroke="#fbbf24" stroke-width="2" marker-end="url(#arrowhead)"/>
|
||||
<text x="145" y="340" fill="#fbbf24" font-size="8">HTTP</text>
|
||||
|
||||
<!-- Context Brokers → Visualization -->
|
||||
<line x1="110" y1="392" x2="730" y2="188" stroke="#34d399" stroke-width="2" marker-end="url(#arrowhead-emerald)"/>
|
||||
<text x="350" y="280" fill="#34d399" font-size="8">Query</text>
|
||||
|
||||
<line x1="290" y1="392" x2="730" y2="188" stroke="#34d399" stroke-width="2" marker-end="url(#arrowhead-emerald)"/>
|
||||
|
||||
<line x1="470" y1="392" x2="730" y2="188" stroke="#34d399" stroke-width="2" marker-end="url(#arrowhead-emerald)"/>
|
||||
|
||||
<!-- GeoServer → MapStore -->
|
||||
<line x1="420" y1="652" x2="910" y2="268" stroke="#fbbf24" stroke-width="2" marker-end="url(#arrowhead)"/>
|
||||
<text x="600" y="440" fill="#fbbf24" font-size="8">WMS/WFS</text>
|
||||
|
||||
<!-- Context Brokers → GeoServer (PostGIS) -->
|
||||
<path d="M 110 392 Q 110 500 420 590" fill="none" stroke="#34d399" stroke-width="1.5" stroke-dasharray="3,3"/>
|
||||
<text x="200" y="480" fill="#34d399" font-size="7">DB Sync</text>
|
||||
|
||||
<!-- OpenRemote → Grafana -->
|
||||
<line x1="130" y1="542" x2="730" y2="268" stroke="#a78bfa" stroke-width="2" marker-end="url(#arrowhead-emerald)"/>
|
||||
<text x="350" y="380" fill="#a78bfa" font-size="8">API Query</text>
|
||||
|
||||
<!-- All → Prometheus (Metrics) -->
|
||||
<line x1="320" y1="500" x2="260" y2="588" stroke="#fbbf24" stroke-width="1.5" stroke-dasharray="4,4"/>
|
||||
<text x="260" y="540" fill="#fbbf24" font-size="7">Metrics</text>
|
||||
|
||||
<!-- ===== LEGEND ===== -->
|
||||
<text x="1050" y="30" fill="white" font-size="11" font-weight="600">Légende</text>
|
||||
|
||||
<rect x="1050" y="42" width="16" height="12" rx="2" fill="rgba(251, 146, 60, 0.3)" stroke="#fb923c" stroke-width="1"/>
|
||||
<text x="1072" y="52" fill="#94a3b8" font-size="9">Source de données</text>
|
||||
|
||||
<rect x="1050" y="60" width="16" height="12" rx="2" fill="rgba(34, 211, 238, 0.3)" stroke="#22d3ee" stroke-width="1"/>
|
||||
<text x="1072" y="70" fill="#94a3b8" font-size="9">MQTT Broker</text>
|
||||
|
||||
<rect x="1050" y="78" width="16" height="12" rx="2" fill="rgba(52, 211, 153, 0.3)" stroke="#34d399" stroke-width="1"/>
|
||||
<text x="1072" y="88" fill="#94a3b8" font-size="9">Context Broker</text>
|
||||
|
||||
<rect x="1050" y="96" width="16" height="12" rx="2" fill="rgba(167, 139, 250, 0.3)" stroke="#a78bfa" stroke-width="1"/>
|
||||
<text x="1072" y="106" fill="#94a3b8" font-size="9">IoT Platform</text>
|
||||
|
||||
<rect x="1050" y="114" width="16" height="12" rx="2" fill="rgba(120, 53, 15, 0.3)" stroke="#fbbf24" stroke-width="1"/>
|
||||
<text x="1072" y="124" fill="#94a3b8" font-size="9">Stockage / Métriques</text>
|
||||
|
||||
<rect x="1050" y="132" width="16" height="12" rx="2" fill="rgba(8, 51, 68, 0.4)" stroke="#22d3ee" stroke-width="1"/>
|
||||
<text x="1072" y="142" fill="#94a3b8" font-size="9">Visualisation</text>
|
||||
|
||||
<line x1="1050" y1="156" x2="1066" y2="156" stroke="#34d399" stroke-width="2" marker-end="url(#arrowhead-emerald)"/>
|
||||
<text x="1072" y="159" fill="#94a3b8" font-size="9">Flux de données</text>
|
||||
|
||||
<line x1="1050" y1="174" x2="1066" y2="174" stroke="#fb923c" stroke-width="2" marker-end="url(#arrowhead-orange)"/>
|
||||
<text x="1072" y="177" fill="#94a3b8" font-size="9">MQTT</text>
|
||||
|
||||
<line x1="1050" y1="190" x2="1066" y2="190" stroke="#a78bfa" stroke-width="2" stroke-dasharray="5,5"/>
|
||||
<text x="1072" y="193" fill="#94a3b8" font-size="9">REST API</text>
|
||||
|
||||
</svg>
|
||||
</div>
|
||||
|
||||
<!-- Info Cards -->
|
||||
<div class="cards">
|
||||
<div class="card">
|
||||
<div class="card-header">
|
||||
<div class="card-dot orange"></div>
|
||||
<h3>Sources & Simulator</h3>
|
||||
</div>
|
||||
<ul>
|
||||
<li>• Smart City Simulator (Python)</li>
|
||||
<li>• 10 capteurs : Traffic, Air, Parking, Noise, Weather, Light</li>
|
||||
<li>• Intervalle : 10 secondes</li>
|
||||
<li>• Protocoles : MQTT + REST API</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<div class="card-header">
|
||||
<div class="card-dot cyan"></div>
|
||||
<h3>MQTT Brokers</h3>
|
||||
</div>
|
||||
<ul>
|
||||
<li>• EMQX : Port 11883 (public)</li>
|
||||
<li>• Mosquitto : Port 1883 (Traefik)</li>
|
||||
<li>• BunkerM : Port 1900 (TLS)</li>
|
||||
<li>• OpenRemote : Port 1883 (interne)</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<div class="card-header">
|
||||
<div class="card-dot emerald"></div>
|
||||
<h3>Context Brokers (NGSI-LD)</h3>
|
||||
</div>
|
||||
<ul>
|
||||
<li>• Orion-LD : 10 entités NGSI-LD</li>
|
||||
<li>• Stellio : 14 payloads entités</li>
|
||||
<li>• FROST-Server : 21k+ observations</li>
|
||||
<li>• Smart Data Models utilisés</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<div class="card-header">
|
||||
<div class="card-dot violet"></div>
|
||||
<h3>OpenRemote Platform</h3>
|
||||
</div>
|
||||
<ul>
|
||||
<li>• Realm : Smart City Martinique</li>
|
||||
<li>• 33 assets IoT configurés</li>
|
||||
<li>• Keycloak pour l'authentification</li>
|
||||
<li>• REST API pour les capteurs</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<div class="card-header">
|
||||
<div class="card-dot amber"></div>
|
||||
<h3>Stockage & Métriques</h3>
|
||||
</div>
|
||||
<ul>
|
||||
<li>• InfluxDB : Bucket iot_data</li>
|
||||
<li>• Prometheus : Metrics brokers</li>
|
||||
<li>• GeoServer : PostGIS + WMS</li>
|
||||
<li>• PostgreSQL : OpenRemote + FROST</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<div class="card-header">
|
||||
<div class="card-dot cyan"></div>
|
||||
<h3>Visualisation & Analyse</h3>
|
||||
</div>
|
||||
<ul>
|
||||
<li>• Grafana : Dashboards (port 3001)</li>
|
||||
<li>• MapStore : Cartographie WMS</li>
|
||||
<li>• OpenRemote UI : Manager Smart City</li>
|
||||
<li>• Datasources : InfluxDB, FROST, Orion</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Footer -->
|
||||
<p class="footer">
|
||||
Smart City Digital Twin Martinique • Stack complet déployé sur digitribe.fr •
|
||||
Dernière mise à jour : 04 Mai 2026
|
||||
</p>
|
||||
</div>
|
||||
SIM --> EMQ
|
||||
SIM --> MOS
|
||||
SIM --> BUN
|
||||
SENS --> EMQ
|
||||
SENS --> MOS
|
||||
SENS --> BUN
|
||||
SENS -.-> ORM
|
||||
EMQ --> ORI
|
||||
EMQ --> STE
|
||||
EMQ --> FRO
|
||||
EMQ --> ORM
|
||||
MOS --> ORM
|
||||
BUN --> ORM
|
||||
ORM --> UI
|
||||
ORM -.-> KC
|
||||
SIM --> INF
|
||||
ORI --> GRA
|
||||
STE --> GRA
|
||||
FRO --> GRA
|
||||
ORI -.-> GEO
|
||||
STE -.-> GEO
|
||||
FRO -.-> GEO
|
||||
GEO --> MAP
|
||||
ORM --> GRA
|
||||
EMQ -.-> PRO
|
||||
ORI -.-> PRO
|
||||
STE -.-> PRO
|
||||
ORM -.-> PRO</code></pre>
|
||||
<hr />
|
||||
<h2 id="description-des-flux">Description des flux</h2>
|
||||
<h3 id="génération-des-données-simulator">1. <strong>Génération des
|
||||
données (Simulator)</strong></h3>
|
||||
<ul>
|
||||
<li><strong>Smart City Simulator</strong> (Python) génère des données
|
||||
pour 10 capteurs (Traffic, Air Quality, Parking, Noise, Weather,
|
||||
Light)</li>
|
||||
<li>Intervalle de publication : 10 secondes</li>
|
||||
<li>Protocoles : MQTT (vers brokers uniquement)</li>
|
||||
<li><strong>⚠️ Projet</strong> : Le simulateur n’envoie PAS directement
|
||||
à OpenRemote (pas de REST API)</li>
|
||||
</ul>
|
||||
<h3 id="ingestion-mqtt-brokers">2. <strong>Ingestion MQTT
|
||||
(Brokers)</strong></h3>
|
||||
<ul>
|
||||
<li><strong>EMQX</strong> (port 11883) : Broker public, reçoit tous les
|
||||
capteurs</li>
|
||||
<li><strong>Mosquitto</strong> (port 1883) : Via Traefik, accès
|
||||
externe</li>
|
||||
<li><strong>BunkerM</strong> (port 1900) : MQTTS (TLS), accès
|
||||
sécurisé</li>
|
||||
</ul>
|
||||
<h3 id="context-brokers-ngsi-ld-sensorthings">3. <strong>Context Brokers
|
||||
(NGSI-LD & SensorThings)</strong></h3>
|
||||
<ul>
|
||||
<li><strong>Orion-LD</strong> : Reçoit les données au format NGSI-LD
|
||||
<ul>
|
||||
<li>10 entités (TrafficFlowObserved, AirQualityObserved, etc.)</li>
|
||||
<li>Smart Data Models utilisés</li>
|
||||
</ul></li>
|
||||
<li><strong>Stellio</strong> : Alternative NGSI-LD
|
||||
<ul>
|
||||
<li>14 payloads entités</li>
|
||||
<li>Contexte :
|
||||
<code>https://uri.etsi.org/ngsi-ld/v1/ngsi-ld-core-context.jsonld</code></li>
|
||||
</ul></li>
|
||||
<li><strong>FROST-Server</strong> : SensorThings API
|
||||
<ul>
|
||||
<li>21 256+ observations</li>
|
||||
<li>PostgreSQL + TimescaleDB</li>
|
||||
</ul></li>
|
||||
</ul>
|
||||
<h3 id="plateforme-iot-openremote">4. <strong>Plateforme IoT
|
||||
(OpenRemote)</strong></h3>
|
||||
<ul>
|
||||
<li><strong>OpenRemote Manager</strong> (realm <code>smartcity</code>)
|
||||
<ul>
|
||||
<li>33 assets IoT configurés</li>
|
||||
<li>Carte Martinique (mapsettings.json)</li>
|
||||
<li>Réception via <strong>MQTT Agent</strong> depuis les brokers (EMQX,
|
||||
Mosquitto, BunkerM)</li>
|
||||
<li>Peut aussi recevoir directement des capteurs IoT (via MQTT)</li>
|
||||
</ul></li>
|
||||
<li><strong>Keycloak</strong> : Authentification OpenID Connect
|
||||
<ul>
|
||||
<li>Client <code>openremote</code> avec Service Account</li>
|
||||
<li>Token endpoint :
|
||||
<code>/auth/realms/smartcity/protocol/openid-connect/token</code></li>
|
||||
</ul></li>
|
||||
</ul>
|
||||
<h3 id="stockage-métriques">5. <strong>Stockage &
|
||||
Métriques</strong></h3>
|
||||
<ul>
|
||||
<li><strong>InfluxDB</strong> : Stockage temporel pour Grafana
|
||||
<ul>
|
||||
<li>Bucket : <code>iot_data</code></li>
|
||||
<li>Datasource dans Grafana</li>
|
||||
</ul></li>
|
||||
<li><strong>Prometheus</strong> : Collecte des métriques
|
||||
<ul>
|
||||
<li>MQTT brokers, Context brokers, OpenRemote</li>
|
||||
</ul></li>
|
||||
<li><strong>GeoServer</strong> : Données géospatiales
|
||||
<ul>
|
||||
<li>PostGIS pour centralisation</li>
|
||||
<li>WMS/WFS pour MapStore</li>
|
||||
</ul></li>
|
||||
</ul>
|
||||
<h3 id="visualisation-analyse">6. <strong>Visualisation &
|
||||
Analyse</strong></h3>
|
||||
<ul>
|
||||
<li><strong>Grafana</strong> (port 3001)
|
||||
<ul>
|
||||
<li>Dashboard : <code>smartcity-martinique-2026</code></li>
|
||||
<li>Datasources : InfluxDB, FROST, Orion-LD</li>
|
||||
</ul></li>
|
||||
<li><strong>MapStore</strong> : Cartographie
|
||||
<ul>
|
||||
<li>Sources WMS/WFS depuis GeoServer</li>
|
||||
</ul></li>
|
||||
<li><strong>OpenRemote UI</strong> : Manager Interface
|
||||
<ul>
|
||||
<li>Visualisation des assets realm Smart City</li>
|
||||
</ul></li>
|
||||
</ul>
|
||||
<hr />
|
||||
<h2 id="technologies-clés">Technologies clés</h2>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Composant</th>
|
||||
<th>Technologie</th>
|
||||
<th>Port</th>
|
||||
<th>Statut</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>Simulator</td>
|
||||
<td>Python + paho-mqtt</td>
|
||||
<td>Interne</td>
|
||||
<td>✅ Actif</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>EMQX</td>
|
||||
<td>MQTT Broker</td>
|
||||
<td>11883</td>
|
||||
<td>✅ Connecté</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Orion-LD</td>
|
||||
<td>NGSI-LD Broker</td>
|
||||
<td>1026</td>
|
||||
<td>⚠️ À vérifier</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Stellio</td>
|
||||
<td>NGSI-LD Broker</td>
|
||||
<td>8080</td>
|
||||
<td>⚠️ À vérifier</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>FROST-Server</td>
|
||||
<td>SensorThings API</td>
|
||||
<td>8080</td>
|
||||
<td>⚠️ À vérifier</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>OpenRemote</td>
|
||||
<td>IoT Platform</td>
|
||||
<td>8080</td>
|
||||
<td>⚠️ 403 (Service Account)</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>InfluxDB</td>
|
||||
<td>Time Series DB</td>
|
||||
<td>8086</td>
|
||||
<td>✅ Configuré</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Grafana</td>
|
||||
<td>Visualization</td>
|
||||
<td>3001</td>
|
||||
<td>✅ Dashboard créé</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>GeoServer</td>
|
||||
<td>GeoServer</td>
|
||||
<td>8080</td>
|
||||
<td>⚠️ À intégrer</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Prometheus</td>
|
||||
<td>Metrics</td>
|
||||
<td>9090</td>
|
||||
<td>✅ En cours</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<hr />
|
||||
<h2 id="fichiers-associés">Fichiers associés</h2>
|
||||
<ul>
|
||||
<li><strong>Simulator</strong> :
|
||||
<code>~/smart-city-digital-twin-martinique/simulator.py</code></li>
|
||||
<li><strong>Dashboard Grafana</strong> :
|
||||
<code>~/smart-city-digital-twin-martinique/grafana_dashboard_smartcity.json</code></li>
|
||||
<li><strong>Ce diagramme</strong> :
|
||||
<code>~/smart-city-digital-twin-martinique/data-flow-diagram.md</code></li>
|
||||
<li><strong>Session Resume</strong> :
|
||||
<code>~/smart-city-digital-twin-martinique/session_resume_2026-05-04.md</code></li>
|
||||
</ul>
|
||||
<hr />
|
||||
<p><strong>Dernière mise à jour :</strong> 04 Mai 2026<br />
|
||||
<strong>Projet :</strong> Smart City Digital Twin Martinique<br />
|
||||
<strong>URL Grafana :</strong>
|
||||
http://localhost:3001/d/smartcity-martinique-2026</p>
|
||||
</body>
|
||||
</html>
|
||||
|
||||
Reference in New Issue
Block a user