Afficher le texte sourceAnciennes révisionsLiens de retourHaut de page Table des matières Principe Implémentation Modèle de données Sensors Analyses AnalysisItem ActiveSensor Côté lib Côté modèle Capteurs Les capteurs sont objets qui ont la capacité de relevés des mesures physiques. Ils transmettent les valeurs régulièrement ou sur changement notable. Ils peuvent être indépendants ou embarqués. Cette spécification traite principalement du premier cas. Spécification en cours de rédaction Principe Pour récupérer les informations des capteurs, il existe plusieurs méthodes : Le capteur pousse directement les données en web-service dans Ekylibre via l'API normalisée. Un utilisateur enregistre un fichier de données issu de capteurs Ekylibre interroge le capteur directement pour récupérer les valeurs à interval régulier ou en mode manuel Ekylibre interroge le serveur de centralisation des données du capteur pour récupérer les valeurs à interval régulier ou en mode manuel Cela étant dit, les objectifs sont : Permettre de développer rapidement des contrôleurs de capteurs pour récupérer les valeurs. Récupérer les valeurs centralisées de capteurs, ou en accès direct via un service web REST Pour cela, il faudra définir chaque capteur utilisé sur l'exploitation et son mode de récupération de données. En fonction des capteurs, une méthode de récupération des données (retrieve) devra être définie. Les contrôleurs de capteurs permettront à terme de configurer ceux qui sont configurables. Dans l'immédiat, la méthode sera appelée toutes les heures. Implémentation Modèle de données Le modèle doit permettre de recenser les capteurs et stocker les valeurs qu'ils mesurent. De plus, ce valeurs doivent être mise en lien avec le sujet de la mesure (équipement hôte, parcelle…). Sensors Une table sensors permet de stocker les capteurs : vendor_euid~: EUID du fabricant. Ex.~: previmeteo, weenat… model_euid~: (Ex.~: weather_plus3502, hygromax200…) name~: (Ex.~: capteur température n°3…) active~: Si le capteur est actif ou non retrieval_mode~: Mode de récupération des valeurs manual, automatic access_parameters~: Paramètres demandé par le contrôleur (stocké en JSON). Exemple~: id capteur externe, id client externe, clef API… product ⇒ Product~: Produit du capteur (si approvisionné) embedded~: Si le capteur est embarqué host ⇒ Product~: Hôte du capteur embarqué stamps EUID signifie External Unique ID. Analyses La table analyses permet de stocker les relevés et en cas de problème, l'erreur remontée : product ⇒ Product host ⇒ Product sensor ⇒ Sensor mode : mode temporel instantané ou sur un période (instant, period) stopped_at (pour period) return_status (ok, error) return_explanation (text) geolocation nature number (reference_number) sampled_at analysed_at stamps AnalysisItem La table analysis_items permet de stocker les valeurs du relevé : analysis indicator_name (température, pluviométrie cumulée…) *value Une base de fabricants et de matériels sera nécessaire. ActiveSensor Le module ActiveSensor doit permettre de définir rapidement la connexion à un capteur. Une méthode par mode de récupération de données (une par fournisseur pour l'instant) lib/previmeteo/generic_controller.rb class Previmeteo::GenericController < ActiveSensor::Controller has_parameter :id has_parameter :api has_parameter :id_station has_parameter :url, default: "http://my.previmeteo.com/api" # Méthode appelée par ActiveSensor pour récupérer les valeurs # La méthode dispose d'un jeu de méthode permettant de récupérer # le fabricant (''vendor''), le modèle (''model'') et les # informations du capteur en général. # La méthode doit retourner un hash avec les différentes valeurs mesurées, # la géolocalisation et les informations temporelles. def retrieve(options = {}) # Requête JSON et retraitement des valeurs end end lib/previmeteo.rb ... ActiveSensor.register( :previmeteo, :weather_2000, label: 'Weather 2000/2001', # I18n à voir description: 'Weather station ....', # I18n indicators: [:temperature, :cumulated_rainfall, :wind_speed, :hygrometry], image: '/path/to/beautiful/image.png', # 500px × 500px controller: 'Previmeteo::GenericController' ) ActiveSensor.register( :previmeteo, :weather_4000, label: { fra: 'Weather 4000/4001', jpn: '気象センサ4000/4001' }, description: 'Weather station 4000 series ....', # I18n indicators: [:temperature, :cumulated_rainfall, :wind_speed, :hygrometry, :sunshine, :atmospheric_pressure], image: '/path/to/beautiful/image.png', # 500px × 500px controller: 'Previmeteo::GenericController' ) # Une approche YAML peut être envisagée, dans ce cas-là # le chemin des images peut-être envisagé en relatif s'il # ne commence pas par un '/' ActiveSensor.register_many('config/sensors.yml') ... Le fichier de conf YAML est une idée. À voir pour la pertinence. config/sensors.yml previmeteo: weather_2000: label: "Weather 2000/2001" description: "Weather station ..." indicators: - temperature - cumulated_rainfall - wind_speed - hygrometry image: "/path/to/beautiful/image.png" controller: "Previmeteo::GenericController" weather_4000: label: fra: "Weather 4000/4001" jpn: "気象センサ4000/4001" description: "Weather station 4000 series..." indicators: - temperature - cumulated_rainfall - wind_speed - hygrometry - sunshine - atmospheric_pressure image: "/path/to/beautiful/image.png" controller: "Previmeteo::GenericController" ... Il y a une méthode par mode de récupération de données (soit une par fournisseur pour l'instant). Côté lib Le module ActiveSensor permet de gérer la base de données de capteurs via plusieurs méthodes~: vendors : pour lister les fabricants equipments_of : pour retourner la liste des équipements d'un fabricant register(vendor, model, options={}) : pour enregistrer un matériel erase(vendor, model) : pour le supprimer find(vendor, model) : pour le trouver (retourne une instance ActiveSensor::Equipment) connect(vendor, model, access_parameter={}) : pour récupérer une instance ActiveSensor::Connection La classe ActiveSensor::Equipment permet de stocker la description d'un équipement et d'accéder à ces informations (avec support i18n). Elle sert de proxy pour récupérer les paramètres de la méthode. La classe ActiveSensor::Connection permet de gérer la connexion au capteur. Un new initialise la connexion, un close la ferme. Aujourd'hui le close n'est pas nécessaire mais à implémenter pour les futurs capteurs qui le nécessiteront. Cette classe implémente la méthode retrieve qui permet d'appeler le contrôleur. Résultat d'un relevé de capteur sous représentation YAML : --- status: ok sampled_at: 2015-..... sampling_temporal_mode: instant # optional nature: meteorological_analysis # optional geolocation: Charta::Point # optional values: indicator_1: a indicator_2: b ... En cas d'erreur : --- status: error message: Vivamus mattis ullamcorper nibh, non sollicitudin nisl luctus nec. Praesent at rutrum diam. Aliquam nulla ante, lobortis vel cursus id, varius eu erat. Sed venenatis scelerisque sem, et pretium neque posuere quis. Morbi pretium tincidunt ipsum, vel fringilla sem. Nunc ac posuere leo. Vivamus non auctor nunc, vel commodo elit. Côté modèle Au niveau modèle, il faut prévoir une méthode pour effectuer la récupération des valeurs~: class Sensor < Ekylibre::Record::Base ... # Parcourt et execute les tâches de récupération # pour chacun des capteurs def self.retrieve_all(mode) where(mode: mode).find_each do |sensor| connection = ActiveSensor.get(vendor, model, sensor.access_parameters) results = connection.retrieve(started_at: ..., stopped_at: ...) # Traiter et sauvegarder les résultats, gérer les erreurs end end ... end OSS sidekiq ne gérant pas les tâches programmées, voir pour Crono : https://github.com/plashchynski/crono En fait sidekiq-cron doit faire l'affaire à voir avec Apartment. fr/specs/sensors.txt Dernière modification: 2016/08/26 21:06(modification externe)