es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

¿Cómo conectar al servicio de SQL Server desde Docker en Docker?

Estoy intentando construir y ejecutar una aplicación ASP.NET Core y probarla con Newman. Aquí está la tubería que tengo:

services:
  - mcr.microsoft.com/mssql/server:2019-CU14-ubuntu-20.04
  - docker:19.03.12-dind

variables:
  VERSION: "0.0.0"
  ACCEPT_EULA: Y
  MSSQL_SA_PASSWORD: "***"
  DOCKER_TLS_CERTDIR: "/certs"

stages:
  - test

postman_tests:
  stage: test
  tags:
    - docker
  script:
    - docker run -p 5555:80 -v $(pwd)/CatalogService/:/app/ -w /app -e ASPNETCORE_URLS=http://+:80 -e ASPNETCORE_ENVIRONMENT=Development -t mcr.microsoft.com/dotnet/sdk:6.0.100-alpine3.14-amd64 dotnet run --project ./CatalogService.csproj
    - sleep 120s
    - docker run -v $(pwd)/test:/etc/newman -t postman/newman:alpine run "CatalogService.postman_collection.json" --reporters="cli"

Acabo de empezar hoy a aprender sobre Docker y cómo usarlo con la tubería de Gitlab, por favor háganme saber si tienen una mejor manera de hacerlo.

¿Por qué la aplicación no puede acceder al servicio de mssql? Este es el error que obtengo:

[...]
Status: Downloaded newer image for mcr.microsoft.com/dotnet/sdk:6.0.100-alpine3.14-amd64
Building...
info: Microsoft.EntityFrameworkCore.Infrastructure[10403]
      Entity Framework Core 6.0.0 initialized 'CatalogDb' using provider 'Microsoft.EntityFrameworkCore.SqlServer:6.0.0' with options: None
Unhandled exception. Microsoft.Data.SqlClient.SqlException (0x80131904): A network-related or instance-specific error occurred while establishing a connection to SQL Server. The server was not found or was not accessible. Verify that the instance name is correct and that SQL Server is configured to allow remote connections. (provider: TCP Provider, error: 35 - An internal exception was caught)
[...]

Y esta es la cadena de conexión que estoy utilizando en el archivo appsettings.json:

"ConnectionStrings": {
  "CatalogDb": "Password=****;Persist Security Info=True;User ID=SA;Database=CatalogDb;Server=mcr.microsoft.com__mssql__server"
},

Si ejecuto la siguiente tubería con la imagen .net sdk, entonces la aplicación comienza y puede conectarse a la base de datos. Pero de esta manera, ¿no puedo usar newman para probarla? ¿O sí?

build:
  stage: build
  tags:
    - docker
  image: 
    name: mcr.microsoft.com/dotnet/sdk:6.0
    entrypoint: [""]
  script:
    - dotnet build ./CatalogService.csproj --configuration Release --no-self-contained
    - dotnet run --project ./CatalogService.csproj
  variables: 
    ErrorActionPreference: stop

Actualización:

Agregué un alias y actualicé la cadena de conexión al servicio, pero aún no se conecta.

services:
  - name: mcr.microsoft.com/mssql/server:2019-CU14-ubuntu-20.04
    alias: mssql
  - docker:19.03.12-dind

Password=*****;Persist Security Info=True;User ID=SA;Database=CatalogDb;Server=mssql

También agregué la variable FF_NETWORK_PER_BUILD según lo especificado aquí, pero la aplicación aún no se conecta a la base de datos.

postman_tests:
  stage: test
  tags:
    - docker
  variables:
    FF_NETWORK_PER_BUILD: "true"
  script:
    - docker run -p 5555:80 -v $(pwd)/CatalogService/:/app/ -w /app -e ASPNETCORE_URLS=http://+:80 -e ASPNETCORE_ENVIRONMENT=Development -t mcr.microsoft.com/dotnet/sdk:6.0.100-alpine3.14-amd64 dotnet run --project ./CatalogService.csproj
    - sleep 120s
    - docker run -v $(pwd)/test:/etc/newman -t postman/newman:alpine run "CatalogService.postman_collection.json" --reporters="cli"

Actualización con archivo completo .yml:

Esta tubería tiene 3 etapas:

  1. construir/publicar el origen
  2. construir la imagen de Docker para probar la aplicación
  3. probar la aplicación con una base de datos y postman
variables:
  DOCKER_TLS_CERTDIR: "/certs"
  REGISTRY_TENANT: TTT
  REGISTRY_URL: UUU
  REGISTRY_NAME: NNN
  IMAGE_NAME: image

stages:
  - build
  - docker
  - test

buld_source:
  stage: build
  tags:
    - docker
  image: mcr.microsoft.com/dotnet/sdk:6.0
  script:
    - dotnet clean
    - dotnet build /builds/xxx.sln --configuration Release
    - dotnet publish /builds/xxx1.csproj --output ./publish/xxx1
    - dotnet publish /builds/xxx2.csproj --output ./publish/xxx2
  artifacts:
    paths:
      - ./publish/*
    expire_in: 1 hour
  variables: 
    ErrorActionPreference: stop


docker_test_image:
  stage: docker
  needs: ["buld_source"]
  tags:
    - docker
  variables:
    RUNTIME_IMAGE: mcr.microsoft.com/dotnet/aspnet:6.0
    DOCKER_DRIVER: overlay2
  services:
    - docker:20.10.12-dind
  script:
    # Preparar Dockerfile
    - sed -i "s~\$DOCKERIMAGE~$RUNTIME_IMAGE~g" Dockerfile
    - sed -i 's/\$ENVIRONMENT/Testing/g' Dockerfile
    - sed -i "s/\$ENTRYPOINT/xxx1.dll/g" Dockerfile
    - cat Dockerfile
    # Procesar Dockerfile
    - docker login $REGISTRY_URL -u $REGISTRY_NAME -p $REGISTRY_PASS
    - docker build --tag "$REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA" .
    - docker push "$REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA"


postman_tests:
  stage: test
  needs: ["docker_test_image"]
  tags:
    - docker
  services:
    - docker:20.10.12-dind
  dependencies: []
  variables:
    DOCKER_DRIVER: overlay2
  before_script:
    - docker login $REGISTRY_URL -u $REGISTRY_NAME -p $REGISTRY_PASS
  script:
    - docker network create -d bridge network
    - docker run --name mcr.microsoft.commssqlserver --network network -p 1433:1433 -e "ACCEPT_EULA=Y" -e "MSSQL_SA_PASSWORD=ppp" -d mcr.microsoft.com/mssql/server:2019-Latest
    - sleep 30s
    - docker logs mcr.microsoft.commssqlserver
    - docker run --network network --name xxx1 -p 5535:5535 -d $REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA
    - sleep 30s
    - docker logs xxx1
    - docker run --network network -v $(pwd)/test:/etc/newman -t postman/newman:alpine run "xxx1.postman_collection.json" --reporters="cli"
    - sleep 5s
    - docker rmi -f $REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA
Tags:  , , , ,

Answer

  1. Avatar for davy.ai

    Construyendo y ejecutando una aplicación ASP.NET Core con Docker y pruebas de Newman

    Este es un pipeline de GitLab que construye y ejecuta una aplicación ASP.NET Core y la prueba con Newman. El pipeline tiene tres etapas:

    1. Construcción y publicación del código fuente
    2. Construcción de una imagen de Docker para probar la aplicación
    3. Pruebas de la aplicación con una base de datos y Postman

    Aquí está el código del pipeline:

    variables:
      DOCKER_TLS_CERTDIR: "/certs"
      REGISTRY_TENANT: TTT
      REGISTRY_URL: UUU
      REGISTRY_NAME: NNN
      IMAGE_NAME: image
    
    stages:
      - build
      - docker
      - test
    
    build_source:
      stage: build
      tags:
        - docker
      image: mcr.microsoft.com/dotnet/sdk:6.0
      script:
        - dotnet clean
        - dotnet build /builds/xxx.sln --configuration Release
        - dotnet publish /builds/xxx1.csproj --output ./publish/xxx1
        - dotnet publish /builds/xxx2.csproj --output ./publish/xxx2
      artifacts:
        paths:
          - ./publish/*
        expire_in: 1 hour
      variables: 
        ErrorActionPreference: stop
    
    docker_test_image:
      stage: docker
      needs: ["build_source"]
      tags:
        - docker
      variables:
        RUNTIME_IMAGE: mcr.microsoft.com/dotnet/aspnet:6.0
        DOCKER_DRIVER: overlay2
      services:
        - docker:20.10.12-dind
      script:
        # Prepare Dockerfile
        - sed -i "s~\$DOCKERIMAGE~$RUNTIME_IMAGE~g" Dockerfile
        - sed -i 's/\$ENVIRONMENT/Testing/g' Dockerfile
        - sed -i "s/\$ENTRYPOINT/xxx1.dll/g" Dockerfile
        - cat Dockerfile
    
        # Process Dockerfile
        - docker login $REGISTRY_URL -u $REGISTRY_NAME -p $REGISTRY_PASS
        - docker build --tag "$REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA" .
        - docker push "$REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA"
    
    postman_tests:
      stage: test
      needs: ["docker_test_image"]
      tags:
        - docker
      services:
        - docker:20.10.12-dind
      dependencies: []
      variables:
        DOCKER_DRIVER: overlay2
      before_script:
        - docker login $REGISTRY_URL -u $REGISTRY_NAME -p $REGISTRY_PASS
      script:
        - docker network create -d bridge network
        - docker run --name mcr.microsoft.com__mssql__server --network network -p 1433:1433 -e "ACCEPT_EULA=Y" -e "MSSQL_SA_PASSWORD=ppp" -d mcr.microsoft.com/mssql/server:2019-latest
        - sleep 30s
        - docker logs mcr.microsoft.com__mssql__server
        - docker run --network network --name xxx1 -p 5535:5535 -d $REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA
        - sleep 30s
        - docker logs xxx1
        - docker run --network network -v $(pwd)/test:/etc/newman -t postman/newman:alpine run "xxx1.postman_collection.json" --reporters="cli"
        - sleep 5s
        - docker rmi -f $REGISTRY_URL/$IMAGE_NAME:$CI_COMMIT_SHORT_SHA
    

    El pipeline utiliza Docker para construir, ejecutar y probar la aplicación. La etapa build_source utiliza la imagen .NET SDK para construir y publicar el código fuente. La etapa docker_test_image construye una imagen de Docker a partir del código fuente y la ejecuta. La etapa postman_tests crea una red, inicia un contenedor SQL Server, inicia el contenedor de la aplicación y ejecuta la prueba de Postman contra la aplicación.

    En la etapa build_source, definimos la imagen y el script utilizados para construir y publicar el código fuente. Ejecutamos los comandos dotnet para limpiar, construir y publicar el código. Configuramos las rutas de artefactos para la salida publicada y establecemos un tiempo de caducidad.

    En la etapa docker_test_image, preparamos el archivo Dockerfile y construimos la imagen utilizando el comando docker. Empujamos la imagen a un registro y establecemos el nombre de la imagen en el SHA corto de confirmación.

    En la etapa postman_tests, definimos una red e iniciamos los contenedores SQL Server y de la aplicación. Ejecutamos las pruebas de Postman contra el contenedor de la aplicación y limpiamos la imagen después de la prueba. Utilizamos el comando $(pwd) para obtener el directorio de trabajo actual para la ruta de la prueba de Postman.

    El contenedor de la aplicación se está ejecutando en el puerto 5535 en la etapa docker_test_image. Podemos actualizar la etapa postman_tests para probar la aplicación utilizando la URL `http://xxx1:5535`.

    Para solucionar los problemas de que el contenedor de la aplicación no accede a SQL Server, agregamos un alias al contenedor SQL Server y actualizamos la cadena de conexión para usar el nombre de alias. También agregamos la variable FF_NETWORK_PER_BUILD a la etapa postman_tests. Sin embargo, descubrimos que el problema se debía a un error tipográfico en el archivo appsettings.json. El valor server debería ser mssql en lugar de mcr.microsoft.com__mssql__server.

Comments are closed.