Teilen über


Erstellen des Windows-Diensts mithilfe von BackgroundService

.NET Framework-Entwickler sind wahrscheinlich mit Windows Service-Apps vertraut. Vor .NET Core und .NET 5+ können Entwickler, die sich auf .NET Framework verlassen haben, Windows-Dienste erstellen, um Hintergrundaufgaben auszuführen oder lange ausgeführte Prozesse auszuführen. Diese Funktionalität ist weiterhin verfügbar, und Sie können Workerdienste erstellen, die als Windows-Dienst ausgeführt werden.

In diesem Tutorial lernen Sie, wie Sie:

  • Veröffentlichen Sie eine .NET-Worker-App als ausführbare Einzeldatei.
  • Erstellen Sie einen Windows-Dienst.
  • Erstellen Sie die BackgroundService App als Windows-Dienst.
  • Starten und beenden Sie den Windows-Dienst.
  • Ereignisprotokolle anzeigen.
  • Löschen Sie den Windows-Dienst.

Tipp

Der Quellcode "Workers in .NET" ist im Beispielbrowser zum Herunterladen verfügbar. Weitere Informationen finden Sie unter Durchsuchen von Codebeispielen: Worker in .NET.

Wichtig

Bei der Installation des .NET SDK werden auch Microsoft.NET.Sdk.Worker und die Workervorlage installiert. Mit anderen Worten, nach der Installation des .NET SDK könnten Sie einen neuen Worker mithilfe des Befehls "dotnet new worker " erstellen. Wenn Sie Visual Studio verwenden, wird die Vorlage ausgeblendet, bis die optionale ASP.NET- und Webentwicklungsworkload installiert ist.

Voraussetzungen

Erstellen eines neuen Projekts

Um ein neues Worker Service-Projekt mit Visual Studio zu erstellen, wählen Sie „Datei“>„Neu“>„Projekt…“ aus. Im Dialogfeld „Neues Projekt erstellen“ suchen Sie nach „Worker Service“ und wählen die „Worker Service“-Vorlage aus. Wenn Sie lieber die .NET CLI verwenden möchten, öffnen Sie Ihr bevorzugtes Terminal in einem Arbeitsverzeichnis. Führen Sie den Befehl dotnet new aus, und ersetzen Sie <Project.Name> durch den gewünschten Projektnamen.

dotnet new worker --name <Project.Name>

Weitere Informationen zum .NET-CLI-Befehl für ein neues Workerdienstprojekt finden Sie unter dotnet new worker.

Tipp

Wenn Sie Visual Studio Code verwenden, können Sie .NET CLI-Befehle über das integrierte Terminal ausführen. Weitere Informationen finden Sie unter Visual Studio Code: Integrated Terminal.

NuGet-Paket installieren

Um mit nativen Windows-Diensten aus .NET-Implementierungen interagieren zu können, müssen Sie das Microsoft.Extensions.Hosting.WindowsServices installieren.

Um dies aus Visual Studio zu installieren, verwenden Sie das Dialogfeld "NuGet-Pakete verwalten ". Suchen Sie nach "Microsoft.Extensions.Hosting.WindowsServices", und installieren Sie sie. Wenn Sie lieber die .NET CLI verwenden möchten, führen Sie den folgenden Befehl aus. (Wenn Sie eine SDK-Version von .NET 9 oder einer früheren Version verwenden, verwenden Sie stattdessen das dotnet add package Formular.)

dotnet package add Microsoft.Extensions.Hosting.WindowsServices

Weitere Informationen finden Sie unter dotnet package add.

Nach dem erfolgreichen Hinzufügen der Pakete sollte die Projektdatei nun die folgenden Paketverweise enthalten:

<ItemGroup>
  <PackageReference Include="Microsoft.Extensions.Hosting" Version="9.0.6" />
  <PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="9.0.6" />
</ItemGroup>

Aktualisieren der Projektdatei

Dieses Workerprojekt verwendet die C#-Verweistypen, die NULL-Werte zulassen. Um sie für das gesamte Projekt zu aktivieren, aktualisieren Sie die Projektdatei entsprechend:

<Project Sdk="Microsoft.NET.Sdk.Worker">

  <PropertyGroup>
    <TargetFramework>net8.0-windows</TargetFramework>
    <Nullable>enable</Nullable>
    <ImplicitUsings>true</ImplicitUsings>
    <RootNamespace>App.WindowsService</RootNamespace>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.Extensions.Hosting" Version="9.0.6" />
    <PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="9.0.6" />
  </ItemGroup>
</Project>

Die vorherigen Projektdateiänderungen fügen den <Nullable>enable<Nullable> Knoten hinzu. Weitere Informationen finden Sie unter Festlegen des nullfähigen Kontexts.

Erstellen des Diensts

Fügen Sie dem Projekt eine neue Klasse mit dem Namen JokeService.cs hinzu, und ersetzen Sie den Inhalt durch den folgenden C#-Code:

namespace App.WindowsService;

public sealed class JokeService
{
    public string GetJoke()
    {
        Joke joke = _jokes.ElementAt(
            Random.Shared.Next(_jokes.Count));

        return $"{joke.Setup}{Environment.NewLine}{joke.Punchline}";
    }

    // Programming jokes borrowed from:
    // https://github.com/eklavyadev/karljoke/blob/main/source/jokes.json
    private readonly HashSet<Joke> _jokes = new()
    {
        new Joke("What's the best thing about a Boolean?", "Even if you're wrong, you're only off by a bit."),
        new Joke("What's the object-oriented way to become wealthy?", "Inheritance"),
        new Joke("Why did the programmer quit their job?", "Because they didn't get arrays."),
        new Joke("Why do programmers always mix up Halloween and Christmas?", "Because Oct 31 == Dec 25"),
        new Joke("How many programmers does it take to change a lightbulb?", "None that's a hardware problem"),
        new Joke("If you put a million monkeys at a million keyboards, one of them will eventually write a Java program", "the rest of them will write Perl"),
        new Joke("['hip', 'hip']", "(hip hip array)"),
        new Joke("To understand what recursion is...", "You must first understand what recursion is"),
        new Joke("There are 10 types of people in this world...", "Those who understand binary and those who don't"),
        new Joke("Which song would an exception sing?", "Can't catch me - Avicii"),
        new Joke("Why do Java programmers wear glasses?", "Because they don't C#"),
        new Joke("How do you check if a webpage is HTML5?", "Try it out on Internet Explorer"),
        new Joke("A user interface is like a joke.", "If you have to explain it then it is not that good."),
        new Joke("I was gonna tell you a joke about UDP...", "...but you might not get it."),
        new Joke("The punchline often arrives before the set-up.", "Do you know the problem with UDP jokes?"),
        new Joke("Why do C# and Java developers keep breaking their keyboards?", "Because they use a strongly typed language."),
        new Joke("Knock-knock.", "A race condition. Who is there?"),
        new Joke("What's the best part about TCP jokes?", "I get to keep telling them until you get them."),
        new Joke("A programmer puts two glasses on their bedside table before going to sleep.", "A full one, in case they gets thirsty, and an empty one, in case they don’t."),
        new Joke("There are 10 kinds of people in this world.", "Those who understand binary, those who don't, and those who weren't expecting a base 3 joke."),
        new Joke("What did the router say to the doctor?", "It hurts when IP."),
        new Joke("An IPv6 packet is walking out of the house.", "He goes nowhere."),
        new Joke("3 SQL statements walk into a NoSQL bar. Soon, they walk out", "They couldn't find a table.")
    };
}

readonly record struct Joke(string Setup, string Punchline);

Der vorangehende Joke-Dienstquellcode macht eine einzelne Funktionalität verfügbar, die GetJoke Methode. Dies ist eine string-Rückgabemethode, die einen zufälligen Programmierscherz darstellt. Das klassenweite Feld _jokes wird verwendet, um die Liste der Witze zu speichern. Ein zufälliger Witz wird aus der Liste ausgewählt und zurückgegeben.

Neuschreiben der Worker Klasse

Ersetzen Sie die vorhandene Worker Aus der Vorlage durch den folgenden C#-Code, und benennen Sie die Datei in WindowsBackgroundService.cs um:

namespace App.WindowsService;

public sealed class WindowsBackgroundService(
    JokeService jokeService,
    ILogger<WindowsBackgroundService> logger) : BackgroundService
{
    protected override async Task ExecuteAsync(CancellationToken stoppingToken)
    {
        try
        {
            while (!stoppingToken.IsCancellationRequested)
            {
                string joke = jokeService.GetJoke();
                logger.LogWarning("{Joke}", joke);

                await Task.Delay(TimeSpan.FromMinutes(1), stoppingToken);
            }
        }
        catch (OperationCanceledException)
        {
            // When the stopping token is canceled, for example, a call made from services.msc,
            // we shouldn't exit with a non-zero exit code. In other words, this is expected...
        }
        catch (Exception ex)
        {
            logger.LogError(ex, "{Message}", ex.Message);

            // Terminates this process and returns an exit code to the operating system.
            // This is required to avoid the 'BackgroundServiceExceptionBehavior', which
            // performs one of two scenarios:
            // 1. When set to "Ignore": will do nothing at all, errors cause zombie services.
            // 2. When set to "StopHost": will cleanly stop the host, and log errors.
            //
            // In order for the Windows Service Management system to leverage configured
            // recovery options, we need to terminate the process with a non-zero exit code.
            Environment.Exit(1);
        }
    }
}

Im vorangehenden Code wird JokeService zusammen mit einem ILogger eingefügt. Beide werden der Klasse als Felder zur Verfügung gestellt. In der ExecuteAsync Methode fordert der Witzdienst einen Witz an und schreibt ihn in den Logger. In diesem Fall wird die Protokollierung vom Windows-Ereignisprotokoll implementiert: Microsoft.Extensions.Logging.EventLog.EventLogLoggerProvider. Protokolle werden in die Ereignisanzeige geschrieben und können dort eingesehen werden.

Hinweis

Standardmäßig lautet der Schweregrad des Warning . Dies kann konfiguriert werden, aber zu Demonstrationszwecken protokolliert der WindowsBackgroundService mit der LogWarning-Erweiterungsmethode. Fügen Sie einen Eintrag in EventLog hinzu, um gezielt auf die -Ebene abzuzielen, oder geben Sie einen EventLogSettings.Filter-Wert an.

{
  "Logging": {
    "LogLevel": {
      "Default": "Warning"
    },
    "EventLog": {
      "SourceName": "The Joke Service",
      "LogName": "Application",
      "LogLevel": {
        "Microsoft": "Information",
        "Microsoft.Hosting.Lifetime": "Information"
      }
    }
  }
}

Weitere Informationen zum Konfigurieren von Protokollierungsebenen finden Sie unter Protokollierungsanbieter in .NET: Konfigurieren des Windows EventLog.

Neuschreiben der Program Klasse

Ersetzen Sie die Vorlage Program.cs Dateiinhalte durch den folgenden C#-Code:

using App.WindowsService;
using Microsoft.Extensions.Logging.Configuration;
using Microsoft.Extensions.Logging.EventLog;

HostApplicationBuilder builder = Host.CreateApplicationBuilder(args);
builder.Services.AddWindowsService(options =>
{
    options.ServiceName = ".NET Joke Service";
});

LoggerProviderOptions.RegisterProviderOptions<
    EventLogSettings, EventLogLoggerProvider>(builder.Services);

builder.Services.AddSingleton<JokeService>();
builder.Services.AddHostedService<WindowsBackgroundService>();

IHost host = builder.Build();
host.Run();

Die AddWindowsService Erweiterungsmethode konfiguriert die App so, dass sie als Windows-Dienst funktioniert. Der Dienstname wird auf ".NET Joke Service" festgelegt. Der gehostete Dienst ist für die Abhängigkeitsinjektion registriert.

Weitere Informationen zum Registrieren von Diensten finden Sie unter Dependency Injection in .NET.

Veröffentlichen der App

Um die .NET Worker Service-App als Windows-Dienst zu erstellen, empfiehlt es sich, die App als einzelne ausführbare Datei zu veröffentlichen. Es ist weniger fehleranfällig, eine eigenständige ausführbare Datei zu haben, da keine abhängigen Dateien im Dateisystem vorhanden sind. Sie können jedoch eine andere Veröffentlichungsmodalität auswählen, die vollkommen akzeptabel ist, solange Sie eine *.exe Datei erstellen, die vom Windows Service Control Manager angezielt werden kann.

Wichtig

Ein alternativer Veröffentlichungsansatz besteht darin, die *.dll (anstelle eines *.exe) zu erstellen. Wenn Sie die veröffentlichte App mit dem Windows Service Control Manager installieren, delegieren Sie an die .NET CLI und übergeben die DLL. Weitere Informationen finden Sie unter .NET CLI: dotnet command.

sc.exe create ".NET Joke Service" binpath= "C:\Path\To\dotnet.exe C:\Path\To\App.WindowsService.dll"
<Project Sdk="Microsoft.NET.Sdk.Worker">

  <PropertyGroup>
    <TargetFramework>net8.0-windows</TargetFramework>
    <Nullable>enable</Nullable>
    <ImplicitUsings>true</ImplicitUsings>
    <RootNamespace>App.WindowsService</RootNamespace>
    <OutputType>exe</OutputType>
    <PublishSingleFile Condition="'$(Configuration)' == 'Release'">true</PublishSingleFile>
    <RuntimeIdentifier>win-x64</RuntimeIdentifier>
    <PlatformTarget>x64</PlatformTarget>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.Extensions.Hosting" Version="9.0.6" />
    <PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="9.0.6" />
  </ItemGroup>
</Project>

Die oben hervorgehobenen Zeilen der Projektdatei definieren das folgende Verhalten:

  • <OutputType>exe</OutputType>: Erstellt eine Konsolenanwendung.
  • <PublishSingleFile Condition="'$(Configuration)' == 'Release'">true</PublishSingleFile>: Aktiviert die Einzeldateiveröffentlichung.
  • <RuntimeIdentifier>win-x64</RuntimeIdentifier>: Gibt die RID von win-x64 an.
  • <PlatformTarget>x64</PlatformTarget>: Geben Sie die Zielplattform-CPU von 64-Bit an.

Um die App aus Visual Studio zu veröffentlichen, können Sie ein Veröffentlichungsprofil erstellen, das beibehalten wird. Das Veröffentlichungsprofil ist XML-basiert und verfügt über die Dateierweiterung PUBXML . Visual Studio verwendet dieses Profil, um die App implizit zu veröffentlichen. Wenn Sie .NET CLI verwenden, müssen Sie jedoch explizit das zu verwendende Veröffentlichungsprofil angeben.

Klicken Sie im Projektmappen-Explorer mit der rechten Maustaste auf das Projekt, und wählen Sie "Veröffentlichen" aus. Wählen Sie dann "Hinzufügen eines Veröffentlichungsprofils " aus, um ein Profil zu erstellen. Wählen Sie im Dialogfeld " Veröffentlichen " "Ordner " als Ziel aus.

Das Dialogfeld

Behalten Sie den standardmäßigen Speicherort bei, und wählen Sie dann Fertig stellen aus. Nachdem das Profil erstellt wurde, wählen Sie "Alle Einstellungen anzeigen" aus, und überprüfen Sie Ihre Profileinstellungen.

Die Visual Studio-Profileinstellungen

Stellen Sie sicher, dass die folgenden Einstellungen angegeben sind:

  • Bereitstellungsmodus: Eigenständig
  • Erstellen einer einzelnen Datei: überprüft
  • ReadyToRun-Kompilierung aktivieren: aktiviert
  • Nicht verwendete Assemblys entfernen (in der Vorschau): nicht ausgewählt

Wählen Sie schließlich "Veröffentlichen" aus. Die App wird kompiliert, und die resultierende .exe Datei wird im Ausgabeverzeichnis /publish veröffentlicht.

Alternativ können Sie die .NET CLI verwenden, um die App zu veröffentlichen:

dotnet publish --output "C:\custom\publish\directory"

Weitere Informationen finden Sie unter dotnet publish.

Wichtig

Wenn Sie mit .NET 6 versuchen, die App mit der <PublishSingleFile>true</PublishSingleFile> Einstellung zu debuggen, können Sie die App nicht debuggen. Weitere Informationen finden Sie unter Nicht möglich, eine Verbindung zu CoreCLR herzustellen, wenn eine .NET 6 'PublishSingleFile'-App debuggt wird.

Erstellen des Windows-Diensts

Wenn Sie mit der Verwendung von PowerShell nicht vertraut sind und lieber ein Installationsprogramm für Ihren Dienst erstellen möchten, lesen Sie "Erstellen eines Windows-Dienstinstallationsprogramms". Wenn Sie den Windows-Dienst erstellen möchten, verwenden Sie andernfalls den (sc.exe)-Erstellungsbefehl des systemeigenen Windows-Dienststeuerungs-Managers. Führen Sie PowerShell als Administrator aus.

sc.exe create ".NET Joke Service" binpath= "C:\Path\To\App.WindowsService.exe"

Tipp

Wenn Sie den Inhaltsstamm der Hostkonfiguration ändern müssen, können Sie ihn als Befehlszeilenargument übergeben, wenn Sie folgendes binpathangeben:

sc.exe create "Svc Name" binpath= "C:\Path\To\App.exe --contentRoot C:\Other\Path"

Es wird eine Ausgabemeldung angezeigt:

[SC] CreateService SUCCESS

Weitere Informationen finden Sie unter sc.exe Erstellen.

Konfigurieren des Windows-Diensts

Nachdem der Dienst erstellt wurde, können Sie ihn optional konfigurieren. Wenn Sie mit den Standardeinstellungen des Diensts in Ordnung sind, fahren Sie mit dem Abschnitt " Dienstfunktionalität überprüfen " fort.

Windows-Dienste bieten Wiederherstellungskonfigurationsoptionen. Sie können die aktuelle Konfiguration mit dem sc.exe qfailure "<Service Name>" Befehl (wo <Service Name> befindet sich der Name Ihrer Dienste) abfragen, um die aktuellen Wiederherstellungskonfigurationswerte zu lesen:

sc qfailure ".NET Joke Service"
[SC] QueryServiceConfig2 SUCCESS

SERVICE_NAME: .NET Joke Service
        RESET_PERIOD (in seconds)    : 0
        REBOOT_MESSAGE               :
        COMMAND_LINE                 :

Der Befehl gibt die Wiederherstellungskonfiguration aus, was die Standardwerte ist, da sie noch nicht konfiguriert wurden.

Das Dialogfeld

Verwenden Sie zum Konfigurieren der Wiederherstellung sc.exe failure "<Service Name>", wobei <Service Name> der Name Ihres Diensts ist:

sc.exe failure ".NET Joke Service" reset= 0 actions= restart/60000/restart/60000/run/1000
[SC] ChangeServiceConfig2 SUCCESS

Tipp

Um die Wiederherstellungsoptionen zu konfigurieren, muss Ihre Terminalsitzung als Administrator ausgeführt werden.

Nachdem sie erfolgreich konfiguriert wurde, können Sie die Werte erneut mit dem sc.exe qfailure "<Service Name>" Befehl abfragen:

sc qfailure ".NET Joke Service"
[SC] QueryServiceConfig2 SUCCESS

SERVICE_NAME: .NET Joke Service
        RESET_PERIOD (in seconds)    : 0
        REBOOT_MESSAGE               :
        COMMAND_LINE                 :
        FAILURE_ACTIONS              : RESTART -- Delay = 60000 milliseconds.
                                       RESTART -- Delay = 60000 milliseconds.
                                       RUN PROCESS -- Delay = 1000 milliseconds.

Die konfigurierten Neustartwerte werden angezeigt.

Das Windows Dialogfeld mit den Konfigurationseigenschaften für die Dienstwiederherstellung mit aktiviertem Neustart.

Dienstwiederherstellungsoptionen und .NET-Instanzen BackgroundService

Mit .NET 6 wurden neue Verhalten zur Behandlung von Hosting-Ausnahmen zu .NET hinzugefügt. Die BackgroundServiceExceptionBehavior-Enum wurde dem Microsoft.Extensions.Hosting-Namespace hinzugefügt und gibt an, wie sich der Dienst verhält, wenn eine Ausnahme ausgelöst wird. Die folgende Tabelle enthält die verfügbaren Optionen:

Option BESCHREIBUNG
Ignore In BackgroundServiceausgelöste Ausnahmen werden ignoriert.
StopHost IHost wird beendet, wenn ein Ausnahmefehler ausgelöst wird.

Das Standardverhalten vor .NET 6 ist Ignore, was zu Zombie-Prozessen führte (ein ausgeführter Prozess, der nichts tut). Bei .NET 6 lautet StopHostdas Standardverhalten , das dazu führt, dass der Host beendet wird, wenn eine Ausnahme ausgelöst wird. Dies geschieht jedoch auf saubere Weise, das heißt, der Dienst wird vom Windows-Dienstverwaltungssystem nicht neu gestartet. Um den Neustart des Diensts ordnungsgemäß zuzulassen, können Sie Environment.Exit mit einem Exitcode ungleich null aufrufen. Betrachten Sie den folgenden hervorgehobenen catch Block:

namespace App.WindowsService;

public sealed class WindowsBackgroundService(
    JokeService jokeService,
    ILogger<WindowsBackgroundService> logger) : BackgroundService
{
    protected override async Task ExecuteAsync(CancellationToken stoppingToken)
    {
        try
        {
            while (!stoppingToken.IsCancellationRequested)
            {
                string joke = jokeService.GetJoke();
                logger.LogWarning("{Joke}", joke);

                await Task.Delay(TimeSpan.FromMinutes(1), stoppingToken);
            }
        }
        catch (OperationCanceledException)
        {
            // When the stopping token is canceled, for example, a call made from services.msc,
            // we shouldn't exit with a non-zero exit code. In other words, this is expected...
        }
        catch (Exception ex)
        {
            logger.LogError(ex, "{Message}", ex.Message);

            // Terminates this process and returns an exit code to the operating system.
            // This is required to avoid the 'BackgroundServiceExceptionBehavior', which
            // performs one of two scenarios:
            // 1. When set to "Ignore": will do nothing at all, errors cause zombie services.
            // 2. When set to "StopHost": will cleanly stop the host, and log errors.
            //
            // In order for the Windows Service Management system to leverage configured
            // recovery options, we need to terminate the process with a non-zero exit code.
            Environment.Exit(1);
        }
    }
}

Überprüfen der Dienstfunktionalität

Um die app anzuzeigen, die als Windows-Dienst erstellt wurde, öffnen Sie "Dienste". Wählen Sie die Windows-Taste (oder STRG + ESC) aus, und suchen Sie aus "Dienste". In der Dienst-App sollten Sie in der Lage sein, Ihren Dienst anhand des Namens zu finden.

Wichtig

Standardmäßig können reguläre Benutzer (nicht administratorinterne) Windows-Dienste nicht verwalten. Um zu überprüfen, ob diese App erwartungsgemäß funktioniert, müssen Sie ein Administratorkonto verwenden.

Die Benutzeroberfläche der Dienste.

Um zu überprüfen, ob der Dienst wie erwartet funktioniert, müssen Sie:

  • Starten des Diensts
  • Anzeigen der Protokolle
  • Beenden des Diensts

Wichtig

Um die Anwendung zu debuggen, stellen Sie sicher, dass Sie nicht versuchen, die ausführbare Datei zu debuggen, die aktiv im Windows-Dienstprozess ausgeführt wird.

Programm kann nicht gestartet werden.

Starten des Windows-Diensts

Um den Windows-Dienst zu starten, verwenden Sie den sc.exe start Befehl:

sc.exe start ".NET Joke Service"

Daraufhin wird eine Ausgabe angezeigt, die in etwa wie folgt aussieht:

SERVICE_NAME: .NET Joke Service
    TYPE               : 10  WIN32_OWN_PROCESS
    STATE              : 2  START_PENDING
                            (NOT_STOPPABLE, NOT_PAUSABLE, IGNORES_SHUTDOWN)
    WIN32_EXIT_CODE    : 0  (0x0)
    SERVICE_EXIT_CODE  : 0  (0x0)
    CHECKPOINT         : 0x0
    WAIT_HINT          : 0x7d0
    PID                : 37636
    FLAGS

Der Status des Diensts wechselt von START_PENDING zu Wird ausgeführt.

Protokolle anzeigen

Um Protokolle anzuzeigen, öffnen Sie die Ereignisanzeige. Wählen Sie die Windows-Taste (oder STRG + ESC) aus, und suchen Sie nach "Event Viewer". Wählen Sie den Knoten Ereignisanzeige (lokal)>Windows Logs>Anwendung . Es sollte ein Eintrag auf Warnungsebene mit einer Quelle angezeigt werden, die dem App-Namespace entspricht. Doppelklicken Sie auf den Eintrag, oder klicken Sie mit der rechten Maustaste, und wählen Sie "Ereigniseigenschaften" aus, um die Details anzuzeigen.

Dialogfeld

Nachdem Protokolle im Ereignisprotokoll angezeigt wurden, sollten Sie den Dienst beenden. Es ist so konzipiert, einen zufälligen Witz einmal pro Minute zu protokollieren. Dies ist beabsichtigtes Verhalten, ist aber für Produktionsdienste nicht praktikabel.

Beenden des Windows-Diensts

Um den Windows-Dienst zu beenden, verwenden Sie den sc.exe stop Befehl:

sc.exe stop ".NET Joke Service"

Daraufhin wird eine Ausgabe angezeigt, die in etwa wie folgt aussieht:

SERVICE_NAME: .NET Joke Service
    TYPE               : 10  WIN32_OWN_PROCESS
    STATE              : 3  STOP_PENDING
                            (STOPPABLE, NOT_PAUSABLE, ACCEPTS_SHUTDOWN)
    WIN32_EXIT_CODE    : 0  (0x0)
    SERVICE_EXIT_CODE  : 0  (0x0)
    CHECKPOINT         : 0x0
    WAIT_HINT          : 0x0

Der Status des Diensts geht von STOP_PENDING in Stopped (Beendet) über.

Löschen des Windows-Diensts

Verwenden Sie zum Löschen des Windows-Diensts den Löschbefehl (sc.exe) des systemeigenen Windows-Dienststeuerungs-Managers. Führen Sie PowerShell als Administrator aus.

Wichtig

Wenn sich der Dienst nicht im Status "Beendet " befindet, wird er nicht sofort gelöscht. Stellen Sie sicher, dass der Dienst vor dem Ausgeben des Löschbefehls beendet wird.

sc.exe delete ".NET Joke Service"

Es wird eine Ausgabemeldung angezeigt:

[SC] DeleteService SUCCESS

Weitere Informationen finden Sie unter sc.exe Löschen.

Siehe auch

Weiter