Réflexions sur le développement

Quelques éléments de réflexions sur ma "vision" du développement. 

Ce sont des idées très générales, qui ne peuvent cependant pas être transférées telles quelles, dans n'importe quel contexte. Il s'agit de points de vue applicables plutôt à des petites équipes.

Je parle donc d'un développement "générique" avec des contraintes modérées

  • soft real-time possible [mais pas de hard real-time]
  • pas de contraintes sécuritaires élevées [humaines, matériel exceptionnel]

Cela concerne néanmoins de nombreux développements, que ce soit dans l'informatique industrielle ou la gestion. On est ici dans le "compromis". 

En revanche, je ne livrerai pas de "vision" quant aux développements contraints, puisqu'en matière de sécurité, il n'y a pas de  concession possible.

Sur l'analyse et le dimensionnement

Avertissement : le discours qui suit n'a guère de sens si on évolue dans une structure où il existe déjà un process de qualification adapté et bien établi.

Pour avoir pratiquer certaines méthodes (ou modèles) d'analyse et d'estimation du logiciel (telles que COCOMO), je porte un regard assez pragmatique sur leur usage. Quelle est la fonction de transfert entre l'usage de ces méthodes paramétriques "traditionnelles" et la conduite en succès du projet (couts/délais/fonctionnalités) ? dit autrement, dans quelle mesure la valeur ajoutée du process se retrouve au final dans le logiciel élaboré ? C'est loin d'être évident, car les contraintes du moment ne sont pas toujours compatibles avec l'état de l'art :

  • exigence de réactivité et de souplesse : quand le besoin se réifie (voire évolue), les spécifications changent, les éléments de dimensionnement préalables sont "deprecated" avant de commencer. On ne peut pas "botter en touche" ou crever les budgets à tous les changements, car ce n'est pas conforme au cycle en V
  • équipes de développement hétérogènes (qui connait totalement ces méthodes, qui adhère ?)

Une méthodes d'analyse fonctionnelle récente telle que COSMIC apporte un éclairage (à mon avis) moins précis, mais plus rapide et avec un moindre investissement . Et c'est toujours infiniment mieux qu'une estimation "à la louche" par l'expérience. De plus, on peut capitaliser assez facilement sur les réalisations effectuées (dans les temps, ou pas ...).

Sur la modélisation

Il faut modéliser les zones stratégiques en ayant à l'esprit :

  • qu'une modélisation détaillée n'est pas synonyme de réussite pour un projet
  • qu'une modélisation partielle n'est pas synonyme d'échec d'un projet
  • que pas de modélisation du tout est encore très répandu (malgré l'époque révolue de la programmation "à Papa" des années 90) ; et que c'est une catastrophe quand les acteurs "disparaissent"

La modélisation est d'autant plus utile qu'on peut commencer à implémenter très tôt ; c'est à dire ne pas attendre d'avoir tout modéliser pour se rendre compte que l'on est passé à côté d'un noeud ; ce qui jettera à terre un beau modèle, dès le début de l'implantation. 

C'est un excellent vecteur de communication entre les différents membres d'un projet ... si tout le monde se comprend : c'est à dire qu'il faut limiter le niveau de technicité de la notation ou méthode choisie. C'est pour cela que dans les contextes très agiles, on a plus souvent recours à la métaphore et les drafts statiques, plutôt qu'à une modélisation complète.

Mon point de vue est que le recours à UML est utilement adapté à un très grand nombre de situations, si tant est qu'on ne se limite pas aux diagrammes structurels (les plus simples), les composants logiques, les classes, les objets. Il faut absolument recourir aux diagrammes de séquences et d'états. La plupart du temps on ne voit que des diagrammes de classes, et c'est dommageable car c'est bien dans l'aspect comportemental que les surprises et les problèmes se cachent.

Ce n'est pas UML qui est limitant, mais plutôt :

  • le niveau de connaissance de la notation parmi les développeurs
  • les outils CASE : fiabilité, facilité d'usage, couts, fonctions collaboratives lourdes ou absentes
  • difficulté d'utiliser UML pour des acteurs non informaticiens (exemple des cas d'utilisation)

Sur la conception

La POO

"L'habit ne fait pas le moine" : ce n'est pas parce que l'on utilise un langage objet que l'on aboutit à une conception objet, et encore moins à une bonne conception. Les objets ne se réduisent pas à des agrégats de données et de traitements (leur définition primaire) car ce ne sont pas des structures "améliorées". Il faut raisonner en permanence en terme de mission et de couplage, des classes cohésives limitant les échanges. Tout le monde a été confronté à (ou a codé lui-même) des "spaghettis" : si on représente les échanges entre les objets, on a des flèches dans tous les sens : assurément données et traitements ne sont pas au bon endroit.

Sur les threads

Les threads ne sont pas forcément synonymes d'une bonne conception et d'une application réactive. Les architectures les plus sclérosées que j'ai rencontrées étaient dotées d'un nombre de thread (pas nécessairement) élevé, (mais) avec un grand couplage entre eux. Les threads ne servent à rien s'ils s'attendent sans arrêt les uns les autres. C'est élémentaire mais pas toujours si facile à mettre en oeuvre.

L’avènement des threads a révolutionné la manière de concevoir les applications, mais leur recours avec excès conduit à des logiciels peu déterministes très difficiles à débugger.

Sur les patterns

Les design patterns sont incontournables, encore faut-il utiliser les bons pour la situation donnée. Parfois, il y a plus de code pour l'infrastructure du pattern, que de code opérationnel utile ... dans ce cas le pattern était-il nécessaire ? Un pattern n'est qu'un guide ; si l'implémentation en est mauvaise, c'est pire que tout : on a la contrainte d'un canevas, et aucun bénéfice de son utilisation.

Sur la programmation

La réutilisation

Il faut trouver un compromis entre "réinventer la roue" et utiliser des "composants sur étagères".

On constate que chaque entreprise, chaque équipe, voire chaque développeur peut (re)développer son socle commun ... Des librairies open source conviennent souvent pour ces entités communes, avec parfois plus de fiabilité et richesse que certains outils commerciaux. Constatons que même avec des fonctions métier très différentes, il y a fort à parier que plus la moitié d'une application repose sur des problématiques communes ...

Cependant le développement n'est pas le puzzle de composants que certains éditeurs ou doctrines prétendent. L'assemblage de composants hétéroclites conduit le développeur à se concentrer uniquement sur la manière de faire communiquer ces composants entre eux, sans pouvoir imposer sa propre orchestration. On arrive à des situations aberrantes où on passe plus de temps à essayer de faire fonctionner les briques ensemble, plutôt qu'a les développer.

Outils et technologies

Réflechissons à la dictature des outils et des technologies. Utiliser systématiquement les dernières technologies ou langages, c'est peut-être innover sur le plan de "l'industrie informatique" mais certainement pas innover sur le plan du produit. Développer sans bugs, c'est innover. Développer un logiciel qui n'a pas besoin d'être réécrit à chaque nouvelle technologie, c'est innover aussi. L'informatique invente parfois des langages pour se nourrir elle-même. Un langage sans écosystème de développement ne sert pas à grand chose.

Je constate que les dépendances liées aux technologies sont souvent subies et perçues comme incontournables. De nombreuses outils, langages, ou fonctions sont considérés comme "legacy" ; pourtant ils nous permettent(traient) de faire vivre le logiciel plus longtemps que les générations de technologies : sachons les identifier et maitrisons les. On peut faire du "développement durable" aussi dans l'informatique. Combien de logiciels engagent d'importantes ressources pour porter vers des nouvelles technologies, et pourtant l'utilisateur ne voit pas son logiciel aller plus vite, ou mieux correspondre à son besoin, ou être plus fiable pour autant.

Investissons sur l'usage plutôt que sur les outils : ce n'est pas l'outil qui fait le bon ouvrage, et encore moins le bon produit.

L'utilisation de générateur automatiques de codes fait gagner du temps à l'instant 't', mais sur la durée de vie d'un projet, le gain est loin d'être évident. Cela engendre des couts cachés à prendre en compte, et à bien expliquer.

Les environnements de développement deviennent obèses (parfois plus rapidement que l'augmentation de performances des machines). Il vaut peut être mieux investir du temps collectif ou individuel à rationaliser les méthodes de travail avec des outils plus simples.

En matière de systèmes

Avertissement : dans cette discussion on entre rapidement dans le "troll", donc je ne dirai rien de ce que je pense de Windows/Microsoft et Linux(s) ou MacOS.

Je dirai simplement que c'est illusoire de parler d'un système d'exploitation 

  • sans évoquer l'écosystème qui gravite autour : matériel supporté, librairies open-source disponibles, librairies commerciales disponibles, compétences répandues ou rares, domaines d'application, histoire
  • sans évoquer les domaines d'application
  • en faisant abstraction des contraintes de déploiement, d'exploitation et de maintenance

On ne peut pas tout faire :

  • avec un client léger ou un terminal
  • avec des écrans à 2 cases et 1 bouton

Il y a aura toujours des OS desktop et des applications "riches" ... pendant un bon bout de temps (à moins d'avoir des LAN qui tournent à la vitesse du bus PCI ... ou d'être satisfaits avec des applications anémiques comme les applications G...le à 2 boutons).

Les OS spécialisés (temps réel, embarqué, sécurité, mainframe) sont tous des "cas à part", avec une lourde histoire. Néanmoins, il me semble que certains éditeurs ou fabricants de matériels tordent un peu trop ce pauvre Linux dans tous les sens, pour remplacer (s'affranchir) à moindres couts (de) ces OS spécialisés.