web-dev-qa-db-fra.com

Jenkins - Récupérer la sortie complète de la console pendant l'étape de construction

Cela fait des jours que je parcours l’internet, j’ai un problème similaire à this .

J'ai besoin de récupérer la sortie de la console en texte brut (brut). Mais si je peux l’obtenir en HTML, c’est très bien aussi, je peux toujours l’analyser. La seule chose à faire est que j’ai besoin de l’obtenir lors de l’étape de construction, ce qui pose un problème car l’emplacement où il devrait être disponible est tronqué ...

J'ai essayé de récupérer la sortie de la console à partir des URL suivantes (par rapport au travail):

  • /consoleText
  • /logText/progressiveText
  • /logText/progressiveHTML

Les deux textes sont en texte brut et seraient parfaits si ce n’était pour la troncature, il en va de même pour le HTML ... exactement ce dont j'ai besoin - seulement sa troncature ....

Je suis sûr qu'il est possible de récupérer ces informations d'une manière ou d'une autre, car lors de l'affichage de /consoleFull, il existe une mise à jour en temps réel de la console, sans tronquer ni mettre en mémoire tampon.

Cependant, en examinant cette page Web, au lieu de trouver le contenu que je souhaitais, j’ai trouvé ce code où il aurait dû être (je n’ai pas inclus le code des pages complètes, car ce serait en grande partie hors de propos, et je crois que les personnes qui répondraient pourraient pour savoir et savoir ce qui devrait être là par eux-mêmes)

      new Ajax.Request(href,{
          method: "post",
          parameters: {"start":e.fetchedBytes},
        requestHeaders: headers,
          onComplete: function(rsp,_) {

          var stickToBottom = scroller.isSticking();
          var text = rsp.responseText;
          if(text!="") {
            var p = document.createElement("DIV");
            e.appendChild(p); // Needs to be first for IE
            // Use "outerHTML" for IE; workaround for:
            // http://www.quirksmode.org/bugreports/archives/2004/11/innerhtml_and_t.html
            if (p.outerHTML) {
              p.outerHTML = '<pre>'+text+'</pre>';
              p = e.lastChild;
            }
            else p.innerHTML = text;
            Behaviour.applySubtree(p);
            if(stickToBottom) scroller.scrollToBottom();
          }

          e.fetchedBytes     = rsp.getResponseHeader("X-Text-Size");
          e.consoleAnnotator = rsp.getResponseHeader("X-ConsoleAnnotator");
            if(rsp.getResponseHeader("X-More-Data")=="true")
              setTimeout(function(){fetchNext(e,href);},1000);
          else
              $("spinner").style.display = "none";
          }
      });

Plus précisément, j'espère qu'il sera possible d'obtenir le contenu de text quoi qu'il en soit. Je ne suis pas familier avec cette langue et je ne sais donc pas comment je pourrais obtenir le contenu que je veux. Les plugins ne m'aideront pas car je veux récupérer ce contenu dans le cadre de mon script pendant la phase de construction

17
Inbar Rose

Vous avez déjà fait une très bonne enquête. Je ne peux ajouter que les éléments suivants: tous les plug-ins liés à la console que je connais sont conçus comme des actions de post-génération. 

Le Log Trigger plugin fournit une action post-build qui permet à Hudson construit pour rechercher leur journal de console pour une expression régulière donnée et si trouvé, déclenche des travaux en aval supplémentaires.

Il semble donc qu'il n'y ait pas de solution simple à votre problème. Je peux voir les options suivantes:

1. Utilisez tee ou quelque chose de similaire (applicable aux étapes de construction de Shell uniquement)

Cette solution est loin d’être universelle, mais elle peut fournir un accès rapide à la dernière sortie de la console, produite par une commande ou un ensemble de commandes. 

tee - lit à partir de l'entrée standard et écrit dans la sortie standard et les fichiers

L'utilisation de synonymes au niveau du système peut être modifiée par d'autres étapes de génération Jenkins afin de produire une sortie de la console. Les fichiers avec une sortie de console peuvent être référencés via Jenkins ou de toute autre manière.

2. Modifier le code Jenkins

Vous pouvez simplement faire une solution rapide pour une utilisation interne ou fournir un correctif introduisant un paramètre spécifique à l’échelle du système. 

3. Comportement imité/console

Le code dans votre exemple est utilisé pour demander des mises à jour du serveur Jenkins. Comme vous vous en doutez, le serveur peut renvoyer des informations en commençant par un décalage. Laisse moi voir.


Périodiquement, la page de la console envoie des requêtes au serveur:

enter image description here


Les paramètres sont simples:

enter image description here


Response est un bloc d'informations à ajouter:

enter image description here


Une autre requête avec valeur offset (début) mise à jour

enter image description here


Vous pouvez facilement comprendre qu'il n'y a pas de données en analysant Content-Length

enter image description here


La réponse est donc la suivante: utilisez url/nom-travail/numéro-construction/logText/progressiveHtml, spécifiez le décalage de début, la demande d'envoi et la mise à jour de la console.

19
Renat Gilmanov

Pour ajouter un aperçu: lorsque la construction de Jenkins était en cours, la réponse pour l'URL .../consoleText a été fixée à 10000 lignes au maximum. J'utilisais le paquet 'request ()' en Python. J'ai essayé la même URL avec curl et je n'ai reçu à nouveau que les premières lignes de 10 Ko . Ce n'est qu'après la fin de la construction que les deux méthodes ont renvoyé le journal complet (> 22 lignes dans mon cas).

Je ferai des recherches plus approfondies et j'espère pouvoir faire rapport.

[2015-08-18] Mise à jour: Il semble que ce problème soit connu ( voir ici) et il a été résolu dans Jenkins 1.618 et versions ultérieures. Je suis toujours en cours d'exécution 1.615 donc je ne peux pas vérifier . Amir

1
Amir Katz

J'ai eu un problème similaire, la dernière partie de mon script de génération Jenkinsfile doit analyser le journal ConsoleLog pour des messages d'erreur particuliers à mettre dans un rapport de génération d'e-mail. 

Première tentative: requête http.
Cela ressemblait à un bidouillage, cela fonctionnait pour la plupart, mais nous avons rencontré des problèmes lorsque nous avons verrouillé l'accès au serveur Jenkins.

Deuxième tentative: utilisez les API pour énumérer les lignes de journal.
Cela semblait être la bonne chose à faire, mais cela a terriblement échoué car il fallait 30 minutes à mes nœuds pour parcourir les fichiers journaux de 100 Mo. Mon hypothèse est que le serveur Jenkins ne mettait pas le fichier en cache, donc chaque demande impliquait une relecture de la totalité du fichier jusqu'au point de la dernière lecture.

Troisième solution et la plus réussie: exécutez grep sur le serveur. 

node('master') {  
  sh 'grep some_criteria $JENKINS_HOME/workspace/path/to/job/console.log'  
}

c'était rapide, fiable et peu importait la taille des fichiers journaux.

Oui, cela nécessitait la confiance de l’administrateur Jenkins et la connaissance des chemins de répertoire sur le serveur Jenkins - mais puisque j’étais l’administrateur, je me suis confié pour faire le bon choix. Votre kilométrage peut varier.

0
Jason De Arte