Integrar la ingeniería de software en el mundo cotidiano

Compartir por correo electrónico

Soy miembro del equipo de investigación de Berger-Levrault desde hace 6 años. Y, uno de nuestros principales retos es integrar nuestra innovación en el día a día de la empresa. Hay varias formas de incorporar la innovación: como biblioteca de código externa, proporcionando esquemas, enseñando a utilizar nuevas herramientas, etc. En esta entrada del blog, presentaré cómo integramos el trabajo de ingeniería de software en las herramientas cotidianas de los desarrolladores.


La ingeniería de software consiste en ayudar a las personas a desarrollar grandes sistemas de software. En Software Engineering Research, construimos herramientas que ayudan a migre su aplicacióno mejorar su arquitectura de software. Sin embargo, este tipo de innovaciones no están pensadas para ser utilizadas todos los días. Por ejemplo, una vez migrada la aplicación, la gente no reutiliza (para la misma aplicación) la herramienta de migración.

Otras innovaciones consisten en diseñar nuevas visualizaciones o proporcionando diagnóstico sobre el código. Este tipo de innovaciones son mejores cuando se actualizan automáticamente con el código. De hecho, cuando se utiliza un mapa, la gente espera que el mapa se actualice. Lo mismo ocurre con los esquemas de software o las críticas al código. Otra limitación para los desarrolladores es que el uso de estas innovaciones debe ser lo más fácil e integrado posible con sus herramientas actuales.

En Berger-Levrault, utilizamos Moose para analizar sistemas de software. Moose nos permite crear visualizaciones y diagnósticos sobre el código. Hoy presentaremos cómo se puede producir una visualización UML básica de su código e integrarla en el wiki de GitLab. A continuación, presentaremos cómo integrar los diagnósticos avanzados de Moose en el conocido Herramienta SonarQube. Por último, exponemos la integración en editor de texto e IDE como VSCode.

Realizar análisis en una IC

El primer paso para realizar el análisis cuando los desarrolladores están trabajando en el código es utilizar el CI para realizar nuestro análisis.

El proceso principal es el siguiente: los desarrolladores editan el código, lo envían a un repositorio git, el CI instala las dependencias del código, nuestra herramienta analiza el código y los nuevos resultados se envían a las herramientas de los desarrolladores.

Considerando el GitLab CI, se requieren dos pasos preliminares para realizar el análisis. La figura siguiente presenta el archivo GitLab CI .gitlab-ci.yml

etapas:
  - instalar
  - analizar

# Instalar las dependencias
instalar
  stage: install
  imagen:     
    nombre: kaiwinter/docker-java8-maven
  script:
# '../maven/settings - critics.xml' establece el repositorio maven en './repo'
    - mvn clean install --settings '../maven/settings - critics.xml' -Dmaven.test.skip=true
  artefactos:
    paths:
      - repo

parse:
  escenario: parse
  imagen:     
    nombre: ghcr.io/evref-bl/verveinej:v3.0.13
    punto de entrada: [""]
  necesidades:
    - job: install
      artefactos: true
  script:
    - /VerveineJ-3.0.13/verveinej.sh -format json -o output.json -alllocals -anchor assoc -autocp ./repo .
  artefactos:
    rutas:
      - output.json

El paso instalar consiste en utilizar Maven (en el caso de código Java) para instalar las dependencias del proyecto. Este paso es opcional pero ayuda a obtener mejores resultados en futuros análisis.

El paso analizar utiliza VerveineJuna herramienta que analiza el código Java y produce un modelo del código que puede utilizarse para el análisis.

Una vez realizados estos pasos preliminares, tenemos que pedir al CI que ejecute el análisis y envíe los resultados a la plataforma de destino.

Integración de visualizaciones en la wiki de GitLab

Para integrar el esquema en la wiki de GitLab, hay dos opciones: utilizar el esquema markdown nativo, o exportar la visualización como png e integrar el archivo png en markdown.

En esta entrada del blog, nos centraremos en el esquema Markdown nativo utilizando MermaidJS. Para utilizar Mermaid con Moose, utilizamos la función MermaidPharo proyecto. La configuración del CI para integrar la visualización en el wiki de GitLab se realiza en tres pasos:

  1. Añadimos un archivo de configuración llamado .smalltalk.ston. Este archivo configura el CI para instalar el proyecto MermaidPharo
SmalltalkCISpec {
    1TP5Carga : [
        SCIMetacelloLoadSpec {
            #baseline : 'MermaidPharo',
            #repository : 'github://badetitou/MermaidPharo:main',
            #directory : 'src',
            #platforms : [ #pharo ],
            #onConflict : #useIncoming,
            #load : [ 'moose' ],
            #onUpgrade : #useIncoming
        }
    ],
    #testing: {
    #failOnZeroTests : false
    }
}
  1. Añadir un Pharo guión en ci/ejecutarCódigo.st que realizará el análisis.
"=== Cargar MooseModel ==="
model := FamixJavaModel new.
'./output.json' asFileReference readStreamDo: [ : stream | model importFromJSONStream: stream ].
model rootFolder: '.'.

diagrama := Famix2Mermaid nuevo
     modelo: modelo;
     generarDiagramaClase.

visitante := MeWritterVisitor nuevo.
visitante endOfLine: String crlf.

"Exportar el diagrama en el archivo markdown './wiki-export/mermaid.md'"
'./wiki-export/mermaid.md' asFileReference ensureCreateFile; writeStreamDo: [ :stream |
    stream << '```mermaid'; << String crlf.
    diagram exportWith: visitor to: stream.
    stream << String crlf; << String crlf; << '```'; << String crlf.
].
 Stdio stderr << '=== Fin Pharo ===' << String crlf.
Smalltalk snapshot: false andQuit: true
  1. Por último, actualizamos el .gitlab-ci.yml para ejecutar el análisis Moose y actualizar el proyecto wiki de GitLab
analizar:
  stage: analyze
  imagen: hpiswa/smalltalkci
  variables:
    ORIGIN_IMAGE_NAME: BLMoose
  necesidades:
    - job: parse
    artefactos: true
  script:
    # Configurar una imagen de Moose para el análisis
    - apt-get install -y wget unzip
    - wget -O artifacts.zip --header "PRIVATE-TOKEN: $GILAB_TOKEN" "https://my.private.gitlab.com/api/v4/projects/219/jobs/artifacts/main/download?job=Moose64-10.0";
    - descomprimir artefactos.zip

    # Instalar Moose usando .smalltalk.ston
    - smalltalkci -s "Moose64-10" --image "$ORIGIN_IMAGE_NAME/$ORIGIN_IMAGE_NAME.image"

    # Ejecutar código de análisis
    - /root/smalltalkCI-master/_cache/vms/Moose64-10/pharo --headless BLMoose/BLMoose.image st ./ci/executeCode.st

    # Configurar y actualizar el Wiki
    - export WIKI_URL="${CI_SERVER_PROTOCOL}://nombre_usuario:${USER_TOKEN}@${CI_SERVER_HOST}:${CI_SERVER_PORT}/${CI_PROJECT_PATH}.wiki.git"

    # Desactiva la comprobación ssl que pueda fallar
    - git config --global http.sslverify "false"
    - rm -rf "/tmp/${CI_PROJECT_NAME}.wiki"
    - git clone "${WIKI_URL}" /tmp/${CI_PROJECT_NAME}.wiki
    - rm -rf "/tmp/${CI_PROJECT_NAME}.wiki/wiki-export"
    - rm -rf "/tmp/${CI_PROJECT_NAME}.wiki/wiki-export"
    - mv -f wiki-export /tmp/${CI_PROJECT_NAME}.wiki
    - cd /tmp/${CI_PROJECT_NAME}.wiki

    # configurar committer info
    - git config user.name "$GITLAB_USER_NAME"
    - git config user.email "$GITLAB_USER_EMAIL"

    # confirmar el archivo
    - git add -A
    - git commit -m "Archivo auto-actualizado en CI"

    # empuja el cambio de nuevo a la rama maestra de la wiki
    - git push origin "HEAD:main"

Envíe diagnósticos avanzados a SonarQube

Otra integración posible es con SonarQube. De nuevo, para realizar la integración SonarQube, tenemos que modificar .smalltalk.ston, ci/ejecutarCódigo.sty .gitlab-ci.yml. También tenemos que crear un informes/reglas/reglas.ston que contiene las reglas ejecutadas por Moose.

  1. Para el .smalltalk.stonesta vez, cargamos el FamixCritics al proyecto SonarQube
SmalltalkCISpec {
    1TP5Carga : [
        SCIMetacelloLoadSpec {
            #baseline : 'FamixCriticSonarQubeExporter',
            #repository : 'github://badetitou/Famix-Critic-SonarQube-Exporter:main',
            #directory : 'src',
            #platforms : [ #pharo ],
            #onConflict : #useIncoming,
            #onUpgrade : #useIncoming
        }
    ],
    #testing: {
        #failOnZeroTests : false
    }
}
  1. Para el informes/reglas/reglas.stonincluye las reglas que Moose ejecutará al analizar el código. La creación de este archivo es fácil gracias al navegador Critics de Moose. El ejemplo siguiente presenta una regla que comprueba que los atributos Java no empiezan por _.
FamixCBContext {
    #contextBlock : '[ :colección | | colección select: [ :el | el isKindOf: FamixJavaAttribute ] ]',
    #summary : '',
    #name : 'FamixJavaAttribute';
}FamixCBCondition {
    #query : '[ :entidad | nombre entidad beginsWith: \'_\' ]',
    #summary : '# El nombre del atributo no puede empezar por _\r\rUn atributo no debe empezar por `_`',
    #name : 'El nombre del atributo no puede empezar por _';
}OrderedCollection [
    0,
    1
]
  1. Para el ci/ejecutarCódigo.st, pedimos a Moose que cargue las reglas previamente definidas, las ejecutamos, y generamos el fichero compatible SonarQube a partir de los resultados
"=== Cargar MooseModel ==="
model := FamixJavaModel new.
'./output.json' asFileReference readStreamDo: [ : stream | model importFromJSONStream: stream ].
model rootFolder: '.'.

"Ejecutar reglas"
criticBrowser := MiCriticBrowser on: MiCriticBrowser newModel.
'./informes/reglas/reglas.ston' asFileReference readStreamDo: [ :stream | criticBrowser importRulesFromStream: stream ].
criticBrowser model setEntities: model.
criticBrowser modelo ejecutar.
violaciones := modelo criticBrowser getAllViolations.
    
"Exportar críticas al archivo './reports/sonarGenericIssue.json' asFileReference"
targetRef := './informes/sonarGenericIssue.json' asFileReference.
FmxCBSQExporter nuevo
   violaciones: violaciones;
    targetFileReference: targetRef;
    exportar.
  1. Por último, actualizamos el .gitlab-ci.yml para ejecutar el análisis y enviar los resultados a SonarQube
analizar:
    stage: analyze
    imagen: hpiswa/smalltalkci
    variables:
        ORIGIN_IMAGE_NAME: BLMoose
    necesidades:
        - job: parse
        artefactos: true
    script:
        # Configurar una imagen de Moose para el análisis
        - apt-get install -y wget unzip
        - wget -O artifacts.zip --header "PRIVATE-TOKEN: $GILAB_TOKEN" "https://my.private.gitlab.com/api/v4/projects/219/jobs/artifacts/main/download?job=Moose64-10.0"'
        - descomprimir artifacts.zip
         # Instalar Moose usando .smalltalk.ston
        - smalltalkci -s "Moose64-10" --image "$ORIGIN_IMAGE_NAME/$ORIGIN_IMAGE_NAME.image"
         # Ejecutar código de análisis
        - /root/smalltalkCI-master/_cache/vms/Moose64-10/pharo --headless BLMoose/BLMoose.image st ./ci/executeCode.st
    artefactos:
      paths:
        - reports/sonarGenericIssue.json
        expire_in: 1 semana
        
sonar
    stage: sonar
    imagen: kaiwinter/docker-java8-maven
    necesidades:
        - job: analizar
        artefactos: true
    variables:
        MAVEN_CLI_OPTS: '--batch-mode -Xmx10g -XX:MaxPermSize=10g'
        SONAR_URL: 'https://my.private.gitlab.com'
    script:
        - mvn clean install sonar:sonar -Dsonar.projectKey=$PROJECT_KEY -Dsonar.host.url=$SONAR_URL -Dsonar.login=$MOOSE_SONAR_TOKEN -Dsonar.externalIssuesReportPaths=../reports/sonarGenericIssue.json --settings '../maven/settings - critics.xml' -Dmaven.test.skip=true

Las críticas están disponibles a través de la interfaz SonarQube.

Problema con DASH en SonarQube

Integración con VSCode

La última gran integración posible es la integración de Critics (ver sección con SonarQube) directamente dentro de VSCode. Este enfoque es similar al de SonarLint.

Para lograr dicha integración, también utilizamos Moose y Pharo, y sobre todo, utilizamos el módulo Protocolo del servidor de idiomas y su implementación para Pharo (badetitou.pharo-servidor-de-idiomas). Lo hemos ampliado para calcular las mismas críticas que nuestro CI. Y muestra directamente las críticas dentro del entorno de los desarrolladores.

El BL Language Server (extensión de Berger-Levrault para VSCode) muestra un error directamente dentro del IDE del desarrollador

Más ...

Scroll al inicio