Existe-t-il un paradigme de programmation qui encourage à rendre les dépendances extrêmement évidentes pour les autres programmeurs?

26

Je travaille dans un entrepôt de données qui source plusieurs systèmes via de nombreux flux et couches avec des dépendances de labyrinthe reliant divers artefacts. À peu près tous les jours, je rencontre des situations comme celle-ci: je lance quelque chose, cela ne fonctionne pas, je passe par beaucoup de code, mais quelques heures plus tard, je me rends compte que j'ai réussi à conceptualiser la carte de processus d'une infime partie de ce que je sais maintenant plus tard dans la journée est nécessaire, donc je demande à quelqu'un et ils me disent que cet autre flux doit être exécuté en premier et que si je vérifiais ici (indiquant une partie apparemment arbitraire d'une énorme pile d'autres dépendances codées), alors j'aurais vu ca. C'est incroyablement frustrant.

Si je pouvais suggérer à l'équipe que ce serait peut-être une bonne idée de faire plus pour rendre les dépendances entre les objets plus visibles et évidentes, plutôt que de les intégrer profondément dans des niveaux de code récursifs, ou même dans les données qui doit être présent car il est alimenté par un autre flux, peut-être en se référant à un paradigme logiciel bien connu et éprouvé - alors je pourrais peut-être rendre mon travail et tout le monde beaucoup plus simple.

C'est un peu difficile d'expliquer les avantages de cela à mon équipe. Ils ont tendance à accepter les choses telles qu'elles sont et à ne pas `` voir grand '' en termes de voir les avantages de pouvoir conceptualiser l'ensemble du système d'une nouvelle manière - ils ne voient pas vraiment cela si vous pouvez modéliser un énorme système efficacement, il est moins probable que vous rencontriez des inefficacités de mémoire, des contraintes uniques d'arrêt de flux et des clés en double, des données absurdes car il est beaucoup plus facile de les concevoir conformément à la vision d'origine et vous ne rencontrerez plus tard tous ces problèmes qui nous vivons maintenant, ce que je sais être inhabituel des emplois passés, mais qu'ils semblent penser comme inévitable.

Alors, quelqu'un connaît-il un paradigme logiciel qui met l'accent sur les dépendances et promeut également un modèle conceptuel commun d'un système en vue d'assurer l'adhésion à long terme à un idéal? En ce moment, nous avons à peu près un gâchis géant et la solution à chaque sprint semble être "juste ajouter cette chose ici, et ici et ici" et je suis le seul à craindre que les choses commencent vraiment à s'effondrer.

Christs_Chin
la source
2
Pourriez-vous préciser de quel type de "dépendances de labyrinthe reliant divers artefacts" il s'agit? S'agit-il de dépendances, qui pourraient être résolues avec un outil de construction comme Maven? S'agit-il de dépendances d'entrée, où l'un de ces artefacts dépend d'une entrée qui n'est pas évidente ou claire? S'agit-il de dépendances clés entre les tables de base de données?
FrustratedWithFormsDesigner
Le système est PLSQL, Unix bash, OWB etc donc il y a toutes sortes de dépendances. Parfois, les données sont requises d'un certain format, à un certain endroit, à un certain moment, par un certain module, mais ce n'est pas évident à distance d'après le code et ne peut être discerné que de deux manières: en parcourant une montagne de code, prendre peut-être des jours, pour découvrir que certaines données avaient un point-virgule délimitant dans une partie du système que vous ne saviez même pas référencer car elles étaient enfouies dans 10 couches de code appelé récursivement, ou en demandant à quelqu'un, toutes les à chaque fois. Cela ne favorise pas l'indépendance.
Christs_Chin
4
Littéralement tous
Miles Rout
3
Peu tangente: Haskell étant paresseux, vous ne spécifiez en fait pas l'ordre des opérations lorsque vous écrivez du code. Vous spécifiez uniquement les dépendances. La fonction C dépend des résultats des fonctions A et B. Donc, A et B doivent être exécutés avant C, mais cela pourrait fonctionner aussi bien si A est exécuté en premier, ou si B est exécuté en premier. Je pensais juste que c'était intéressant.
GlenPeterson
1
Il y a un livre intitulé Design patterns (le livre craint, mais la plupart de ce qu'il dit est bon, sauf le bit sur singleton). Il comporte plusieurs sections sur la gestion des dépendances.
ctrl-alt-delor

Réponses:

19

Découvrabilité

Son absence afflige de nombreuses organisations. Où est cet outil que Fred a construit à nouveau? Dans le référentiel Git, bien sûr. Où?

Le modèle logiciel qui me vient à l'esprit est Model-View-ViewModel. Pour les non-initiés, ce modèle est un mystère complet. Je l'ai expliqué à ma femme comme "cinq widgets flottant au-dessus de la table qui se parlent via une force mystérieuse." Comprenez le modèle et vous comprenez le logiciel.

De nombreux systèmes logiciels ne documentent pas leur architecture car ils supposent qu'elle s'explique d'elle-même ou émerge naturellement du code. Ce n'est pas le cas et ce n'est pas le cas. À moins que vous n'utilisiez une architecture bien définie, de nouvelles personnes se perdront. Si ce n'est pas documenté (ou bien connu), de nouvelles personnes se perdront. Et les anciens combattants se perdront aussi, une fois qu'ils auront été loin du code pendant quelques mois.

Il est de la responsabilité de l'équipe de proposer une architecture organisationnelle sensée et de la documenter. Cela inclut des choses comme

  • Organisation des dossiers
  • Références projets
  • Documentation de classe (ce qu'elle est, ce qu'elle fait, pourquoi elle existe, comment elle est utilisée)
  • Projet, module, assemblage, quelle que soit la documentation.

Il est de la responsabilité de l'équipe de rendre les choses organisées et découvrables afin que l'équipe ne réinvente pas constamment la roue.

Soit dit en passant, la notion selon laquelle «le code devrait être auto-documenté» n'est que partiellement correcte. Bien qu'il soit vrai que votre code doit être suffisamment clair pour que vous n'ayez pas à expliquer chaque ligne de code avec un commentaire, les relations entre les artefacts tels que les classes, les projets, les assemblys, les interfaces et autres ne sont pas évidentes, et restent doivent être documentés.

Robert Harvey
la source
3
Bien sûr, mais les gens qui s'appuient trop sur les modèles de conception font partie du problème. Ce sont eux qui écrivent du code sans aucune documentation, en supposant que tout le monde comprendra ce qu'ils ont fait juste en regardant le code. De plus, les modèles de conception de logiciels ne sont pas de l'architecture (pour la plupart).
Robert Harvey
1
Où est cet outil que Fred a construit à nouveau? Dans le référentiel Git, bien sûr. Où? - Exactement! Le modèle MVC est trop spécifique au développement frontal (je pense), et les modèles ne sont utiles que si tout le monde dans l'équipe les connaît donc cela fait simplement passer le problème des dépendances qui ne sont pas évidentes, à elles étant évidentes si tout le monde sait comment trouver leur. Mais le problème suppose que ce n'est pas le cas. En tant que tel, j'espère qu'il y a quelque chose qui promeut une manière vraiment évidente d'expliquer les dépendances qui ne nécessite pas un autre cadre conceptuel appris à utiliser.
Christs_Chin
7
Cela s'appelle la «documentation». Au-delà de cela, vous avez besoin d'un cadre de dépendance sensible que tout le monde prend en charge. Malheureusement, il n'y a pas de modèle standard que vous pouvez simplement insérer dans votre projet; la structure organisationnelle du logiciel est quelque chose que votre équipe crée elle-même, avec l'aide d'une architecture sensible.
Robert Harvey
5
@RobertHarvey: Entendu assez récemment: "Nous écrivons du code qui n'a pas besoin de documentation". Faux. Vous écrivez du code sans documentation.
gnasher729
3
Quelques bonnes choses ici. NB il y a une différence entre l'écriture de code qui ne nécessite pas de commentaires et la rédaction de documentation à l'appui.
Robbie Dee
10

La meilleure façon d'aborder ce genre de problèmes est progressivement. Ne soyez pas frustré et proposez de vastes changements architecturaux. Ceux-ci ne seront jamais approuvés et le code ne s'améliorera jamais. Cela suppose que vous pouvez même déterminer les modifications architecturales larges et correctes à apporter, ce qui est peu probable.

Ce qui est probable, c'est que vous pourriez déterminer un changement plus petit qui vous aurait aidé avec le problème spécifique que vous venez de résoudre. Peut-être en inversant certaines dépendances, en ajoutant de la documentation, en créant une interface, en écrivant un script qui avertit d'une dépendance manquante, etc. Proposez donc cette petite modification à la place. Encore mieux, selon la culture de votre entreprise, ils peuvent tolérer ou même s'attendre à ce que vous apportiez des améliorations comme celle-ci dans le cadre de votre tâche d'origine.

Lorsque vous apportez ces changements mineurs à une partie régulière de votre travail et, par votre exemple, encouragez les autres à le faire également, ils s'accumulent vraiment au fil du temps. Beaucoup plus efficace que de pleurnicher sur des changements plus importants que vous n'êtes pas autorisé à effectuer.

Karl Bielefeldt
la source
2
Je suis d'accord avec l'idée de changements progressifs. Le problème est que, sans certains principes organisationnels déjà en place, vous pourriez simplement créer plus de chaos. Considérez l'effet du déplacement d'un seul projet, classe ou autre artefact (dont dépendent les autres modules) vers un emplacement plus sensible.
Robert Harvey
1
Super truc. Mes difficultés ont souvent été rendues moins ardues par quelques âmes diligentes qui ont le nous d'ajouter un outil / widget ici et là pour créer de l'ordre à partir du chaos. Bien que je ne sois pas un fan des rames et des rames de documentation, une feuille de triche bien écrite ou une liste pointée de gotchas / fonctionnalités peut grandement aider.
Robbie Dee
+1 pour avoir proposé de petites modifications susceptibles d'être approuvées. J'ai vécu cela et cela m'a aidé à devenir quelqu'un avec plus d'influence, puis mes propositions ont eu plus d'impact.
RawBean
2

Architecture.

Il n'y a pas de principe ou de pratique unique, spécifique et universel qui résout les problèmes de découverte et de maintenabilité qui s'appliquent à tous les aspects de tous les logiciels. Mais, le terme large pour désigner ce qui rend un projet sain d'esprit est l' architecture.

Votre architecture est l'ensemble des décisions concernant chaque point de confusion potentielle (ou historique) - y compris la désignation de la façon dont les décisions architecturales sont prises et documentées. Tout ce qui concerne le processus de développement, la structure des dossiers, la qualité du code, les modèles de conception, etc. sont toutes des choses qui peuvent entrer dans votre architecture, mais aucune d'entre elles n'est une architecture.

Idéalement, ces règles sont unifiées par une singularité d'esprit.

Une petite équipe peut certainement créer une architecture en collaboration. Mais, avec des opinions différentes, cela peut rapidement conduire à une architecture très schizophrénique qui ne sert pas à maintenir votre santé mentale. Le moyen le plus simple de vous assurer que votre architecture, et les nombreux TLA et modèles qu'elle contient, sont au service de la réussite de l'équipe avec une singularité d'esprit est d'en confier la responsabilité à un seul esprit.

Or, cela ne nécessite pas nécessairement un «architecte» pour pontifier . Et, alors que certaines équipes peuvent vouloir qu'une personne expérimentée prenne simplement ces décisions, le point principal est que quelqu'un doit posséder l'architecture, surtout à mesure que l'équipe grandit. Quelqu'un garde le pouls de l'équipe, modère les discussions architecturales, documente les décisions, surveille les décisions et travaille à l'avenir pour se conformer à l'architecture et à sa philosophie.

Je ne suis pas un grand fan d'une seule personne prenant toutes les décisions; mais identifier un «architecte» ou un «propriétaire de produit technique» chargé de modérer les discussions architecturales et de documenter les décisions combat un plus grand mal: la diffusion de la responsabilité qui ne conduit à aucune architecture perceptible.

svidgen
la source
Vous avez absolument raison d'identifier la diffusion de la responsabilité comme n'étant responsable d'aucune architecture discernable. Des décisions n'ont été prises que récemment pour remédier à ce problème. Je pense toujours qu'une bonne solution pour cela serait de créer un système distribué entier via un autre système logiciel qui agit comme une sorte de harnais, où vous décidez ce qui va dans le système, mais il décide où, selon la façon dont l'architecte le programme. Vous auriez une vue sur plusieurs systèmes et technologies différents et les navigueriez via un schéma architectural du système ...
Christs_Chin
Je pense que votre point dans cette réponse est la meilleure façon de combattre / empêcher le type de chose dont parle le PO. Cela s'applique même à l'héritage d'un désordre comme l'OP l'a fait.
GWR
1

Bienvenue en génie logiciel (dans les deux sens);) C'est une bonne question, mais il n'y a vraiment pas de réponses faciles, comme je suis sûr que vous le savez. Il s'agit vraiment d'évoluer vers de meilleures pratiques au fil du temps, de former les gens à être plus compétents (par définition, la plupart des gens de l'industrie ont des compétences médiocres) ...

Le génie logiciel en tant que discipline souffre de le construire d'abord et de le concevoir au fur et à mesure, en partie par opportunisme et en partie par nécessité. C'est juste la nature de la bête. Et bien sûr, les hacks s'appuient sur les hacks au fil du temps, car les codeurs susmentionnés mettent rapidement en place des solutions fonctionnelles qui répondent souvent aux besoins à court terme au prix de l'introduction de dettes techniques.

Le paradigme que vous devez utiliser est essentiellement d'obtenir de meilleures personnes, de former les personnes que vous avez bien et de souligner l'importance de prendre du temps sur la planification et l'architecture. On ne peut pas être facilement "Agile" quand on travaille avec un système monolithique. La mise en place de modifications, même minimes, peut prendre beaucoup de temps. La mise en place d'un excellent processus de documentation de haut niveau aidera également les personnes clés à maîtriser le code plus rapidement.

Les idées sur lesquelles vous pourriez vous concentrer seraient (au fil du temps, progressivement) d'isoler et de refactoriser les éléments clés du système de manière à les rendre plus modulaires et découplés, lisibles, maintenables. L'astuce consiste à travailler en fonction des exigences commerciales existantes, de sorte que la réduction de la dette technique puisse se faire simultanément avec la fourniture d'une valeur commerciale visible. La solution consiste donc à améliorer les pratiques et les compétences et à essayer d'avancer davantage vers une réflexion architecturale à long terme, comme je peux vous le dire.

Notez que j'ai répondu à cette question du point de vue de la méthodologie de développement logiciel plutôt que du point de vue de la technique de codage, car c'est vraiment un problème bien plus important que les détails du codage ou même le style architectural. C'est vraiment une question de comment vous planifiez le changement.

Brad Thomas
la source
6
J'entends ce que vous dites, mais votre réponse est finalement insatisfaisante et franchement un peu insultante. C'est un problème plus important que l'embauche de meilleures personnes; même dans la petite boutique dans laquelle je travaille, nous avons du mal avec cela, et je pense que c'est plus qu'un problème de personnes; Je pense qu'il a des problèmes techniques spécifiques.
Robert Harvey
1
Je suis d'accord qu'il y a des aspects techniques, mais je pense qu'ils sont relativement mineurs par rapport à l'accent mis sur une méthodologie plus solide pour planifier le changement. Je ne pense pas que cela concerne autant les modèles de conception qu'un changement culturel vers plus de planification et d'analyse, une planification et une analyse plus tôt et une meilleure planification et analyse.
Brad Thomas
D'accord, je posterai ma propre réponse à titre de comparaison. Je ne pense pas que cela ait quoi que ce soit à voir avec les modèles de logiciels.
Robert Harvey
Brad, merci pour la réponse. Votre réponse est appréciée car je sais que je ne suis pas le seul à être conscient de ce problème. Cela ressemble à ça dans mon équipe. Je suis également d'accord avec Robert Harvey, en ce que ce problème est répandu et je ne veux pas abandonner la croyance qu'il existe une solution, que ce soit dans un nouveau type de logiciel ou une nouvelle pratique de travail.
Christs_Chin
2
Exactement mon expérience: vous devez faire comprendre aux membres de votre équipe ce qu'ils font. Je vois des gens mélanger MVVM et MVC, d'autres utilisant des contrôles WPF d'une manière qui était normale avec Windows Forms (ou plutôt: VB6), des gens programmant en C # sans une compréhension de base de l'orientation objet ... Enseignez-leur. Enseignez-les à nouveau. Soyez frustré. Enseignez-leur à nouveau, ... Pensant souvent à abandonner. Et leur enseigner à nouveau ...
Bernhard Hiller
1

J'aime l'idée de @ RobertHarvey sur les conventions et je pense qu'elles aident. J'aime aussi l'idée de @ KarlBielefeldt de "documenter au fur et à mesure" et je sais que c'est essentiel parce que c'est la seule façon de maintenir la documentation à jour. Mais je pense que l'idée générale est que documenter comment trouver tous les morceaux de votre code, les construire et les déployer est important!

J'ai récemment envoyé un e-mail à un important projet open source qui avait une configuration XML qui générait du code était totalement non documenté. J'ai demandé au responsable: "Où ce processus de génération de code XML est-il documenté? Où est la configuration de la base de données de test documentée?" et il a dit: "Ce n'est pas le cas." Il s'agit essentiellement d'un projet à contributeur unique et maintenant je sais pourquoi.

Écoutez, si vous êtes cette personne et que vous lisez ceci, j'apprécie vraiment ce que vous faites. J'adore pratiquement les fruits de vos travaux! Mais si vous avez passé une heure à documenter la façon dont vos éléments vraiment créatifs sont assemblés, je pourrais passer quelques jours à coder de nouvelles fonctionnalités qui pourraient vous aider. Face au mur de briques du "manque de documentation n'est pas un problème", je ne vais même pas essayer.

Dans une entreprise, un manque de documentation est une énorme perte de temps et d'énergie. Des projets comme celui-ci sont souvent confiés à des consultants qui coûtent encore plus cher, juste pour qu'ils puissent comprendre des choses de base telles que «où sont toutes les pièces et comment s'assemblent-elles».

En conclusion

Ce qu'il faut, ce n'est pas tant une technologie ou une méthodologie, mais un changement de culture; une conviction partagée que documenter comment les choses sont construites et pourquoi est important. Cela devrait faire partie des revues de code, une condition pour passer à la production, liée aux augmentations. Lorsque tout le monde y croit et agit en conséquence, les choses vont changer. Sinon, ce sera comme ma contribution open source qui a échoué.

GlenPeterson
la source
2
Je soupçonne qu'une partie du problème culturel réside dans la croyance agile selon laquelle "si cela ne fait pas partie d'une User Story (c'est-à-dire qu'il ne contribue pas directement à la valeur des parties prenantes), alors ce n'est pas important". Poudlard. Conversation connexe ici: en mode agile, comment les tâches d'infrastructure de base au début d'un projet sont-elles planifiées et allouées?
Robert Harvey
@RobertHarvey Oui. Tout le monde dans mon équipe est incroyablement brillant et très facile à vivre. Les Scrum Masters et les chefs de projet sont bien intentionnés et motivés, et les pratiques sont les plus agiles au sein desquelles j'ai travaillé. Mais la documentation fait défaut, probablement pour la raison même que vous suggérez. De plus, lorsque la documentation est créée, une autre couche d'aléatoire dans l'efficacité de la communication est introduite dans la capacité de la personne à identifier les concepts pertinents et à les expliquer, sans parler de son attitude à l'égard de devoir entreprendre une telle tâche. Habituellement, c'est juste "Ask somone"
Christs_Chin
@GlenPeterson Oui, je suis d'accord que ce serait utile. Mais il faut préciser non seulement qu'il doit être construit, mais aussi comment et ce qui peut être qualifié de documentation. Par exemple, comme exemple récent ici, quelqu'un a inclus une liste de nouveaux numéros que notre système identifiera. C'est ça. Il n'y avait aucune mention de la façon dont ces chiffres entrent dans le système, où, pourquoi, par qui, à quelle fréquence ou quoi que ce soit d'utile, seulement ce qu'ils font. À aucun moment je ne me suis demandé quels chiffres notre système identifierait comme pertinents. Mais je me suis souvent demandé, où entrent-ils, où vont-ils et ce qui se passe en chemin. C'est encore un mystère.
Christs_Chin
1
@Christs_Chin Une grande partie de la communication est basée sur le contexte. Sans ce contexte, la plupart des communications n'ont presque aucun sens. Je ressens ta douleur. Mais je pense qu'il est difficile d'écrire (anglais) pour que les autres puissent vous comprendre. Parfois, les premières spécifications d'un système ont le contexte dont vous avez besoin pour le comprendre, même si elles sont horriblement obsolètes, le contexte aide généralement.
GlenPeterson
1

Pour répondre à la question telle qu'elle est posée (plutôt que de vous conseiller sur votre situation particulière):

Le paradigme de programmation connu sous le nom de programmation fonctionnelle pure exige que tout ce qui affecte la sortie d'une fonction soit spécifié dans les paramètres d'entrée. Il n'y a pas de dépendances cachées ou de variables globales ou d'autres forces mystérieuses agissant de manière invisible à travers la base de code. Il n'y a pas de couplage temporel "vous devez faire ce premier".

JacquesB
la source
0

Chaque entrepôt de données est différent, mais vous pouvez faire beaucoup pour vous faciliter la tâche.

Pour commencer, chaque ligne de la base de données avait une colonne DATE_ADDED et DATA_UPDATED afin que nous puissions voir quand elle a été ajoutée à la base de données et quand elle a été modifiée. Nous avions également une colonne SOURCE_CODE afin que nous puissions suivre où chaque bit de données est entré dans le système.

Ensuite, nous avions des outils communs qui traversaient tous nos entrepôts de données tels que les tris, les correspondances de table, les trancheuses et les découpeuses, etc.

Le code sur mesure a été maintenu à un minimum absolu et même dans ce cas, il a dû être confirmé par différents styles de codage et de rapport.

Je suppose que vous connaissez déjà les suites ETL . Il y a beaucoup de fonctionnalités que vous obtenez gratuitement ces jours-ci qui n'étaient pas présentes lorsque j'étais dans le jeu il y a une dizaine d'années.

Vous voudrez peut-être également examiner les data marts pour présenter une version plus conviviale et aseptisée de votre entrepôt de données. Ce n'est pas une solution miracle, bien sûr, mais cela pourrait aider à résoudre certains problèmes plutôt que d'avoir à reconstruire / corriger votre entrepôt de données.

Robbie Dee
la source
merci pour la réponse. Oui, nous utilisons tous ces champs, mais ils ne contribuent vraiment qu'à l'identification d'une seule ligne, pas aux dépendances entre les flux, les couches et les systèmes. Vous avez raison au sujet des suites ETL - nous étions en train de passer à un outil ETL bien connu à partir d'un outil qui était hors de support mais qui a fini par revenir à PLSQL. C'est bien de coder, mais pour la maintenabilité et pour comprendre le système global à partir du niveau de code, c'est absolument terrible.
Christs_Chin
1
L'idéal est que vous puissiez suivre les données de bout en bout, que ce soit via des tables de transfert ou des fichiers plats, mais si vous ne les avez pas, vous vous retrouvez avec du code de marche.
Robbie Dee
0

Je ne sais pas dans quelle mesure cela est pertinent pour votre cas, il existe des stratégies pour rendre les dépendances plus visibles et la maintenance générale du code-

  • Évitez les variables globales, utilisez plutôt des paramètres. Cela s'applique également aux appels multilingues.
  • Évitez autant que possible de modifier / muter les valeurs des variables. Créez une nouvelle variable et utilisez, si vous devez modifier la valeur, si possible.
  • Rendez le code modulaire. S'il n'est pas possible de décrire ce que fait (pas comment) la portion est réellement en train de faire dans une phrase simple, décomposez-la en modules qui satisfont la condition.
  • Nommez correctement vos portions de code. Lorsque vous pouvez réellement décrire ce qu'une portion de code fait en termes simples, ces termes deviennent le nom de la portion. Ainsi, le code devient auto-documenté à travers les noms des modules / classes / fonctions / procédures / méthodes etc.
  • Testez votre code. Testez si les entités de votre code justifient leurs noms, discuté au point précédent.
  • Consigner les événements dans le code. Maintenez au moins deux niveaux de journal. Le premier est toujours activé (même en production) et enregistre uniquement les événements critiques. Et utilisez l'autre pour tout enregistrer, mais vous pouvez l'activer ou le désactiver.
  • Trouvez et utilisez des outils appropriés pour parcourir, maintenir et développer votre base de code. Même une simple option «Rechercher tout» de Visual Studio Code m'a beaucoup simplifié la vie dans certains cas.
Gulshan
la source