Thématiques principales

lundi 26 février 2018

Dépôt Debian signé

Dans un article précédent nous avions traité de la construction de dépôts debian. Basiquement nous nous étions contenté de l’initialisation du listing des packages du dépôt en effectuant un scanpackage [1].

Aujourd’hui de façon à rendre un peu plus fiable et sécurisé les paquets et fournir plus de garanties aux utilisateurs du dépôts, nous allons regarder comment signer les éléments du dépôts, mais nous allons aussi industrialiser un peu la méthode de production du dépôt.

Pour cela nous allons tout d’abord récupérer reprepro [2] et gpg2 [3-4]. On aurait pu faire sans reprepro mais bon, quand il existe un outil qui sait faire autant ne pas s’en priver [5-6].

Générer la clef pour signer le dépôt

Tout d’abord il faut construire une clef pour notre futur dépôt et on vérifie la présence de notre clef dans le trousseau

gpg2 --gen-key
gpg2 --list-keys

Puis on export cette clef dans répertoire accessible au travers de votre serveur apache (un chemin proche de l’url du futur repo par exemple)

gpg2 --armor --export votreNom@mail.com >> /var/www/pathInApache/key/keyName.gpg.key

Ici par exemple notre clef sera accessible à l'adresse http://localhost/pathInApache/key/keyName.gpg.key. Pour l’ajouter il faudra ajouter la clef publique en mode admin (en root ou en ajoutant des sudo

wget -O - http://hostserver/pathInApache/key/keyName.gpg.key | apt-key add -

Comme ça lorsque l’on aura a faire le apt-get update, apt sera capable de vérifier la signature, grâce à la clef.

Construction du dépôt

Une fois la clef configurée, il ne nous reste plus qu'à construire le dépôt pour mettre à disposition les paquets Debian. Pour ce faire, nous allons dans un premier temps utiliser reprepro qui va automatiser une très grosse partie du travail en partant d’une config et d’un répertoire de livraison dans lequel nous déposerons nos paquets à la suite de leur production.

Il nous faut tout d’abord définir un répertoire accessible via http donc un répertoire tel que /var/www/apt par exemple. Au passage dans ce répertoire on peut y placer notre répertoire key, qui contient la clef publique du dépôt.

Dans ce répertoire apt nous allons y créer un répertoire livraison dédié aux paquets Debian. A côté de celui ci nous allons également créer un répertoire conf dans lequel on va déposer un fichier que l’on nommera distributions. Ce fichier contiendra toutes les informations nécessaire à reprepro pour initialiser le dépôt et l’alimenter.

Ainsi ce fichier doit contenir les champs suivants [10]:

Origin: Votre nom ou un url 
Label: monLabel 
Suite: stable 
Codename: le nom code de votre projet comme wheeze ou xenial par exemple “monCode” 
Version: 1.0 
Architectures: i386 amd64 armhf 
Components: all non-free contrib 
Description: Un peu de blabla 
SignWith: yes

Le paramètre SignWith est essentiellement le plus important pour ce qui nous préoccupe, c’est a dire de faire un dépôt signé. A la place du yes, il est possible de mettre la clef GPG mais avec le yes, reprepro ira directement la chercher dans le trousseau.

Ainsi on va avoir l’arborescence suivante:
  • /var/www/apt/conf/distributions
  • /var/www/apt/key/keyName.gpg.key
  • /var/www/apt/livraison/
On met un Debian dans le répertoire livraison et on applique la commande suivante:


APT_DIR=”/var/www/apt”reprepro --dbdir $APT_DIR/db --confdir $APT_DIR/conf -b $APT_DIR/deb include monCode $APT_DIR/livraison/*.deb

reprepro va procéder a l’analyse du répertoire livraison en récupérer la dernière version des Debian présents et les classer dans un répertoire deb/pool. Dans ce même répertoire, il va constituer un répertoire dists dans lequel il déposera l'équivalent du scanpackage avec sa version signée qui permettra au client d’identifier notre dépôt avec la clef publique qu’il aura obtenu. Le répertoire db est un répertoire de travail de reprepro, nous ne nous attarderons pas dessus.

Bien sur pour à chaque nouvelle production des paquets, il faudra rappeler ce script. Pour cela, il est possible d’utiliser le daemon mini-dinstall [11-13]. Cela sera peut être l’occasion d’un autre article.

Pour les plus avisés qui voudront aller vraiment plus loin, je vous invite lire l’article de Vincent qui reprend un cas d’utilisation complet [9]

Note (26/08/2018) : attention a utiliser les commandes gpg2 avec sudo de facon a ce que les clefs soient accessibles lors de l'appel de reprepro qui se fait assez logiquement aussi en sudo (puisque c'est pour initialiser le depot.... )

Note 2 (26/08/2018) Sinon pour convertir de gpg a gpg2 et reciproqement:

gpg2 --export-secret-keys | gpg --import -
gpg --export-secret-keys | gpg2 --import -

Références

[1] https://un-est-tout-et-tout-est-un.blogspot.fr/2017/12/faire-un-depot-debian.html
[2] https://doc.ubuntu-fr.org/tutoriel/comment_creer_depot
[3] https://www.gnupg.org/
[4] https://doc.ubuntu-fr.org/gnupg#utilisation_et_configuration
[5] https://wiki.debian-fr.xyz/Faire_un_d%C3%A9pot_sign%C3%A9_ou_non
[6] http://blog.glehmann.net/2015/01/27/Creating-a-debian-repository/
[7] https://www.francoz.net/doc/gpg/x218.html
[8] http://www.serveur-linux.info/2012/01/depot-personnalise-paquets-debian/
[9] https://vincent.bernat.im/fr/blog/2014-depots-apt-locaux
[10] https://blog.packagecloud.io/eng/2017/03/23/create-debian-repository-reprepro/
[11] https://github.com/shartge/mini-dinstall
[12] https://manpages.debian.org/stretch/mini-dinstall/mini-dinstall.1.en.html
[13] https://debian-handbook.info/browse/fr-FR/stable/sect.setup-apt-package-repository.html

samedi 24 février 2018

Agilité: Combinatoire d'activité

Dans un article précédent [1] nous avons vu un modèle de processus de développement dans lequel je faisais intervenir 5 acteurs clefs responsables des axes majeurs intervenant dans le développement logiciel:
  • axe fonctionnel : le PO
  • axe technique : l’architecte
  • axe process : le scrum master
  • axe IVQ : le responsable IVQ (Intégration Validation Qualification)
  • axe savoir faire : le développeur


Je suis bien sûr très intéressé par votre opinion concernant mon avis sur le sujet. Alors n’hésitez pas à mettre des commentaires.

Références:


[1] http://un-est-tout-et-tout-est-un.blogspot.fr/2018/02/integration-continue.html

mercredi 21 février 2018

Intégration continue

Petit aparté pour parler un peu de l'intégration continu. Nous avions évoqué un peu le sujet dans l’article précédent [1] sur Gradle qui en est tout comme Maven [2] un élément et outil central à la construction d’un composant logiciel. Cependant, si nous avions décrit son rôle dans le processus de développement, nous n'avons pas décrit qu’elles sont les autres outils qui peuvent nous aider a automatiser l’ensemble du processus, nous aider à mener à bien l’entreprise de production logiciel complet, de A a Z.

Contextualisation

Repartons d’un processus de développement de base. Nous en avions vu quelques un dans l’article [3]. En voici un, sûrement perfectible, dans lequel nous utilisons une approche agile au sein de laquelle vont intervenir nos outils d'intégration continue.




Sans forcément faire un long discours explicatif des différents éléments de ce schéma (qui n’est qu’un modèle parmi d’autres possibles), nous pouvons décrire ce processus comme suit:

A partir de l’idée du client, sont définies un certain nombre de spécifications fonctionnelles plus ou moins raffinées. Ces spécification sont injectées, une fois suffisamment mature et dont la valeur ajoutée est considérée comme suffisamment significative, dans un certain nombre de Sprint sous la forme de Stories fonctionnelles et ou techniques. Le but final de l’approche étant de produire un certain nombre d'artefacts évoluant au fil d’un certain nombre de versions

Différents acteurs cités ici ont des rôles spécialisés selon les différents axes majeurs du développement logiciels :

  • axe fonctionnel : le PO
  • axe technique : l’architecte
  • axe process : le scrum master
  • axe IVQ : le responsable IVQ (Intégration Validation Qualification)
  • axe savoir faire : le développeur
La collaboration de ces différents acteurs est primordiale (et a mon sens, l’absence de l’un d’eux ne peut que mener à un désastre mais nous y reviendrons lorsque nous traiterons de la combinatoire de leur activités).

Nous avons déjà parler de l’approche agile mais nous pouvons constater ici qu’une phase importante du processus concerne la sortie de la partie cyclique. Cette phase peut être appeler livraison car elle correspond à la finalisation du ou des développements, et correspond au final à la livraison d’un nouvel incrément fonctionnel par l’ajout de nouveaux morceaux de code. Il faut comprendre que cette phase n’est pas terminale mais itérative comme l’est le développement et consiste à soutenir le développement en permettant la validation/livraison a chaque itération.

L'integration Continue

Cette phase est en fait appeler la phase d’intégration continue. Elle provient du besoin de tester systématiquement le code source et les nouvelles fonctionnalités apportées tout en garantissant la non régression des fonctionnalités déjà développées précédemment.


Mot d'ordre : automatisation

Dans ce schéma, le processus d'intégration continu fait intervenir un ensemble de composants en interaction et répondant à différents besoins. En entrée de l'intégration continu nous avons l’outil de gestion des sources (tel que Git [4], SVN [5] ou Mercurial [6]) dans lequel les développeurs déposeront le code produit et tester localement unitairement.

Ceci n’est cependant clairement pas suffisant car si un ajout de code peut être correct sur le poste du développeur et même en considérant que ce poste est conforme à un standard commun à toute l'équipe, il persistera toujours des différences sans compter les différences évidentes entre le poste de dev et la configuration d’un serveur cible.


Feed-back

Pour résoudre ces problèmes, intervient alors la phase d'intégration continu. Elle va permettre de procéder à une construction complète, automatisé et régulière de l’ensemble du composant logiciel soit de façon journalière, soit a chaque modification du référentiel de code, voir les deux. En procédant ainsi, l'intégration continu permettra la validation dans des plateforme de référence, de l’ensemble de fonctionnalités en déroulant l’ensemble des tests prévus (à noter que ces tests sont définis selon des niveaux différents, N1: tests unitaires, N2 tests d'intégrations, N3 : tests fonctionnels; les niveaux N2 et N3 sont souvent fusionnés). Les tests une fois validés, les développement réalisés par les développeurs sont alors intégré ensemble au sein d’une même branche ou de nouvelles validations sont déroulées (voila le coté intégration en continu).

Dans les faits, les sources sont récupérées par un outil d'orchestration tel que Jenkins [7] ou Travis [8] qui par configuration va appliquer un certain nombre de processus via un outil de build comme maven ou gradle ou directement sur la branche contenant les sources.

Procéduralement l’outil d’orchestration va devoir:

  • construire le composant (via maven [9] ou gradle [10]) en s’appuyant sur un entrepôt de composant (artifactory [11] ou nexus [12])
  • utiliser les éléments produit pour effectuer des tests unitaires
  • utiliser les éléments produit pour effectuer des tests fonctionnels dans un plateforme cible (virtuelle VM/docker ou non) avec des outils tels que robotframework [13] , sikuli [14]
  • effectuer de l’analyse de code à l’aide d’un outil comme sonar [15]
  •  produire de la documentation à l’aide d’outils comme maven site [16] ou java doc [17]


Vers le continuous delivery et le DevOps

En parallèle de cette approche ou le but est de vérifier au plus tôt l’absence de défauts mais aussi de problème d'intégration, il est considéré aujourd’hui de nouvelles approches par l’utilisation de conteneur versionable et livrable directement au client.

Ces nouvelles approches permettent au développeur de disposer d’un environnement de test ( voir de développement) local beaucoup plus proche et conforme à ce que sera la cible chez le client. Ces approches portées par des logiciels comme Docker fournissent des moyens beaucoup plus simple et élémentaires de validation et d'intégration en rapprochant le développeur de la plateforme cible cependant, elle nécessite l’utilisation par le client d’architecture spécifique basé sur ce type de conteneur. 


Facilitant d’un coté la maintenance, ces solutions doivent malgré tout, “en solution de virtualisation”, fournir des moyens de sécurisation et d’optimisation des performances au moins équivalentes aux solutions conventionnelles.

Conclusion

Dans ce blog, nous avons déjà traité des sujets tels que Docker. Il ne fait aucun doute que ce type de technologies ont leur adepte, et à juste titre. Cependant, même si ces approches ont leur avantages, il me semble que les approches conventionnelles (parce que omniprésente) gardent elles aussi leur points forts et que les solutions de productions logicielles futurs devront surtout composer avec des approches mixtes.

Il n’en reste pas moins que l'intégration continu est un environnement fortement outillé. Certains de ces outils, comme Maven, Gradle ou même la production documentaire, ont été évoqué dans différents articles. Pour les prochains articles, afin d’affiner notre vision des possibilités de l'intégration continu et des architectures possible la guidant, nous tacherons de rentrer un peu plus dans le détails de ces autres outils

References

[1] http://un-est-tout-et-tout-est-un.blogspot.com/2018/01/gradle.html
[2] http://un-est-tout-et-tout-est-un.blogspot.com/2017/12/maven-introduction.html
[3] http://un-est-tout-et-tout-est-un.blogspot.com/2017/12/les-processus-de-developpement-ou.html
[4] https://git-scm.com/
[5] https://subversion.apache.org/
[6] https://www.mercurial-scm.org/
[7] https://jenkins.io/
[8] https://travis-ci.org/
[9] https://maven.apache.org/
[10] https://gradle.org/
[11] https://jfrog.com/artifactory/
[12] https://www.sonatype.com/nexus-repository-sonatype
[13] http://robotframework.org/
[14] http://www.sikuli.org/
[15] https://www.sonarqube.org/
[16] https://maven.apache.org/plugins/maven-site-plugin/
[17] https://maven.apache.org/plugins/maven-javadoc-plugin/

lundi 19 février 2018

Google Street View API

Petit test d’intégration d’utilisation de Google street view dans une page.

Alors bien sur il faut d'abord une clef ici [1].

Ensuite tout bêtement on interroge l'API en lui spécifiant les paramètres de localisation et d'orientation.

Par exemple prenons la place d'arme de Douai de coordonnées 50.367610,203.082489

il faudra ensuite renseigner quelques paramètres tels que :

  • size : le format de l'image
  • location : les coordonnes
  • fov : le zoom, a 0 on a le grossissement max, autour de 100 on a une vision assez large de la rue.
  • heading : orientation de 0 a 360° par défaut a 90 (a gauche)
  • pitch : l’assiette ou en gros, l'orientation haut/bas sachant que 10° c'est plutôt bien
  • key: la clef que Google vous aura donnée

Voila il ne reste plus qu'a construire notre requête:

https://maps.googleapis.com/maps/api/streetview?size=400x400&location=50.367610,203.082489&fov=1000&heading=360&pitch=10&key=XXXXXXXXXXX

Ce qui donnera:



Nous verrons ce que nous pourrons en faire de cette API...

Références:


[1] https://developers.google.com/maps/documentation/streetview/?hl=fr

samedi 17 février 2018

IA : Petit point de littérature

Petit retour sur quelques lectures du début d'année .

Un premier livre qui donne des bases théoriques et techniques complètes en machine learning, pour ceux qui aiment le python je recommande vivement, et pour les autres aussi car Scikit learn est un incontournable, donc c'est aussi une bonne occasion de se mettre au python.

A destination d'un public avec un minimum de bagages techniques...

Machine Learning avec Scikit-Learn




Le second livre est traite du deep learning. Honnêtement, un peu déçu, l'ouvrage s'adresse vraiment a qui ne connait vraiment rien sur le sujet, (même pas qu'il nécessite de maîtriser quelques rudiments de calcul matriciel), en même temps, il est vraiment que ce n'est qu'une "introduction". 

Je conseille aux pures novices, qui étudient le sujet par curiosité.

Comprendre le Deep Learning




Un troisième ouvrage sur lequel je ne fondais pas beaucoup d'espoirs... Et grosse surprise, un ouvrage bien construit et complet, suffisamment abstrait sur les sujets du Dig Data, du ML et des rudiments du DL pour conclure que : 
  • tout manager se doit de le lire pour comprendre le monde qui se profile ces prochaines années 
  • suffisamment technique pour orienter les techos sur les frameworks principaux des ces domaines avec la bonne dose d'explications pour en comprendre les utilisations et les architectures types 

Un indispensable je pense pour celui qui veut entrer dans ces trois sujets a la fois et en comprendre les tenants et aboutissants.

Big Data et Machine Learning


Voila un petit aperçu de mes dernières lectures, ces dernières me serviront pour les prochains articles  qui traiteront de l'IA mais avant il reste deux à traiter
Mais je reviendrais sur ces deux livres

jeudi 15 février 2018

SGBD-R : Jointures

A la base je pensais ne faire qu’un article sur l'algèbre relationnelle mais les jointures se sont révélées être un sujet plus qu'intéressant a traiter a elles seules donc voici la suite de l’article [10] dédié exclusivement aux jointures.
Les jointures sont les opérations avancées de l’algèbre relationnelles les plus importantes [5]. Elles pourraient être le propos d’un article à elle seule mais nous ne voulons que donner du sens à leur utilisation, nous ne rentrerons donc pas dans le détails (et le cas échéant cela sera l’occasion d’en faire un autre article) (et en fait c’est le cas mais c’était pas prévu)


Reprenons les éléments de l’article précédent [10] :

CREATE TABLE "Client"
(
 nom            varchar(40) NOT NULL,
 produit        varchar(40) NOT NULL
);
CREATE TABLE "Produit"
(
 produit        varchar(40) NOT NULL
);
INSERT INTO "Produit" VALUES ('epad');
INSERT INTO "Produit" VALUES ('asis');
INSERT INTO "Produit" VALUES ('windause');
INSERT INTO "Client" VALUES ('thomas','epad');
INSERT INTO "Client" VALUES ('thomas','asis');
INSERT INTO "Client" VALUES ('kevin','windause');
INSERT INTO "Client" VALUES ('kevin','asis');
INSERT INTO "Client" VALUES ('paul','asis');
Ajoutons un nouvel attribut disponibilité a la relation Produit et mettons a jour les donnée
alter table "Produit" add disponibilité boolean;
update "Produit" p set "disponibilité" = true where p.produit='windause';
update "Produit" p set "disponibilité" = true where p.produit='epad';
update "Produit" p set "disponibilité" = false where p.produit='asis';
Il existe différents types de jointures.

    Equi-jointure 

    L’equi-jointure est une opération construisant une nouvelle relation faisant l’union des attributs des deux relations initiales et contenant les enregistrement conforme a la condition. Attention cela va dédoublé l’attribut commun [6]
      select * from "Client" c inner join "Produit" p on p.produit=c.produit;
      client equi-jointure produit
      nom
      produit
      produit
      disponibilité

      thomas
      epad
      epad
      t

      thomas
      windause
      windause
      t

      kevin
      windause
      windause
      t

      paul
      asis
      asis
      f

      kevin
      asis
      asis
      f

      thomas
      asis
      asis
      f

      A noter que la jointure part du produit cartésien en y apposant une restriction et la formule ci dessus peut s'écrire ainsi (mais on n'évitera):
      select * from "Client" c, "Produit" p where c.produit = p.produit;

      Jointure complète


      Ou full join cette jointure est une jointure similaire à l'équi-jointure inner mais les résultats seront tendu par des attributs vide

      Par exemple en ajoutant:

      insert into "Client" values ('toto', '');
      La commande jointure complète suivante fournira (alors que l'équi-jointure fournira le même résultat):
      select * from "Client" c FULL JOIN "Produit" p on p.produit=c.produit;
      client equi-jointure produit
      nom
      produit
      produit
      disponibilité

      thomas
      epad
      epad
      t

      thomas
      windause
      windause
      t

      kevin
      windause
      windause
      t

      paul
      asis
      asis
      f

      kevin
      asis
      asis
      f

      thomas
      asis
      asis
      f

      toto




        Jointure naturelle 


        La jointure naturelle [7] retourne la fusion des deux tables et est donc équivalente à l'équi-jointure sans le doublon ni condition (celle ci étant implicite au attribut commun aux deux relations).

          client jointure naturelle produit
          nom
          produit
          disponibilité

          thomas
          epad
          t

          thomas
          windause
          t

          kevin
          windause
          t

          paul
          asis
          f

          kevin
          asis
          f

          thomas
          asis
          f

          Auto-jointure 

          L'auto Jointure est une equi jointure classique pour les tables jointes sont les même. Ce genre de jointure est utilisé lorsque des attributs références d’autres attributs de la même tables [8]
           

          La jointure cartésienne ou cross join est équivalent au produit cartésien que nous avons vu précédemment

          Theta jointure 

          La thêta jointure part du même principe que l'équi-jointure mais en ne se limitant pas à l'égalité des colonne mais en utilisant des inégalités pour construire la jointure.

          Semi-jointure

          Les semi-jointures sont des jointures sur lesquels on privilégie lors de la construction de la condition, le contenu d’une relation par rapport a une autre. Cette jointure peut être stricte ou non. C’est a dire excluant ou non les éléments partagé [9].

          Par exemple :

          select * from "Client" c LEFT join "Produit" p on c.produit = p.produit;
          client equi-jointure produit
          nom
          produit
          produit
          disponibilité

          thomas
          epad
          epad
          t

          thomas
          windause
          windause
          t

          kevin
          windause
          windause
          t

          paul
          asis
          asis
          f

          kevin
          asis
          asis
          f

          thomas
          asis
          asis
          f

          toto




          La version strict de cette requête nous produira alors:

          select * from "Client" c LEFT join "Produit" p on c.produit = p.produit where p.produit is null;
          client equi-jointure produit
          nom
          produit
          produit
          disponibilité

          toto




          Bien sur la requête a droite est équivalente à inverser dans la requête les Tables Client et Produit ainsi que les variables p et c.

          A noter que l’on peut utiliser le mot clef outer entre left et join mais que cela n'amène pas de changement sémantique particulier.
          Pour le dernier article dédié aux SGBR-R, nous terminerons sur les formes normales 4, 5 et 6.

          Références

          [2] https://www.google.fr/url?sa=t&rct=j&q=&esrc=s&source=web&cd=2&ved=0ahUKEwiaivuwvaDZAhUCSBQKHWpXDd4QFgguMAE&url=http%3A%2F%2Fwww.i3s.unice.fr%2F~edemaria%2Fcours%2Fc3.pdf&usg=AOvVaw05kk_PL5IdXIxKsT1WdRlm
          [4] http://sqlpro.developpez.com/cours/divrelationnelle/
          [5] http://sql.sh/cours/jointures
          [9] https://fr.wikipedia.org/wiki/Jointure_(informatique)
          [10] http://un-est-tout-et-tout-est-un.blogspot.com/2018/02/sgbd-r-algebre-relationnelle.html