Delen via


Docker-implementatie

Tip

Zelfs als u bekend bent met Docker of Orleans, is het raadzaam dit artikel tot het einde te lezen om problemen te voorkomen die u kunt tegenkomen met tijdelijke oplossingen.

Dit artikel en het bijbehorende voorbeeld zijn een werk dat wordt uitgevoerd. Alle feedback, pull-aanvragen of suggesties zijn welkom.

Oplossingen implementeren Orleans in Docker

Implementeren in Orleans Docker kan lastig zijn gezien de manier waarop Docker-orchestrators en clusteringstacks zijn ontworpen. Het meest gecompliceerde is om inzicht te hebben in het concept van Overlay Network van Docker Swarm en Kubernetes-netwerkmodel.

Docker-containers en netwerkmodellen zijn ontworpen om voornamelijk stateless en onveranderbare containers uit te voeren. Het opzetten van een cluster met node.js- of Nginx-toepassingen is dus vrij eenvoudig. Als u echter iets uitgebreider probeert te gebruiken, zoals een echte geclusterde of gedistribueerde toepassing (zoals Orleansop basis van toepassingen) ondervindt u uiteindelijk problemen bij het instellen ervan. Het is mogelijk, maar niet zo eenvoudig als webtoepassingen.

Docker-clustering bestaat uit het samenstellen van meerdere hosts om te werken als één groep resources, beheerd met behulp van een Container Orchestrator. Docker Inc. geef Swarm op als hun optie voor Container Orchestration terwijl Google Kubernetes (ook wel K8s genoemd) heeft. Er zijn andere Orchestrators zoals DC/OS, Mesos, maar in dit document zullen we het hebben over Swarm en K8s, omdat ze veel meer worden gebruikt.

Dezelfde graaninterfaces en implementaties die overal Orleans worden uitgevoerd, worden ook uitgevoerd in Docker-containers. Er zijn geen speciale overwegingen nodig om uw toepassing in Docker-containers uit te voeren.

De concepten die hier worden besproken, kunnen worden gebruikt voor zowel .NET Core als .NET 4.6.1, Orleans maar om de platformoverschrijdende aard van Docker en .NET Core te illustreren, gaan we ons richten op het voorbeeld waarbij u .NET Core gebruikt. In dit artikel vindt u mogelijk platformspecifieke gegevens (Windows/Linux/OSX).

Vereisten

In dit artikel wordt ervan uitgegaan dat u de volgende vereisten hebt geïnstalleerd:

  • Docker - Docker4X heeft een gebruiksvriendelijk installatieprogramma voor de belangrijkste ondersteunde platforms. Het bevat docker-engine en ook Docker Swarm.
  • Kubernetes (K8s) - Google's aanbieding voor Container Orchestration. Het bevat richtlijnen voor het installeren van Minikube (een lokale implementatie van K8s) en kubectl , samen met alle afhankelijkheden.
  • .NET - Platformoverschrijdende smaak van .NET
  • Visual Studio Code (VSCode): u kunt elke gewenste IDE gebruiken. VSCode is platformoverschrijdend, dus we gebruiken het om ervoor te zorgen dat het werkt op alle platforms. Nadat u VSCode hebt geïnstalleerd, installeert u de C#-extensie.

Belangrijk

U hoeft Kubernetes niet te laten installeren als u deze niet gaat gebruiken. Docker4X-installatieprogramma bevat al Swarm, dus er is geen extra installatie vereist om het te gebruiken.

Notitie

In Windows schakelt Docker Installer Hyper-V in tijdens het installatieproces. Aangezien in dit artikel en de voorbeelden .NET Core worden gebruikt, zijn de gebruikte containerinstallatiekopieën gebaseerd op Windows Server NanoServer. Als u niet van plan bent om .NET Core te gebruiken en .NET 4.6.1 volledig framework gebruikt, moet de gebruikte installatiekopieën Windows Server Core en de 1.4+ versie van Orleans (die alleen .NET full Framework ondersteunt).

Orleans-oplossing maken

In de volgende instructies ziet u hoe u een reguliere Orleans oplossing maakt met behulp van de nieuwe dotnet hulpmiddelen.

Pas de opdrachten aan op wat geschikt is voor uw platform. De mapstructuur is ook slechts een suggestie. Pas het aan uw behoeften aan.

mkdir Orleans-Docker
cd Orleans-Docker
dotnet new sln
mkdir -p src/OrleansSilo
mkdir -p src/OrleansClient
mkdir -p src/OrleansGrains
mkdir -p src/OrleansGrainInterfaces
dotnet new console -o src/OrleansSilo --framework netcoreapp1.1
dotnet new console -o src/OrleansClient --framework netcoreapp1.1
dotnet new classlib -o src/OrleansGrains --framework netstandard1.5
dotnet new classlib -o src/OrleansGrainInterfaces --framework netstandard1.5
dotnet sln add src/OrleansSilo/OrleansSilo.csproj
dotnet sln add src/OrleansClient/OrleansClient.csproj
dotnet sln add src/OrleansGrains/OrleansGrains.csproj
dotnet sln add src/OrleansGrainInterfaces/OrleansGrainInterfaces.csproj
dotnet add src/OrleansClient/OrleansClient.csproj reference src/OrleansGrainInterfaces/OrleansGrainInterfaces.csproj
dotnet add src/OrleansSilo/OrleansSilo.csproj reference src/OrleansGrainInterfaces/OrleansGrainInterfaces.csproj
dotnet add src/OrleansGrains/OrleansGrains.csproj reference src/OrleansGrainInterfaces/OrleansGrainInterfaces.csproj
dotnet add src/OrleansSilo/OrleansSilo.csproj reference src/OrleansGrains/OrleansGrains.csproj

Wat we tot nu toe hebben gedaan, was gewoon standaardcode voor het maken van de oplossingsstructuur en projecten en het toevoegen van verwijzingen tussen projecten. Niets anders dan een gewoon Orleans project.

Op het moment dat dit artikel is geschreven, Orleans bevindt 2.0 (de enige versie die .NET Core en platformoverschrijdend ondersteunt) zich in Technology Preview, zodat de NuGet-pakketten worden gehost in een MyGet-feed en niet worden gepubliceerd naar Nuget.org officiële feed. Als u de Preview NuGet-pakketten wilt installeren, gebruiken dotnet we CLI om de bronfeed en versie van MyGet af te dwingen:

dotnet add src/OrleansClient/OrleansClient.csproj package Microsoft.Orleans.Core -s https://dotnet.myget.org/F/orleans-prerelease/api/v3/index.json -v 2.0.0-preview2-201705020000
dotnet add src/OrleansGrainInterfaces/OrleansGrainInterfaces.csproj package Microsoft.Orleans.Core -s https://dotnet.myget.org/F/orleans-prerelease/api/v3/index.json -v 2.0.0-preview2-201705020000
dotnet add src/OrleansGrains/OrleansGrains.csproj package Microsoft.Orleans.Core -s https://dotnet.myget.org/F/orleans-prerelease/api/v3/index.json -v 2.0.0-preview2-201705020000
dotnet add src/OrleansSilo/OrleansSilo.csproj package Microsoft.Orleans.Core -s https://dotnet.myget.org/F/orleans-prerelease/api/v3/index.json -v 2.0.0-preview2-201705020000
dotnet add src/OrleansSilo/OrleansSilo.csproj package Microsoft.Orleans.OrleansRuntime -s https://dotnet.myget.org/F/orleans-prerelease/api/v3/index.json -v 2.0.0-preview2-201705020000
dotnet restore

Nu hebt u alle basisafhankelijkheden om een eenvoudige Orleans toepassing uit te voeren. Houd er rekening mee dat er tot nu toe niets is gewijzigd van uw reguliere Orleans toepassing. Nu gaan we wat code toevoegen, zodat we er iets mee kunnen doen.

Uw Orleans toepassing implementeren

Als u VSCode gebruikt, voert u deze uit code .vanuit de oplossingsmap. Hiermee opent u de map in VSCode en laadt u de oplossing.

Dit is de oplossingsstructuur die we zojuist hebben gemaakt.

Visual Studio Code: Explorer met Program.cs geselecteerd.

We hebben ook bestanden Program.cs, OrleansHostWrapper.cs, IGreetingGrain.cs en GreetingGrain.cs aan de interfaces en graanprojecten toegevoegd. Dit is de code voor deze bestanden:

IGreetingGrain.cs:

using System;
using System.Threading.Tasks;
using Orleans;

namespace OrleansGrainInterfaces
{
    public interface IGreetingGrain : IGrainWithGuidKey
    {
        Task<string> SayHello(string name);
    }
}

GreetingGrain.cs:

using System;
using System.Threading.Tasks;
using OrleansGrainInterfaces;

namespace OrleansGrains
{
    public class GreetingGrain : Grain, IGreetingGrain
    {
        public Task<string> SayHello(string name)
        {
            return Task.FromResult($"Hello from Orleans, {name}");
        }
    }
}

OrleansHostWrapper.cs:

using System;
using System.NET;
using Orleans.Runtime;
using Orleans.Runtime.Configuration;
using Orleans.Runtime.Host;

namespace OrleansSilo;

public class OrleansHostWrapper
{
    private readonly SiloHost _siloHost;

    public OrleansHostWrapper(ClusterConfiguration config)
    {
        _siloHost = new SiloHost(Dns.GetHostName(), config);
        _siloHost.LoadOrleansConfig();
    }

    public int Run()
    {
        if (_siloHost is null)
        {
            return 1;
        }

        try
        {
            _siloHost.InitializeOrleansSilo();

            if (_siloHost.StartOrleansSilo())
            {
                Console.WriteLine(
                    $"Successfully started Orleans silo '{_siloHost.Name}' as a {_siloHost.Type} node.");
                return 0;
            }
            else
            {
                throw new OrleansException(
                    $"Failed to start Orleans silo '{_siloHost.Name}' as a {_siloHost.Type} node.");
            }
        }
        catch (Exception exc)
        {
            _siloHost.ReportStartupError(exc);
            Console.Error.WriteLine(exc);

            return 1;
        }
    }

    public int Stop()
    {
        if (_siloHost is not null)
        {
            try
            {
                _siloHost.StopOrleansSilo();
                _siloHost.Dispose();
                Console.WriteLine($"Orleans silo '{_siloHost.Name}' shutdown.");
            }
            catch (Exception exc)
            {
                siloHost.ReportStartupError(exc);
                Console.Error.WriteLine(exc);

                return 1;
            }
        }
        return 0;
    }
}

Program.cs (Silo):

using System;
using System.Collections.Generic;
using System.Linq;
using System.NET;
using System.Threading.Tasks;
using Orleans.Runtime.Configuration;

namespace OrleansSilo
{
    public class Program
    {
        private static OrleansHostWrapper s_hostWrapper;

        static async Task<int> Main(string[] args)
        {
            int exitCode = await InitializeOrleansAsync();

            Console.WriteLine("Press Enter to terminate...");
            Console.ReadLine();

            exitCode += ShutdownSilo();

            return exitCode;
        }

        private static int InitializeOrleansAsync()
        {
            var config = new ClusterConfiguration();
            config.Globals.DataConnectionString =
                "[AZURE STORAGE CONNECTION STRING HERE]";
            config.Globals.DeploymentId = "Orleans-Docker";
            config.Globals.LivenessType =
                GlobalConfiguration.LivenessProviderType.AzureTable;
            config.Globals.ReminderServiceType =
                GlobalConfiguration.ReminderServiceProviderType.AzureTable;
            config.Defaults.PropagateActivityId = true;
            config.Defaults.ProxyGatewayEndpoint =
                new IPEndPoint(IPAddress.Any, 10400);
            config.Defaults.Port = 10300;
            var ips = await Dns.GetHostAddressesAsync(Dns.GetHostName());
            config.Defaults.HostNameOrIPAddress =
                ips.FirstOrDefault()?.ToString();

            s_hostWrapper = new OrleansHostWrapper(config);
            return hostWrapper.Run();
        }

        static int ShutdownSilo() =>
            s_hostWrapper?.Stop() ?? 0;
    }
}

Program.cs (client):

using System;
using System.NET;
using System.Threading;
using System.Threading.Tasks;
using Orleans;
using Orleans.Runtime.Configuration;
using OrleansGrainInterfaces;

namespace OrleansClient
{
    class Program
    {
        private static IClusterClient s_client;
        private static bool s_running;

        static async Task Main(string[] args)
        {
            await InitializeOrleansAsync();

            Console.ReadLine();

            s_running = false;
        }

        static async Task InitializeOrleansAsync()
        {
            var config = new ClientConfiguration
            {
                DeploymentId = "Orleans-Docker";
                PropagateActivityId = true;
            };
            var hostEntry =
                await Dns.GetHostEntryAsync("orleans-silo");
            var ip = hostEntry.AddressList[0];
            config.Gateways.Add(new IPEndPoint(ip, 10400));

            Console.WriteLine("Initializing...");

            using client = new ClientBuilder().UseConfiguration(config).Build();
            await client.Connect();
            s_running = true;
            Console.WriteLine("Initialized!");

            var grain = client.GetGrain<IGreetingGrain>(Guid.Empty);

            while (s_running)
            {
                var response = await grain.SayHello("Gutemberg");
                Console.WriteLine($"[{DateTime.UtcNow}] - {response}");

                await Task.Delay(1000);
            }
        }
    }
}

We gaan hier niet in op details over de graanuitvoering, omdat deze buiten het bereik van dit artikel valt. Controleer andere documenten met betrekking tot deze documenten. Deze bestanden zijn in wezen een minimale Orleans toepassing en we beginnen ermee om verder te gaan met de rest van dit artikel.

In dit artikel gebruiken OrleansAzureUtils we lidmaatschapsprovider, maar u kunt ook alle andere die al worden ondersteund door Orleans.

Het Dockerfile

Docker maakt gebruik van installatiekopieën om uw container te maken. Raadpleeg de Docker-documentatie voor meer informatie over het maken van uw eigen documentatie. In dit artikel gaan we officiële Microsoft-installatiekopieën gebruiken. Op basis van de doel- en ontwikkelplatforms moet u de juiste afbeelding kiezen. In dit artikel gebruiken microsoft/dotnet:1.1.2-sdk we een installatiekopieën op basis van Linux. U kunt bijvoorbeeld voor Windows gebruiken microsoft/dotnet:1.1.2-sdk-nanoserver . Kies er een die bij uw behoeften past.

Opmerking voor Windows-gebruikers: Zoals eerder vermeld, gebruiken we .NET Core en Orleans Technical Preview 2.0 in dit artikel om platformoverschrijdend te zijn. Als u Docker in Windows wilt gebruiken met de volledig uitgebrachte Orleans versie 1.4+, moet u de installatiekopieën gebruiken die zijn gebaseerd op Windows Server Core, omdat NanoServer- en Linux-installatiekopieën alleen ondersteuning bieden voor .NET Core.

Dockerfile.debug:

FROM microsoft/dotnet:1.1.2-sdk
ENV NUGET_XMLDOC_MODE skip
WORKDIR /vsdbg
RUN apt-get update \
    && apt-get install -y --no-install-recommends \
        unzip \
    && rm -rf /var/lib/apt/lists/* \
    && curl -sSL https://aka.ms/getvsdbgsh | bash /dev/stdin -v latest -l /vsdbg
WORKDIR /app
ENTRYPOINT ["tail", "-f", "/dev/null"]

Dit Dockerfile downloadt en installeert in feite het VSdbg-foutopsporingsprogramma en start een lege container, waardoor deze voor altijd actief blijft, zodat we tijdens het opsporen van foutopsporing niet hoeven af te scheuren/omhoog te gaan.

Voor productie is de installatiekopieën nu kleiner omdat deze alleen de .NET Core-runtime en niet de hele SDK bevat, en het dockerfile een beetje eenvoudiger is:

Dockerfile:

FROM microsoft/dotnet:1.1.2-runtime
WORKDIR /app
ENTRYPOINT ["dotnet", "OrleansSilo.dll"]
COPY . /app

Het docker-compose-bestand

Het docker-compose.yml bestand definieert in wezen (binnen een project) een set services en de bijbehorende afhankelijkheden op serviceniveau. Elke service bevat een of meer exemplaren van een bepaalde container, die is gebaseerd op de installatiekopieën die u hebt geselecteerd in uw Dockerfile. Meer informatie over de docker-compose documentatie over docker-compose vindt u hier.

Voor een Orleans implementatie is een veelvoorkomende use-case een docker-compose.yml toepassing die twee services bevat. Een voor Orleans Silo en de andere voor Orleans Client. De Klant zou afhankelijk zijn van de Silo en dat betekent dat deze pas zal beginnen nadat de Silo-service is opgestart. Een ander geval is het toevoegen van een opslag-/databaseservice/container, zoals bijvoorbeeld SQL Server, die eerst moet beginnen voor de client en de silo, dus beide services moeten een afhankelijkheid nemen.

Notitie

Voordat u verder leest, moet u er rekening mee houden dat inspringing van belang is in docker-compose bestanden. Let er dus op als u problemen ondervindt.

Hier volgt een beschrijving van onze services voor dit artikel:

docker-compose.override.yml (foutopsporing):

version: '3.1'

services:
  orleans-client:
    image: orleans-client:debug
    build:
      context: ./src/OrleansClient/bin/PublishOutput/
      dockerfile: Dockerfile.Debug
    volumes:
      - ./src/OrleansClient/bin/PublishOutput/:/app
      - ~/.nuget/packages:/root/.nuget/packages:ro
    depends_on:
      - orleans-silo
  orleans-silo:
    image: orleans-silo:debug
    build:
      context: ./src/OrleansSilo/bin/PublishOutput/
      dockerfile: Dockerfile.Debug
    volumes:
      - ./src/OrleansSilo/bin/PublishOutput/:/app
      - ~/.nuget/packages:/root/.nuget/packages:ro

docker-compose.yml (productie):

version: '3.1'

services:
  orleans-client:
    image: orleans-client
    depends_on:
      - orleans-silo
  orleans-silo:
    image: orleans-silo

In productie wijzen we de lokale map niet toe en hebben we geen van beide de build: actie. De reden hiervoor is dat de installatiekopieën in productie moeten worden gebouwd en naar uw eigen Docker-register moeten worden gepusht.

Plaats alles samen

Nu we alle bewegende onderdelen hebben die nodig zijn om uw Orleans toepassing uit te voeren, gaan we deze samenbrengen zodat we onze Orleans oplossing kunnen uitvoeren in Docker (tot slot!).

Belangrijk

De volgende opdrachten moeten worden uitgevoerd vanuit de oplossingsmap.

Eerst gaan we ervoor zorgen dat we alle NuGet-pakketten vanuit onze oplossing herstellen. Je hoeft het maar één keer te doen. U hoeft dit alleen opnieuw te doen als u een pakketafhankelijkheid van uw project wijzigt.

dotnet restore

Nu gaan we onze oplossing bouwen met behulp van dotnet CLI zoals gewoonlijk en publiceren naar een uitvoermap:

dotnet publish -o ./bin/PublishOutput

Tip

We gebruiken publish hier in plaats van build, om problemen met onze dynamisch geladen assembly's in Orleanste voorkomen. We zijn nog steeds op zoek naar een betere oplossing.

Wanneer de toepassing is gebouwd en gepubliceerd, moet u uw Dockerfile-installatiekopieën bouwen. Deze stap hoeft slechts eenmaal per project te worden uitgevoerd en moet alleen opnieuw worden uitgevoerd als u het Dockerfile, docker-compose wijzigt of om welke reden dan ook het lokale installatiekopieënregister hebt opgeschoond.

docker-compose build

Alle installatiekopieën die in beide Dockerfile worden gebruikt en docker-compose.yml worden opgehaald uit het register en in de cache op uw ontwikkelcomputer opgeslagen. Uw installatiekopieën zijn gebouwd en u bent klaar om uit te voeren.

Laten we het nu uitvoeren!

# docker-compose up -d
Creating network "orleansdocker_default" with the default driver
Creating orleansdocker_orleans-silo_1 ...
Creating orleansdocker_orleans-silo_1 ... done
Creating orleansdocker_orleans-client_1 ...
Creating orleansdocker_orleans-client_1 ... done
#

Als u nu een docker-compose ps, ziet u 2 containers die worden uitgevoerd voor het orleansdocker project:

# docker-compose ps
             Name                     Command        State   Ports
------------------------------------------------------------------
orleansdocker_orleans-client_1   tail -f /dev/null   Up
orleansdocker_orleans-silo_1     tail -f /dev/null   Up

Notitie

Als u windows gebruikt en uw container een Windows-installatiekopieën als basis gebruikt, ziet u in de kolom Opdracht de relatieve PowerShell-opdracht naar een tail op *NIX-systemen, zodat de container op dezelfde manier blijft.

Nu u uw containers hebt ingesteld, hoeft u deze niet steeds te stoppen wanneer u de Orleans toepassing wilt starten. U hoeft alleen uw IDE te integreren om fouten in de toepassing op te sporen in de container die eerder in uw docker-compose.ymlcontainer is toegewezen.

Schalen

Zodra het opstellen van het project wordt uitgevoerd, kunt u de toepassing eenvoudig omhoog of omlaag schalen met behulp van docker-compose scale de opdracht:

# docker-compose scale orleans-silo=15
Starting orleansdocker_orleans-silo_1 ... done
Creating orleansdocker_orleans-silo_2 ...
Creating orleansdocker_orleans-silo_3 ...
Creating orleansdocker_orleans-silo_4 ...
Creating orleansdocker_orleans-silo_5 ...
Creating orleansdocker_orleans-silo_6 ...
Creating orleansdocker_orleans-silo_7 ...
Creating orleansdocker_orleans-silo_8 ...
Creating orleansdocker_orleans-silo_9 ...
Creating orleansdocker_orleans-silo_10 ...
Creating orleansdocker_orleans-silo_11 ...
Creating orleansdocker_orleans-silo_12 ...
Creating orleansdocker_orleans-silo_13 ...
Creating orleansdocker_orleans-silo_14 ...
Creating orleansdocker_orleans-silo_15 ...
Creating orleansdocker_orleans-silo_6
Creating orleansdocker_orleans-silo_5
Creating orleansdocker_orleans-silo_3
Creating orleansdocker_orleans-silo_2
Creating orleansdocker_orleans-silo_4
Creating orleansdocker_orleans-silo_9
Creating orleansdocker_orleans-silo_7
Creating orleansdocker_orleans-silo_8
Creating orleansdocker_orleans-silo_10
Creating orleansdocker_orleans-silo_11
Creating orleansdocker_orleans-silo_15
Creating orleansdocker_orleans-silo_12
Creating orleansdocker_orleans-silo_14
Creating orleansdocker_orleans-silo_13

Na enkele seconden ziet u dat de services zijn geschaald naar het specifieke aantal exemplaren dat u hebt aangevraagd.

# docker-compose ps
             Name                     Command        State   Ports
------------------------------------------------------------------
orleansdocker_orleans-client_1   tail -f /dev/null   Up
orleansdocker_orleans-silo_1     tail -f /dev/null   Up
orleansdocker_orleans-silo_10    tail -f /dev/null   Up
orleansdocker_orleans-silo_11    tail -f /dev/null   Up
orleansdocker_orleans-silo_12    tail -f /dev/null   Up
orleansdocker_orleans-silo_13    tail -f /dev/null   Up
orleansdocker_orleans-silo_14    tail -f /dev/null   Up
orleansdocker_orleans-silo_15    tail -f /dev/null   Up
orleansdocker_orleans-silo_2     tail -f /dev/null   Up
orleansdocker_orleans-silo_3     tail -f /dev/null   Up
orleansdocker_orleans-silo_4     tail -f /dev/null   Up
orleansdocker_orleans-silo_5     tail -f /dev/null   Up
orleansdocker_orleans-silo_6     tail -f /dev/null   Up
orleansdocker_orleans-silo_7     tail -f /dev/null   Up
orleansdocker_orleans-silo_8     tail -f /dev/null   Up
orleansdocker_orleans-silo_9     tail -f /dev/null   Up

Belangrijk

In Command de kolom in deze voorbeelden wordt de tail opdracht weergegeven, alleen omdat we de container voor foutopsporingsprogramma gebruiken. Als we in productie waren, zou dit bijvoorbeeld worden weergegeven dotnet OrleansSilo.dll .

Docker swarm

Docker clustering stack heet Swarm, voor meer informatie, Docker Swarm.

Als u dit artikel in een Swarm cluster wilt uitvoeren, hebt u geen extra werk. Wanneer u in een Swarm knooppunt wordt uitgevoerddocker-compose up -d, worden containers gepland op basis van de geconfigureerde regels. Hetzelfde geldt voor andere op Swarm gebaseerde services, zoals Azure ACS (in Swarm-modus) en AWS ECS Container Service. U hoeft alleen maar uw Swarm cluster te implementeren voordat u uw dockerizedOrleans toepassing implementeert.

Notitie

Als u een Docker-engine gebruikt met de Swarm-modus die al ondersteuning heeft voor stack, deployen compose v3, is docker stack deploy -c docker-compose.yml <name>een betere aanpak om uw oplossing te implementeren. Houd er rekening mee dat het v3 compose-bestand vereist om uw Docker-engine te ondersteunen en het merendeel van de gehoste services zoals Azure en AWS gebruikt nog steeds v2 en oudere engines.

Google Kubernetes (K8s)

Als u Van plan bent Om Kubernetes te hostenOrleans, is er een door de community onderhouden clusteringprovider beschikbaar op OrleansContrib\Orleans. Clustering.Kubernetes. Daar vindt u documentatie en voorbeelden over het naadloos hosten Orleans in Kubernetes met behulp van de provider.

Fouten opsporen Orleans in containers

Nu u weet hoe u een volledig nieuwe container kunt uitvoeren Orleans , is het handig om gebruik te maken van een van de belangrijkste principes in Docker. Containers zijn onveranderbaar. En ze moeten (bijna) dezelfde installatiekopieën, afhankelijkheden en runtime hebben in ontwikkeling als in productie. Dit zorgt voor de goede oude instructie "Het werkt op mijn computer!" gebeurt nooit meer. Om dat mogelijk te maken, moet u een manier hebben om te ontwikkelen in de container en dat omvat het hebben van een foutopsporingsprogramma dat is gekoppeld aan uw toepassing in de container.

Er zijn meerdere manieren om dat te bereiken met behulp van meerdere hulpprogramma's. Na het evalueren van verschillende, tegen de tijd dat ik dit artikel schreef, heb ik uiteindelijk een gekozen die er eenvoudiger uitziet en minder intrusief is in de toepassing.

Zoals eerder in dit artikel is vermeld, gebruiken VSCode we het voorbeeld om het voorbeeld te ontwikkelen, dus hier volgt hoe u het foutopsporingsprogramma kunt koppelen aan uw Orleans toepassing in de container.

Wijzig eerst twee bestanden in uw .vscode map in uw oplossing:

tasks.json:

{
    "version": "0.1.0",
    "command": "dotnet",
    "isShellCommand": true,
    "args": [],
    "tasks": [
        {
            "taskName": "publish",
            "args": [
                "${workspaceRoot}/Orleans-Docker.sln", "-c", "Debug", "-o", "./bin/PublishOutput"
            ],
            "isBuildCommand": true,
            "problemMatcher": "$msCompile"
        }
    ]
}

Dit bestand geeft in wezen aan VSCode dat wanneer u het project bouwt, de publish opdracht wordt uitgevoerd zoals we eerder handmatig hebben gedaan.

launch.json:

{
   "version": "0.2.0",
   "configurations": [
        {
            "name": "Silo",
            "type": "coreclr",
            "request": "launch",
            "cwd": "/app",
            "program": "/app/OrleansSilo.dll",
            "sourceFileMap": {
                "/app": "${workspaceRoot}/src/OrleansSilo"
            },
            "pipeTransport": {
                "debuggerPath": "/vsdbg/vsdbg",
                "pipeProgram": "/bin/bash",
                "pipeCwd": "${workspaceRoot}",
                "pipeArgs": [
                    "-c",
                    "docker exec -i orleansdocker_orleans-silo_1 /vsdbg/vsdbg --interpreter=vscode"
                ]
            }
        },
        {
            "name": "Client",
            "type": "coreclr",
            "request": "launch",
            "cwd": "/app",
            "program": "/app/OrleansClient.dll",
            "sourceFileMap": {
                "/app": "${workspaceRoot}/src/OrleansClient"
            },
            "pipeTransport": {
                "debuggerPath": "/vsdbg/vsdbg",
                "pipeProgram": "/bin/bash",
                "pipeCwd": "${workspaceRoot}",
                "pipeArgs": [
                    "-c",
                    "docker exec -i orleansdocker_orleans-client_1 /vsdbg/vsdbg --interpreter=vscode"
                ]
            }
        }
    ]
}

U kunt nu gewoon de oplossing VSCode bouwen van (die zal publiceren) en zowel de Silo als de Client starten. Er wordt een docker exec opdracht naar het actieve service-exemplaar/de container docker-compose verzonden om het foutopsporingsprogramma naar de toepassing te starten en dat is het. U hebt het foutopsporingsprogramma gekoppeld aan de container en gebruikt het alsof het een lokaal uitgevoerde Orleans toepassing was. Het verschil is nu dat deze zich in de container bevindt. Zodra u klaar bent, kunt u de container gewoon publiceren naar uw register en deze in productie halen op uw Docker-hosts.