Planning Poker Rapide

Le planning poker est une technique d'estimation utilisant des cartes comportant les chiffres de la suite de fibonacci, représentant des points de complexité.

Je souhaitais partager avec vous une pratique permettant d'accélerer vos planning poker.

 

 

 
Planning-card

 

Les etapes habituelles du planning poker sont les suivantes:

  1. Description de la story par le Product Owner
  2. Question/réponse pour approfondir la story
  3. Décision si la story est 'ready', selon les critères définis par l'équipe
  4. Evocation des taches nécessaires à la réalisation
  5. Les participants, excepté le PO, choisissent leur carte et la posent devant eux
  6. Les cartes sont retournées en même temps
  7. Les estimations les plus hautes et les plus basses expliquent leurs chiffrage
  8. Répéter les étapes 5,6,7 jusqu'à obtention d'un consensus

 

Les avantages de cette technique sont nombreux:

  • Le vote caché limite les influences
  • Elle utilise l'inteligence collective pour résoudre un problème complexe
  • Le planning game produit une estimation, mais contribue également à la construction d' un domaine métier partagé par l'équipe
  • La suite de fibonacci permet d'être moins précis sur les grand chiffres
  • En cours de planning poker, les story peuvent être remaniées ou découpées

Cependant, l'expérience m'a appris que la recherche du consensus parfait prenait du temps, beaucoup de temps. Au final, ce qui est important, c'est une estimation permettant de dimensionner le sprint de manière réaliste. Si vous trouvez vos planning game trop long, vous pouvez essayer ces petites règles aditionnelles:

  • Si les cartes sont regroupés sur 2 ou 3 valeurs consécutives, faire une moyenne retombant sur un chiffre de la suite
  • N'expliquer les chiffrages haut ou bas que si il y a un ecart de 2 cartes
  • En cas d'égalité, prendre l'estimation la plus haute

 

Exemples:

2,3,3,53

2,2,2,5'5' s'explique puis nouveau tour

1,1,5,13 les '1' et le '13' s'expliquent puis nouveau tour

3,3,5,55

 

Bon Planning Game

Artisan du logiciel - Traduction

Manifesto_for_software_craftsmanship-184413

Manifeste pour un artisanat du logiciel

Elever le niveau.

 
En inspirant des artisans du logiciels, nous élevons le niveau du développement logiciel professionnel, en pratiquant, et en aidant les autres à apprendre ce métier.
 Ce faisant, nous privilégions :
 

Non seulement un logiciel qui fonctionne,

mais aussi un logiciel bien conçu

 

Non seulement répondre au changement,

mais aussi en apportant continuellement de la valeur


Non seulement les individus et les interactions,

mais aussi une communauté de professionnels


Non seulement la collaboration avec le client,

mais aussi un partenariat bénéfique


En recherchant les éléments de gauche, nous avons découvert que les éléments de droite étaient indispensables.

 

⇒Insérer caractères spéciaux ✓

Le dévelopement web recherche sans cesse la prerformance, et cela encore plus pour le dévelopement mobile.

La moindre image est à banir.

Et l'on s'appercoit alors qu'il existe un encodage de caractères bien connu, UTF-8, qui cache de petites perles pour faire la  et le 

Ces caractères peuvent donc facilement être utilisés à la place d'une image, se mettent automatiquement à la taille du texte. Super!

Cela est également du plus bel effet dans un tweet

 

Maintenant, ces petits caractères, ils sont où sur mon clavier ?

Des combinaisions de touche permettent de taper certains caractères, mais pas les plus cool .

L'outil charmap, intégré à windows permet de faire l'insertion. Et chaque OS a son équivalent.

On peut aussi passer par des extensions de navigateur :

Chrome:

Firefox:

 

Avec cette (re)découverte, j'ai eu la même impression qu'en (re)découvrant http avec REST. Les technologies que l'on utilise ont été bien pensées dès le départ, et par notre méconnaissance de celles-ci, nous faisons des surcouches, c'est ce qui s'appelle de la complexité accidentelle.

Il ne reste plus qu'à utiliser ces caractères à bon escient.

Cela marche aussi pour vos carte de voeux.

Joyeux nöel

Bonne année

 

Source d'inspiration :

http://blog.goetter.fr/post/14449665753/des-images-sans-images

 

Refactoring: Supprimmer le bruit

Je voulais vous présenter un type de réfactoring que j'ai experimenté récemment: Supprimmer le bruit.

Avant tout je précise ce que j'entend par bruit. C'est un terme qui provient du traitement du signal, et qui signifie parasite, la partie du signal qui n'apporte pas d'information. http://fr.wikipedia.org/wiki/Rapport_signal_sur_bruit

Pour du code, le bruit est l'ensemble des caractères qui n'apportent pas d'information, et ralentissent le compréhension du code.

Je l'ai utilisé sur des tests d'integration en regression dont je n'arrivais pas à comprendre le sens. J'ai donc appliqué des améliorations sur les classes de test. Les modifications présentées ci dessous ont la caractéristique de ne pas changer le comportement de production, et permettent donc d'avancer en confiance.

 

Visibilité

Supprimmer la visibilité dans les interfaces et les attributs des classes de test.

 

Javadoc vide

Déjà, la javadoc sur une application sans API publique, cela n'apporte que rarement quelque chose de plus q'un bon nommage. En plus, quand c'est sur un méthode de test, et que en plus elle est vide, alors là, je supprime sans etat d'ame.

 

Getter inutile

Certains tests injectent ou se font injecter les attributs à partir d'un contexte spring ou autre. Le getter n'est pas nécessaire pour cela.

 

Assertions verbeuses

Pour vérifier la non-nullité et la taille d'un collection, on peut fairre l'assertion en junit

assertNotNull(list);

assertEquals(2, list.size());

... ou avec Fest Assert

assertThat(list).hasSize(2);

 

Découpage de test

Parfois vous vous rendez compte qu'une methode de test appelle plusieurs fois la même méthode avec des paramêtres différents. Cela signifie que ce sont plusieurs tests distincts. Il convient donc de découper le test en plusieurs méthodes avec un nommage décrivant ces différents cas de test.

 

Formattage BDD

Cela facilite également la lecture de passer une ligne entre les différents blocs du test:

  • initialisation (given)
  • action (when)
  • assertions (then)

J'ai  parfois utilisé des commentaires pour séparer ces blocs, mais lorsque cette simple règle de formattage est connu, cela est beaucoup plus efficace. Par ailleurs, certains framework de mock comme Mockito proposent des méthode utilisant le nommage BDD

 

Suppression des catch-fail

J'ai souvent retrouvé cet anti pattern du catch-fail, voire du catch-log-fail. Je ne vois pas l'interêt d'avoir un failure plutôt q'une erreur lorsque le méthode testée renverra une erreur. Quelle que soit la manière dont le test sera lancée, cette erreur sera remontée. Par contre je suis sûr que cela freine la lecture du code. Supprimé!

 

Regroupement des exceptions

Dans la close throws d'une méthode de test, peu m'importe de lister les exceptions que peut renvoyer cette méthode, un 'throws Exception' suffit.

 

Utilisation de expected pour les exceptions attendues

Transformer

 

@Test

public void testCasLimite() throws Exception {

  try {

    service.doSomething();

    fail();

  } catch (ExpectedException e) {

    // success

  }

}

 

... en 

 

@Test(expected=ExpectedException.class)

public void testCasLimite() throws Exception {

  service.doSomething();

}

 

 

Suppression du constructeur vide

Un constructeur d'une classe de test, vide ou avec le paramêtre 'name', mais pas de code, je le supprimme aussi. (Je conserve par contre volontier un constructeur vide dans une classe de production, afin de faciliter la navigation dans le code, et ne pas oublier ce constructeur vide au cas où l'on en ajoute un autre, mais que l'objet en question est serialisé, et a besoin d'un constructeur vide)

 

Suppression du message d'assertion

Le message d'assertion apporte peu d'informations par rapport à l'assertion elle-même, et au message construit par cette assertion lorsqu'elle echoue (ex: expected: 1 but was: 2). Parfois le code evolue, mais le message est resté identique, si bien qu'il nomme les objets avec un certain nom au moment où l'on écrit le test, mais que ce message apoprte aujourd'hui une confusion. Un message peut néanmoins être utile s'il apporte des valeurs importantes qui ne sont pas dans l'assertion elle-même.

 

Renommage de variable locale

Le meilleur nommage pour une variable est le nom de sa classe.

 

Utiliser les imports statics

Transformer

Assert.assertEquals("expected",actual);

... en

assertEquals("expected",actual);

 

Les plus attentifs et courageux qui seront arrivé jusqu'ici ont été indigné par cette approche. Quoi? du refactoring sur une barre rouge? n'importe quoi ! Tel que l'a rappellé récement Martin Fowler dans cet article sur le refactoring opportuniste, le refactoring s'effectue sur une barre verte. J' ai fait une entorse à cette règle en choisissant les améliorations qui me semblait sans danger.

J'espère que cela vous donnera des idées pour rendre votre code plus propre. Les commentaires sont les bienvenus.

 

Pour aller plus loin

 

Optimisation du Build Maven

 Une de mes premières impression à france billet etait le temps du build maven.

Voici l'etat de nos reflexions et exprimentations

Situation actuelle

  • 364 projets
  • 3 artefacts finaux
  • 13 jobs Hudson pour builder, gérer les évolutions du schema de la base et déployer sur plusieurs environnements dont les premiers sont
    • 1 Job Compilation  + Tests Unitaires
    • 1 Job Test IT avec appel à la base de données
    • 1 Job Integration avec serveurs démarrés
  • 33min pour un build complet en local sans les tests
  • 1 intégrateur à plein temps pour gérer l'usine logicielle

 

Done

Bien connaître les options maven

Le réacteur contient le projet courant et l'ensemble de ses modules.

Les options utiles permettant de ne pas builder l'ensemble du réacteur sont:

  • -pl, –projects Une fois placé à la racine des projets, cette option permet de sélectionner les projets à builder
  • -am, –also-make Build également les dependances des projets selectionnés lorsque celles-ci sont dans le reacteur, ce qui permet de builder u produit à jour
  • -amd, –also-make-dependents Build également les projets du réacteurs qui dépendent des projets selectionnés, ce qui permet de propager les modifications
  • -rf, –resume-from Permet de reprendre un build sur un projet donné, après avoir effectué une correction

http://www.sonatype.com/people/2009/10/maven-tips-and-tricks-advanced-reactor-options/

http://blog.aheritier.net/construire-moins-pour-aller-plus-vite/

Régler les paramêtres de JVM

Sur le build, il y a 3 endroits où j'ai pu configurer la taille allouée pour la JVM

  • Build Maven, avec la variable d'environnement MAVEN_OPTS (Maven indique gentiement la mémoire utlisée en fin de build)
  • Compilation Java, avec la configuration maxmem du plugin maven-compiler-plugin
  • Compilation GWT, avec la configuration extraJvmArgs du plugin gwt-maven-plugin

A manier avec précaution, car si le Xms est trop grand, la mémoire est allouée pour rien, s'il est trop petit, l'allocation progressive est plus coûteuese.

Si le Xmx est trop grand, il y a un risque de freezer la machine, et s'il est trop petit, c'est le java.lang.OutOfMemoryError

http://download.oracle.com/javase/6/docs/technotes/tools/windows/java.html

Spécifier le chemin du parent

Préciser un parent permet de faire de l'héritage et d'éviter de la duplication de configuration.

Lorsque l'on précise un parent, toujours ajouter le relativePath. Cela permet d'utiliser la dernière version du pom parent sans avoir à installer ce dernier.

Fixer les versions

Une grande partie de nos projets sont en SNAPSHOT. Nous ne passons pas par l'étape de version Fixe pour ces projets. L' ensemble des projets change de version en même temps.

Quelques projets dit 'ext' sont placés dans une autre arborescence avec des versions fixes car ils ne bougent plus.

Utiliser un build incrémental

Ce plugin permet de détecter si la recompilation est nécessaire. Ce plugin a été fait ici.

http://maven-incremental-build.java.net/site/index.html

Faire du TDD

Avec des tests unitaires, pas question de build, tout se passe dans l'IDE. Et je ne m'attarde pas sur les nombreux intérêts de cette pratique.

Mettre en places des circuits courts pour la partie présentation

Le build peut simplement être évité au cour du developement, suivant la technologie utilisée:

  • jsp/js: Faire du war:inplace lorsque cela est possible, ou alors faire les modifications dans le repertoire de deploiment utilisé par le serveur (sans oublier de répercuter les modifs - OK ce n'est pas idéal)
  • GWT: Se placer en mode dévelopement pour éviter la compilation GWT
  • Code serveur/EJB: Se brancher en debug. Le code peut être remplacé à chaud tant que les signatures de méthode ne changent pas.

Détecter les modifications pour builder moins

Le job construit la commande maven en se basant sur le changelog, afin de ne builder que les projets qui ont changé, et les projets dépendants.

Mieux connaître l'avancement du build

Un plugin nommé progress-maven-plugin de mon cru permet d'ajouter un log de ce type:

Reactor Progress: 32/60 (53.33%) /workspace/module/subModule

Cela permet d'ajouter du feedback:

  • sur un build local: un 53,33% permet de définir assez précisement la durée de la pause café :)
  • sur le build hudson: Nous sommes sur des jobs de type FreeStyle, et pas Maven, donc nous n'avons pas l'avancement module par module. D'autres part, les calculs faits par hudson pour prédire la durée du job est faussé par l'aspect dynamique de nos jobs (voir 'détecter les modifications'). Cela est surtout utile lorsque le build est claimé et que la correction est en cours de build.

Générer le Mind Map des relations

Comme un dessin vaut 10 000 mots, il est interessant d'avoir le graphe des dépendances maven. IL existe plusieurs plugin qui génèrent une image, mais à partir d'une taille limite, l'image devient inutilisable. L'interêt de l'avoir sous forme de mindmap, c'est que l'on peut l'ouvrir avec l'outil de son choix, le parcourir, le modifier, afin d'en extraire l'information voulue.

http://blog.xebia.fr/2011/05/05/le-mind-mapping-applique-aux-dependances-des-projets-mavenises/

 

In Progress

Fixer les versions

Déplacer quelques projets en 'ext' et fixer la version pour ne plus les builder ni les télécharger plusieurs fois.

Casser des dépendances

Puisque notre build détecte le modifications et les propage, il devient critique de ne pas avoir de gros projet utilisés par de nombreux autres projets. Le risque est en effet de builder les projets qui ont une dépendance même s'il n'en utilise qu'une infime partie. Il faut donc continuer à découper, spécialiser les projets afin de builder juste.

Passer à Maven 3

C'est je pense un gros gain possible, mais quelques plugin maven ne sont pas compatibles, et n'ont pas encore été apadptés.

Essayer Jenkins

A ma connaissance, il n'y a pas de gain de performance particulier à obtenir. Ce qui fait la différence, c'est le nombre de plugin et l'activité de la communauté.

 

To Do

Parralléliser les tests

Cela nécessite d'avoir des tests bien indépendants, sans ordre, ni resources partagées, ni données en base réutilisées.

http://maven.apache.org/plugins/maven-surefire-plugin/test-mojo.html#parallel

Parralléliser le build

Une fois passé à Maven3, il est possible de parralléliser les builds à l'interieur du réacteur, en définnissant la taille du pool de threads.

https://cwiki.apache.org/confluence/display/MAVEN/Parallel+builds+in+Maven+3

Passer les jobs en type Maven

En supprimant la partie script non-maven du job, nous bénéficierons de la vue du build en cours avec le statut de chaque module.

Automatiser la génération du mind Map

Créer un job permettant de générer le mind map et le publier sur le serveur d'intégration continuer, afin de pouvoir consulter la version la plus récente sans le générer en local.

Atteindre le build incassable

Réaliser un build pre-commit.

http://blog.javabien.net/2009/12/01/serverless-ci-with-git/

http://blog.octo.com/integration-continue-performante-part-2/

Parralléliser le déploiement

Nos serveur d'intégration sont déployés en série, rendant la plateforme indisponnible pendant 15min à chaque déploiement (arrêt, copie, démarrage des 2 * 3 serveurs).

Faire du war:inplace partout

Mettre en place le mode de dévelopement inplace sur tous les projets web jsp.

 

Conclusion

Chouchoutez votre build pour vous faciliter la vie.

Développement logiciel : art ou artisanat?

Traduction d'un article de Patrick Lee Dooley

http://organicprogramming.blogspot.com/2011/04/op-is-software-development-art-or-craft.html


Durant la dernière année et demi, j'ai travaillé sur les fondements de l'approche de développement logiciel appelée "Programmation Organique" (PO). Les résultats de mes recherches sont très intéressants. Je voudrais partager ces découvertes et générer une discussion riche. Je pense que cela est la clé du concept d'Artisanat du logiciel - un sujet qui est cher à mon cœur. Et tant que nous ne l'aurons pas défini, nous ne serons pas en mesure d'énoncer clairement ce que nous entendons par ce terme. 

Il y a eu beaucoup de discussions au cours des années pour savoir si le développement logiciel (Software Development) doit être considérée comme un Art. Nous sentons intuitivement qu'il est plus correctement compris comme un artisanat (Craft)Nous sommes plus à l'aise en le considérant comme un artisanat. Nous pensons de cette façon pour la simple raison que nous avons été formés comme artisans, et non pas comme des artistes. Il est inersessant dans la compréhension et le traitement du SD comme un artisanat. Après tout, les fruits de notre profession témoignent de la validité de ce point de vue. Cependant, je ne suis plus convaincu que ce point de vue soit suffisant. J'ai réalisé que le SD est aussi un art. 


N'étant pas un psychologue, j'ai récemment réalisé qu'il ya deux façons distinctes de décrire la réalité. La première est très concise et succincte (Craft). Les mathématiques tombent dans cette catégorie. La seconde est élaborée et sophistiquée (Art). La peinture ou la littérature entre dans cette catégorie. Ce sont les deux extrémités du spectre de l'activité humaine. Notre capacité à bien exprimer la réalité dans ces deux approches détermine la façon dont nous pouvons Interpréter, Modèliser et Communiquer la réalité. 

Notre capacité à résoudre des problèmes est déterminée par notre capacité à faire ces activités, et aussi - tout aussi important - par notre capacité à déterminer la bonne approche pour ces différents aspects de la réalité. Si nous nous trompons dans le choix de l'approche appropriée, notre capacité à créer des solutions en sera affaiblie. Nous pourions encore être en mesure de résoudre le problème, mais nous ne serions pas en mesure de le résoudre de manière efficace. 

Comme exemple simple, si nous souhaitons communiquer la beauté d'un paysage, le choix d'utiliser des représentations en fil de fer pour les éléments dans l'espace du problème entravera notre capacité à transmettre cette beauté. Nous allons être obligés de passer beaucoup plus de temps et d'efforts à tenter de corriger la solution en agitant la main jusqu'à ce que nous soyons en mesure de transmettre cette beauté. Tenter de résoudre ce problème en le réduisant s'avère totalement inefficace. 

Le logiciel n'est pas différent. La création efficace d'un système logiciel requiert la capacité à la fois: 
 - Représenter certains aspects de l'espace de problème avec la sémantique concise et succincte (Craft -. Sémantique à savoir la théorie des ensembles, la sémantique d'analyse, de la sémantique algorithmique etc)
 - Représenter d'autres aspects de l'espace de problème avec la sémantique complexe et sophistiquée (Art - c'est à dire le modèle du logiciel des entités et les relations à multiples facettes entre les entités). 
Un système logiciel efficace doit être à la fois de l'art et de l'Artisanat. Mais ce n'est pas différent de toute autre profession qui tente de résoudre un problème particulier. Une voiture - quand elle est conçue correctement, est également à la fois de l'art art et de l'artisanat. 

C'est vraiment un argument pour le principe selon lequel la forme est définie par la fonctionOn pourrait avancer que dans la profession du logiciel - comme dans aucune autre profession - , la fonction véritable dépendent de la forme du logiciel - particulièrement lorsque la sophistication du système augmente. La Nature elle-même fournit de nombreux exemples où la forme permet la fonction. Il y a des discussions étonnantes sur le gecko sur le site TED. 

Donc, en résumé, je crois que le logiciel a besoin d'être traitée comme un art, quand cela est nécessaire, et elle doit être traitée comme un artisanat - quand cela est nécessaire. Et nous avons besoin de développer la capacité d'être en mesure de déterminer où se situent ces exigences. 

C'est mon expérience, que nous ne sommes pas armés pour faire ce type de distinctions. Nous avons été formés uniquement avec les compétences d'un artisan. Nous avons été amenés à croire que ces compétences sont suffisantes pour l'ensemble de nos problèmes de conception. Nous avons un outil dans notre coffre à outils, et nous nous sentons tellement en confiance avec cet outil qui nous l'utilisons partout. Et pourtant, nous sommes surpris lorsque les résultats sont plutôt satisfaisants. Je pense qu'il est impératif que nous étendions notre ensemble d'outils et d'apprendre leurs usages respectifs.

 

Pour réaliser cette traduction, je me suis aidé de http://translate.google.fr et http://www.granddictionnaire.com

Merci à Patrick Lee Dooley de m'avoir autorisé à publier cette traduction.

 

Pour en savoir plus sur la programmation organique :

http://www.organicprogramming.com/2010/08/what-is-organic-programming-op/

http://en.wikipedia.org/wiki/Organic_computing