Freigeben über


Automatische Wartung

Plattformen

Clients – Windows 8
Server – Windows Server 2012

Beschreibung

Windows hängt von der Ausführung von Posteingangs- und Drittanbieterwartungsaktivitäten für einen Großteil seines Mehrwerts ab, einschließlich Windows Update und automatischer Datenträgerdefragmentierung sowie Antivirenupdates und Scans. Darüber hinaus verwenden Unternehmen häufig Wartungsaktivitäten wie netzwerkzugriffsschutz (Network Access Protection, NAP), um Sicherheitsstandards auf allen Unternehmensarbeitsstationen zu erzwingen.

Wartungsaktivitäten in Windows sind so konzipiert, dass sie im Hintergrund mit eingeschränkter Benutzerinteraktion und minimalen Auswirkungen auf die Leistung und Energieeffizienz ausgeführt werden. In Windows 7 und früheren Versionen wirkt sich die Leistung und Energieeffizienz jedoch weiterhin aufgrund des nicht deterministischen und weit unterschiedlichen Zeitplans der verschiedenen Wartungsaktivitäten in Windows aus. Die Reaktionsfähigkeit der Benutzer wird reduziert, wenn Wartungsaktivitäten ausgeführt werden, während Benutzer aktiv den Computer verwenden. Apps bitten den Benutzer auch häufig, seine Software zu aktualisieren und Hintergrundwartung auszuführen, und leiten Benutzer zu mehreren Oberflächen, einschließlich Info-Center, Systemsteuerung, Windows Update, Aufgabenplanung MMC-Snap-In und Steuerelemente von Drittanbietern.

Das Ziel der automatischen Wartung besteht darin, alle Hintergrundwartungsaktivitäten in Windows zu kombinieren und Drittanbieterentwicklern zu helfen, ihre Wartungsaktivitäten zu Windows hinzuzufügen, ohne die Leistung und Energieeffizienz negativ zu beeinträchtigen. Darüber hinaus ermöglicht die automatische Wartung Benutzern sowie Unternehmen die Kontrolle über die Planung und Konfiguration von Wartungsaktivitäten.

Wichtige Probleme

Die automatische Wartung wurde entwickelt, um diese Probleme mit Wartungsaktivitäten in Windows zu beheben:

  • Terminplanung
  • Ressourcenauslastungskonflikte
  • Energieeffizienz
  • Transparenz für den Benutzer

Funktionalität

Die automatische Wartung erleichtert die Leerlaufeffizienz und ermöglicht es allen Aktivitäten, rechtzeitig und priorisiert zu laufen. Außerdem können Entwickler von Drittanbietern ihre Wartungsaktivitäten einheitlicher Sichtbarkeit und Kontrolle über Wartungsaktivitäten ermöglichen und ihre Wartungsaktivitäten zu Windows hinzufügen, ohne dass sich dies negativ auf die Leistung und Energieeffizienz auswirkt. Dazu wird ein vollständig automatischer Modus, vom Benutzer initiierter Modus, automatisches Beenden, Stichtage und Benachrichtigungen sowie die Unternehmenssteuerung bereitgestellt. Diese werden jeweils unten beschrieben.

vollständig automatischer Modus

Dieser Standardmodus ermöglicht eine intelligente Planung während der PC-Leerlaufzeit und zu geplanten Zeiten – die Ausführung und automatische Unterbrechung von Wartungsaktivitäten ohne Benutzereingriff. Der Benutzer kann einen wöchentlichen oder täglichen Zeitplan festlegen. Alle Wartungsaktivitäten sind nicht interaktiv und werden automatisch ausgeführt.

Der Computer wird automatisch aus dem Ruhezustand fortgesetzt, wenn das System wahrscheinlich nicht verwendet wird, wobei die Energieverwaltungsrichtlinie beachtet wird, die im Fall von Laptops standardmäßig nur aktiviert wird, wenn es sich um einen Netzstrom handelt. Vollständige Systemressourcen mit hoher Leistung werden verwendet, um die Wartungsaktivität so schnell wie möglich abzuschließen. Wenn das System aus dem Ruhezustand für die automatische Wartung fortgesetzt wurde, wird es aufgefordert, in den Ruhezustand zurückzukehren.

Alle erforderlichen Benutzerinteraktionen im Zusammenhang mit Aktivitäten wie der Konfiguration werden außerhalb der automatischen Wartungsausführung ausgeführt.

vom Benutzer initiierten Modus

Wenn Benutzer sich auf die Reise vorbereiten müssen, erwarten Sie, dass sie längere Zeit auf akkubetrieben sind oder die Leistung und Reaktionsfähigkeit optimieren möchten, haben sie die Möglichkeit, die automatische Wartung bei Bedarf zu initiieren. Benutzer können Attribute für die automatische Wartung konfigurieren, einschließlich des Zeitplans für die automatische Ausführung. Sie können den aktuellen Status der automatischen Wartung anzeigen und bei Bedarf die automatische Wartung beenden.

automatische Stopp-

Die automatische Wartung beendet die derzeit ausgeführten Wartungsaktivitäten automatisch, wenn der Benutzer mit der Interaktion mit dem Computer beginnt. Wartungsaktivitäten werden fortgesetzt, wenn das System zum Leerlaufstatus zurückkehrt.

Anmerkung

Alle Aktivitäten in der automatischen Wartung müssen das Beenden in 2 Sekunden oder weniger unterstützen. Der Benutzer sollte benachrichtigt werden, dass die Aktivität beendet wurde.

 

Stichtage und Benachrichtigungen

Kritische Wartungsaktivitäten müssen innerhalb eines vordefinierten Zeitfensters ausgeführt werden. Wenn kritische Vorgänge nicht innerhalb ihres festgelegten Zeitraums ausgeführt werden konnten, beginnt die automatische Wartung automatisch bei der nächsten verfügbaren System-Leerlaufchance. Wenn der Vorgangsstatus jedoch hinter dem Stichtag bleibt, benachrichtigt die automatische Wartung den Benutzer über die Aktivität und bietet eine Option für eine manuelle Ausführung der automatischen Wartung. Alle für die Wartung geplanten Vorgänge werden ausgeführt, obwohl die meisten ausgehungerten Vorgänge Vorrang haben. Diese Aktivität kann sich auf die Reaktionsfähigkeit und Leistung des Systems auswirken; Daher benachrichtigt die automatische Wartung den Benutzer darüber, dass kritische Wartungsaktivitäten ausgeführt werden.

enterprise control

IT-Experten für Unternehmen sollten bestimmen können, wann die automatische Wartung auf ihren Windows-Systemen ausgeführt wird, diesen Zeitplan über standardisierte Verwaltungsschnittstellen erzwingen und Ereignisdaten über den Status von Ausführungsversuchen für die automatische Wartung abrufen. Darüber hinaus sollten IT-Experten in der Lage sein, bestimmte automatische Wartungsaktivitäten remote über Standardverwaltungsschnittstellen aufzurufen. Jedes Mal, wenn die automatische Wartung ausgeführt wird, wird die Statusberichterstattung einschließlich Benachrichtigungen angezeigt, wenn die automatische Wartung nicht ausgeführt werden konnte, da der Benutzer die Aktivität manuell angehalten hat. IT-Experten sollten das Verschieben von Anmeldeskripts in die automatische Wartung erwägen, um die Anmeldeerfahrung des Benutzers schneller zu gestalten.

Erstellen einer automatischen Wartungsaufgabe

In diesem Abschnitt wird erläutert, wie Entwickler eine Aufgabe mithilfe einer Aufgabendefinition in XML oder C erstellen können. Denken Sie daran, dass Wartungsaktivitäten keine Benutzeroberfläche starten sollten, die eine Benutzerinteraktion erfordert, da die automatische Wartung vollständig unbeaufsichtigt ist und ausgeführt wird, wenn der Benutzer nicht vorhanden ist. Wenn der Benutzer während der automatischen Wartung mit dem Computer interagiert, werden alle vorgänge im Prozess bis zum nächsten Leerlaufzeitraum beendet.

Verwenden von XML-

Der Aufgabenplaner enthält ein integriertes Befehlszeilentool schtasks.exe, das eine Aufgabendefinition im XML-Format importieren kann. Das Schema für die Aufgabendefinition wird unter https://msdn.microsoft.com/library/aa383609(v=VS.85).aspxdokumentiert. Nachfolgend finden Sie ein Beispiel für eine in XML definierte Aufgabe für die automatische Wartung.

<?xml version="1.0" encoding="UTF-16"?>
<Task version="1.4" xmlns="http://schemas.microsoft.com/windows/2004/02/mit/task">
  <RegistrationInfo>
    <Date>2011-07-01T11:34:31</Date>
    <Author>IT Department</Author>
  </RegistrationInfo>
  <Principals>
    <Principal id="Author">
      <RunLevel>LeastPrivilege</RunLevel>
      <GroupId>NT AUTHORITY\SYSTEM</GroupId>
    </Principal>
  </Principals>
  <Settings>
    <MultipleInstancesPolicy>IgnoreNew</MultipleInstancesPolicy>
    <DisallowStartIfOnBatteries>true</DisallowStartIfOnBatteries>
    <StopIfGoingOnBatteries>true</StopIfGoingOnBatteries>
    <AllowHardTerminate>true</AllowHardTerminate>
    <StartWhenAvailable>false</StartWhenAvailable>
    <RunOnlyIfNetworkAvailable>false</RunOnlyIfNetworkAvailable>
    <MaintenanceSettings>
      <Period>P2D</Period>
      <Deadline>P14D</Deadline>
    </MaintenanceSettings>
    <AllowStartOnDemand>true</AllowStartOnDemand>
    <Enabled>true</Enabled>
    <Hidden>false</Hidden>
    <RunOnlyIfIdle>false</RunOnlyIfIdle>
    <DisallowStartOnRemoteAppSession>false</DisallowStartOnRemoteAppSession>
    <UseUnifiedSchedulingEngine>true</UseUnifiedSchedulingEngine>
    <WakeToRun>false</WakeToRun>
    <ExecutionTimeLimit>P3D</ExecutionTimeLimit>
    <Priority>7</Priority>
  </Settings>
  <Actions Context="Author">
    <Exec>
      <Command>cmd</Command>
      <Arguments>/c timeout -t 60</Arguments>
    </Exec>
  </Actions>
</Task> 

Um die Aufgabe auf einem Windows-Computer zu speichern, speichern Sie den obigen XML-Code als Textdatei, und verwenden Sie diese Befehlszeile:

Schtasks.exe /create /tn <task name> /xml <text file name>

Verwenden von C-

Eine Aufgabe für die automatische Wartung kann auch mit C-Code erstellt werden. Nachfolgend finden Sie ein Codebeispiel, das zum Konfigurieren der Einstellungen für die automatische Wartung einer Aufgabe verwendet werden kann:

/********************************************************************
This sample creates a maintenance task to start cmd window during maintenance opportunities with periodicity of 2 days and deadline 0f 14 days.
********************************************************************/

#define _WIN32_DCOM

#include <windows.h>
#include <iostream>
#include <stdio.h>
#include <comdef.h>
#include <wincred.h>
//  Include the task header file.
#include <taskschd.h>
//#pragma comment(lib, "taskschd.lib")
//#pragma comment(lib, "comsupp.lib")

int __cdecl 
MainteanceTask( )
{
    //  ------------------------------------------------------
    //  Initialize COM.
    HRESULT hr;

    //  ------------------------------------------------------
    //  Create a name for the task.
    LPCWSTR wszTaskName = L"MaintenanceTask";

    ITaskService *pService = NULL;
    ITaskFolder *pRootFolder = NULL;
    ITaskDefinition *pTask = NULL;
    ITaskSettings *pSettings = NULL;
    IRegistrationInfo *pRegInfo= NULL;
    IPrincipal *pPrincipal = NULL;
    ITaskSettings3 *pSettings3 = NULL;
    IMaintenanceSettings* pMaintenanceSettings = NULL;
    IActionCollection *pActionCollection = NULL;
    IAction *pAction = NULL;
    IExecAction *pExecAction = NULL;
    IRegisteredTask *pRegisteredTask = NULL;

    wprintf(L"\nCreate Maintenance Task %ws", wszTaskName );

    hr = CoInitializeEx( NULL, COINIT_MULTITHREADED);
    if( FAILED(hr) )
    {
        wprintf(L"\nCoInitializeEx failed: %x", hr );
        return 1;
    }

    //  Set general COM security levels.
    hr = CoInitializeSecurity( NULL,
        -1,
        NULL,
        NULL,
        RPC_C_AUTHN_LEVEL_PKT_PRIVACY,
        RPC_C_IMP_LEVEL_IMPERSONATE,
        NULL,
        0,
        NULL);

    if( FAILED(hr) )
    {
        wprintf(L"\nCoInitializeSecurity failed: %x", hr );
        goto CleanUp;
    }

    //  ------------------------------------------------------
    //  Create an instance of the Task Service. 
    hr = CoCreateInstance( CLSID_TaskScheduler,
                           NULL,
                           CLSCTX_INPROC_SERVER,
                           IID_ITaskService,
                           (void**)&pService );  
    if (FAILED(hr))
    {
        wprintf(L"\nFailed to create an instance of ITaskService: %x", hr);
        goto CleanUp;
    }
        
    //  Connect to the task service.
    hr = pService->Connect(_variant_t(), _variant_t(), _variant_t(), _variant_t());
    if( FAILED(hr) )
    {
        wprintf(L"\nITaskService::Connect failed: %x", hr );
        goto CleanUp;
    }

    //  ------------------------------------------------------
    //  Get the pointer to the root task folder.  This folder will hold the
    //  new task that is registered.
    hr = pService->GetFolder( _bstr_t( L"\\") , &pRootFolder );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot get Root folder pointer: %x", hr );
        goto CleanUp;
    }
    
    //  If the same task exists, remove it.
    ( void ) pRootFolder->DeleteTask( _bstr_t(wszTaskName), 0  );
    
    //  Create the task definition object to create the task.
    hr = pService->NewTask( 0, &pTask );
    if (FAILED(hr))
    {
        wprintf(L"\nFailed to CoCreate an instance of the TaskService class: %x", hr);
        goto CleanUp;
    }
        
    //  ------------------------------------------------------
    //  Get the registration info for setting the identification.
    hr = pTask->get_RegistrationInfo( &pRegInfo );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot get identification pointer: %x", hr );
        goto CleanUp;
    }
    
    hr = pRegInfo->put_Author( _bstr_t(L"Author Name") );    
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot put identification info: %x", hr );
        goto CleanUp;
    }

    // The task needs to grant explicit FRFX to LOCAL SERVICE (A;;FRFX;;;LS)
    hr = pRegInfo->put_SecurityDescriptor( _variant_t(L"D:P(A;;FA;;;BA)(A;;FA;;;SY)(A;;FRFX;;;LS)") );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot put security descriptor: %x", hr );
        goto CleanUp;
    }

    //  ------------------------------------------------------
    //  Create the principal for the task - these credentials
    //  are overwritten with the credentials passed to RegisterTaskDefinition
    hr = pTask->get_Principal( &pPrincipal );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot get principal pointer: %x", hr );
        goto CleanUp;
    }
    
    //  Set up principal logon type to interactive logon
    hr = pPrincipal->put_LogonType( TASK_LOGON_INTERACTIVE_TOKEN );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot put principal info: %x", hr );
        goto CleanUp;
    }  

    //  ------------------------------------------------------
    //  Create the settings for the task
    hr = pTask->get_Settings( &pSettings );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot get settings pointer: %x", hr );
        goto CleanUp;
    }

    hr = pSettings->QueryInterface( __uuidof(ITaskSettings3), (void**) &pSettings3 );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot query ITaskSettings3 interface: %x", hr );
        goto CleanUp;
    }

    hr = pSettings3->put_UseUnifiedSchedulingEngine( VARIANT_TRUE );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot put_UseUnifiedSchedulingEngine: %x", hr );
        goto CleanUp;
    }

    hr = pSettings3->CreateMaintenanceSettings( &pMaintenanceSettings );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot CreateMaintenanceSettings: %x", hr );
        goto CleanUp;
    }

    hr = pMaintenanceSettings->put_Period ( _bstr_t(L"P2D") );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot put_Period: %x", hr );
        goto CleanUp;
    }

    hr = pMaintenanceSettings->put_Deadline ( _bstr_t(L"P14D") );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot put_Period: %x", hr );
        goto CleanUp;
    }

    //  ------------------------------------------------------
    //  Add an action to the task. This task will execute cmd.exe.     
    //  Get the task action collection pointer.
    hr = pTask->get_Actions( &pActionCollection );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot get Task collection pointer: %x", hr );
        goto CleanUp;
    }
    
    //  Create the action, specifying that it is an executable action.
    hr = pActionCollection->Create( TASK_ACTION_EXEC, &pAction );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot create the action: %x", hr );
        goto CleanUp;
    }

    //  QI for the executable task pointer.
    hr = pAction->QueryInterface( IID_IExecAction, (void**) &pExecAction );
    if( FAILED(hr) )
    {
        wprintf(L"\nQueryInterface call failed for IExecAction: %x", hr );
        goto CleanUp;
    }

    //  Set the path of the executable to cmd.exe.
    hr = pExecAction->put_Path( _bstr_t(L"cmd") );
    if( FAILED(hr) )
    {
        wprintf(L"\nCannot put action path: %x", hr );
        goto CleanUp;
    }  
    
    //  ------------------------------------------------------
    //  Save the task in the root folder.
    hr = pRootFolder->RegisterTaskDefinition(
            _bstr_t(wszTaskName),
            pTask,
            TASK_CREATE_OR_UPDATE, 
            _variant_t(), 
            _variant_t(), 
            TASK_LOGON_INTERACTIVE_TOKEN,
            _variant_t(L""),
            &pRegisteredTask);
    if( FAILED(hr) )
    {
        wprintf(L"\nError saving the Task : %x", hr );
        goto CleanUp;
    }
    
    wprintf(L"\nSuccess!\n----------------------------------" );

CleanUp:

    if ( pService != NULL ) pService->Release();
    if ( pRootFolder != NULL ) pRootFolder->Release();
    if ( pTask != NULL ) pTask->Release();
    if ( pSettings != NULL ) pSettings->Release();
    if ( pRegInfo != NULL ) pRegInfo->Release();
    if ( pPrincipal != NULL ) pPrincipal->Release();
    if ( pSettings3 != NULL ) pSettings3->Release();
    if ( pMaintenanceSettings != NULL ) pMaintenanceSettings->Release();
    if ( pActionCollection != NULL ) pActionCollection->Release();
    if ( pAction != NULL ) pAction->Release();
    if ( pExecAction != NULL ) pExecAction->Release();
    if ( pRegisteredTask != NULL ) pRegisteredTask->Release();

    CoUninitialize();
    return SUCCEEDED ( hr ) ? 0 : 1;
}

Überprüfen von Vorgängen

Überprüfen Sie, ob die Aufgabe erfolgreich erstellt wurde und als Teil der Wartung ausgeführt wird.

Überprüfen der Aufgabenerstellung

Verwenden Sie diese Befehlszeile, um die Aufgabendefinition in eine Datei zu exportieren und sicherzustellen, dass die Aufgabendefinition wie erwartet ist:

Schtasks.exe /Query /tn<task name> /xml <text file name>

Überprüfen der Aufgabenausführung

Führen Sie diese Befehlszeile aus, um die Aufgabe zu starten und zu überprüfen, ob die Task Scheduler-Benutzeroberfläche (taskschd.msc) die Aufgabe ausgeführt hat:

Schtasks.exe /Run /tn<task name>

Betriebsmittel