Escribir un recurso de DSC personalizado con MOFWriting a custom DSC resource with MOF

Se aplica a: Windows PowerShell 4.0, Windows PowerShell 5.0Applies To: Windows PowerShell 4.0, Windows PowerShell 5.0

En este artículo se define el esquema de un recurso personalizado de Desired State Configuration (DSC) de Windows PowerShell en un archivo MOF y se implementa el recurso en un archivo de script de Windows PowerShell.In this article, we will define the schema for a Windows PowerShell Desired State Configuration (DSC) custom resource in a MOF file, and implement the resource in a Windows PowerShell script file. Este recurso personalizado es para la creación y el mantenimiento de un sitio web.This custom resource is for creating and maintaining a web site.

Crear el esquema MOFCreating the MOF schema

El esquema define las propiedades del recurso que se pueden configurar mediante un script de configuración DSC.The schema defines the properties of your resource that can be configured by a DSC configuration script.

Estructura de carpetas de un recurso MOFFolder structure for a MOF resource

Para implementar un recurso de DSC personalizado con un esquema MOF, cree la siguiente estructura de carpetas.To implement a DSC custom resource with a MOF schema, create the following folder structure. El esquema MOF se define en el archivo Demo_IISWebsite.schema.mof, y el script de recursos se define en Demo_IISWebsite.psm1.The MOF schema is defined in the file Demo_IISWebsite.schema.mof, and the resource script is defined in Demo_IISWebsite.psm1. Opcionalmente, puede crear un archivo de manifiesto del módulo (psd1).Optionally, you can create a module manifest (psd1) file.

$env:ProgramFiles\WindowsPowerShell\Modules (folder)
    |- MyDscResources (folder)
        |- DSCResources (folder)
            |- Demo_IISWebsite (folder)
                |- Demo_IISWebsite.psd1 (file, optional)
                |- Demo_IISWebsite.psm1 (file, required)
                |- Demo_IISWebsite.schema.mof (file, required)

Nota

Es necesario crear una carpeta denominada DSCResources en la carpeta de nivel superior y que la carpeta de cada recurso debe tener el mismo nombre que el recurso.It is necessary to create a folder named DSCResources under the top-level folder, and that the folder for each resource must have the same name as the resource.

Contenido del archivo MOFThe contents of the MOF file

A continuación se muestra un ejemplo de un archivo MOF que se puede utilizar para un recurso de sitio web personalizado.Following is an example MOF file that can be used for a custom website resource. Para seguir este ejemplo, guarde este esquema en un archivo y asigne como nombre del archivo Demo_IISWebsite.schema.mof.To follow this example, save this schema to a file, and call the file Demo_IISWebsite.schema.mof.

[ClassVersion("1.0.0"), FriendlyName("Website")]
class Demo_IISWebsite : OMI_BaseResource
{
  [Key] string Name;
  [Required] string PhysicalPath;
  [write,ValueMap{"Present", "Absent"},Values{"Present", "Absent"}] string Ensure;
  [write,ValueMap{"Started","Stopped"},Values{"Started", "Stopped"}] string State;
  [write] string Protocol[];
  [write] string BindingInfo[];
  [write] string ApplicationPool;
  [read] string ID;
};

Tenga en cuenta lo siguiente sobre el código anterior:Note the following about the previous code:

  • FriendlyName define el nombre que se puede utilizar para hacer referencia a este recurso personalizado en los scripts de configuración DSC.FriendlyName defines the name you can use to refer to this custom resource in DSC configuration scripts. En este ejemplo, Website equivale al nombre descriptivo Archive para el recurso integrado Archive.In this example, Website is equivalent to the friendly name Archive for the built-in Archive resource.
  • La clase que defina para el recurso personalizado debe derivarse de OMI_BaseResource.The class you define for your custom resource must derive from OMI_BaseResource.
  • El calificador de tipo, [Key], en una propiedad indica que esta propiedad identificará de forma única la instancia del recurso.The type qualifier, [Key], on a property indicates that this property will uniquely identify the resource instance. Se necesita al menos una propiedad [Key].At least one [Key] property is required.
  • El calificador [Required] indica que la propiedad es obligatoria (debe especificarse un valor en cualquier script de configuración que use este recurso).The [Required] qualifier indicates that the property is required (a value must be specified in any configuration script that uses this resource).
  • El calificador [write] indica que esta propiedad es opcional cuando se utiliza el recurso personalizado en un script de configuración.The [write] qualifier indicates that this property is optional when using the custom resource in a configuration script. El calificador [read] indica que una propiedad no se puede establecer mediante una configuración y es solo con fines informativos.The [read] qualifier indicates that a property cannot be set by a configuration, and is for reporting purposes only.
  • Values restringe los valores que se pueden asignar a la propiedad a la lista de valores definidos en ValueMap.Values restricts the values that can be assigned to the property to the list of values defined in ValueMap. Para más información, consulte Calificadores Value y ValueMap.For more information, see ValueMap and Value Qualifiers.
  • Se recomienda incluir una propiedad denominada Ensure con los valores Present y Absent en el recurso como una forma de mantener un estilo coherente con los recursos integrados de DSC.Including a property called Ensure with values Present and Absent in your resource is recommended as a way to maintain a consistent style with built-in DSC resources.
  • Asigne el nombre del archivo de esquema para el recurso personalizado de la siguiente forma: classname.schema.mof, donde classname es el identificador que sigue a la palabra clave class en la definición del esquema.Name the schema file for your custom resource as follows: classname.schema.mof, where classname is the identifier that follows the class keyword in your schema definition.

Escribir el script del recursoWriting the resource script

El script del recurso implementa la lógica del recurso.The resource script implements the logic of the resource. En este módulo, debe incluir tres funciones llamadas Get-TargetResource, Set-TargetResource y Test-TargetResource.In this module, you must include three functions called Get-TargetResource, Set-TargetResource, and Test-TargetResource. Las tres funciones deben tomar un conjunto de parámetros que sea idéntico al conjunto de propiedades definidas en el esquema MOF que creó para el recurso.All three functions must take a parameter set that is identical to the set of properties defined in the MOF schema that you created for your resource. En este documento, este conjunto de propiedades se conoce como "propiedades del recurso".In this document, this set of properties is referred to as the "resource properties." Almacene estas tres funciones en un archivo llamado <ResourceName>.psm1.Store these three functions in a file called <ResourceName>.psm1. En el ejemplo siguiente, las funciones se almacenan en un archivo denominado Demo_IISWebsite.psm1.In the following example, the functions are stored in a file called Demo_IISWebsite.psm1.

Nota

Al ejecutar el mismo script de configuración en el recurso más de una vez, no se deberían obtener errores. Asimismo, el recurso debería permanecer en el mismo estado que si se hubiera ejecutado el script una vez.When you run the same configuration script on your resource more than once, you should receive no errors and the resource should remain in the same state as running the script once. Para lograrlo, asegúrese de que las funciones Get-TargetResource y Test-TargetResource no modifiquen el recurso y de que la invocación de la función Set-TargetResource más de una vez en una secuencia con los mismos valores de los parámetros sea siempre equivalente a invocarla una vez.To accomplish this, ensure that your Get-TargetResource and Test-TargetResource functions leave the resource unchanged, and that invoking the Set-TargetResource function more than once in a sequence with the same parameter values is always equivalent to invoking it once.

En la implementación de la función Get-TargetResource, utilice los valores de propiedades clave del recurso que se proporcionan como parámetros para comprobar el estado de la instancia del recurso especificado.In the Get-TargetResource function implementation, use the key resource property values that are provided as parameters to check the status of the specified resource instance. Esta función debe devolver una tabla hash que enumere todas las propiedades del recurso como claves y los valores reales de estas propiedades como los valores correspondientes.This function must return a hash table that lists all the resource properties as keys and the actual values of these properties as the corresponding values. En el código siguiente se muestra un ejemplo.The following code provides an example.

# DSC uses the Get-TargetResource function to fetch the status of the resource instance
# specified in the parameters for the target machine
function Get-TargetResource
{
    param
    (
        [ValidateSet("Present", "Absent")]
        [string]$Ensure = "Present",

        [Parameter(Mandatory)]
        [ValidateNotNullOrEmpty()]
        [string]$Name,

        [Parameter(Mandatory)]
        [ValidateNotNullOrEmpty()]
        [string]$PhysicalPath,

        [ValidateSet("Started", "Stopped")]
        [string]$State = "Started",

        [string]$ApplicationPool,

        [string[]]$BindingInfo,

        [string[]]$Protocol
    )

        $getTargetResourceResult = $null;

        <#
          Insert logic that uses the mandatory parameter values to get the website and
          assign it to a variable called $Website
          Set $ensureResult to "Present" if the requested website exists and to "Absent" otherwise
        #>

        # Add all Website properties to the hash table
        # This simple example assumes that $Website is not null
        $getTargetResourceResult = @{
            Name = $Website.Name
            Ensure = $ensureResult
            PhysicalPath = $Website.physicalPath
            State = $Website.state
            ID = $Website.id
            ApplicationPool = $Website.applicationPool
            Protocol = $Website.bindings.Collection.protocol
            Binding = $Website.bindings.Collection.bindingInformation
        }

        $getTargetResourceResult
}

Según los valores especificados para las propiedades del recurso en el script de configuración, la función Set-TargetResource debe realizar una de las siguientes acciones:Depending on the values that are specified for the resource properties in the configuration script, the Set-TargetResource must do one of the following:

  • Crear un sitio web.Create a new website
  • Actualizar un sitio web existente.Update an existing website
  • Eliminar un sitio web existente.Delete an existing website

Esto se ilustra en el siguiente ejemplo.The following example illustrates this.

# The Set-TargetResource function is used to create, delete or configure a website on the target machine.
function Set-TargetResource
{
    [CmdletBinding(SupportsShouldProcess=$true)]
    param
    (
        [ValidateSet("Present", "Absent")]
        [string]$Ensure = "Present",

        [Parameter(Mandatory)]
        [ValidateNotNullOrEmpty()]
        [string]$Name,

        [Parameter(Mandatory)]
        [ValidateNotNullOrEmpty()]
        [string]$PhysicalPath,

        [ValidateSet("Started", "Stopped")]
        [string]$State = "Started",

        [string]$ApplicationPool,

        [string[]]$BindingInfo,

        [string[]]$Protocol
    )

    <#
        If Ensure is set to "Present" and the website specified in the mandatory input parameters
          does not exist, then create it using the specified parameter values
        Else, if Ensure is set to "Present" and the website does exist, then update its properties
          to match the values provided in the non-mandatory parameter values
        Else, if Ensure is set to "Absent" and the website does not exist, then do nothing
        Else, if Ensure is set to "Absent" and the website does exist, then delete the website
    #>
}

Por último, la función Test-TargetResource debe tomar el mismo parámetro establecido que Get-TargetResource y Set-TargetResource.Finally, the Test-TargetResource function must take the same parameter set as Get-TargetResource and Set-TargetResource. En la implementación de Test-TargetResource, compruebe el estado de la instancia del recurso que se especifica en los parámetros clave.In your implementation of Test-TargetResource, check the status of the resource instance that is specified in the key parameters. Si el estado real de la instancia del recurso no coincide con los valores especificados en el conjunto de parámetros, devuelva $false.If the actual status of the resource instance does not match the values specified in the parameter set, return $false. De lo contrario, devuelva $true.Otherwise, return $true.

El código siguiente implementa la función Test-TargetResource.The following code implements the Test-TargetResource function.

function Test-TargetResource
{
    [CmdletBinding()]
    [OutputType([System.Boolean])]
    param
    (
        [ValidateSet("Present","Absent")]
        [System.String]
        $Ensure,

        [parameter(Mandatory = $true)]
        [System.String]
        $Name,

        [parameter(Mandatory = $true)]
        [System.String]
        $PhysicalPath,

        [ValidateSet("Started","Stopped")]
        [System.String]
        $State,

        [System.String[]]
        $Protocol,

        [System.String[]]
        $BindingData,

        [System.String]
        $ApplicationPool
    )

    # Get the current state
    $currentState = Get-TargetResource -Ensure $Ensure -Name $Name -PhysicalPath $PhysicalPath -State $State -ApplicationPool $ApplicationPool -BindingInfo $BindingInfo -Protocol $Protocol

    # Write-Verbose "Use this cmdlet to deliver information about command processing."

    # Write-Debug "Use this cmdlet to write debug information while troubleshooting."

    # Include logic to
    $result = [System.Boolean]
    # Add logic to test whether the website is present and its status matches the supplied
    # parameter values. If it does, return true. If it does not, return false.
    $result
}

Nota

Para una depuración más sencilla, utilice el cmdlet Write-Verbose en la implementación de las tres funciones anteriores.For easier debugging, use the Write-Verbose cmdlet in your implementation of the previous three functions. Este cmdlet escribe texto en la secuencia de mensajes detallados.This cmdlet writes text to the verbose message stream. De forma predeterminada, la secuencia de mensajes detallados no se muestra, pero se puede mostrar si se cambia el valor de la variable $VerbosePreference o se usa el parámetro Verbose en los cmdlets de DSC = new.By default, the verbose message stream is not displayed, but you can display it by changing the value of the $VerbosePreference variable or by using the Verbose parameter in the DSC cmdlets = new.

Crear el manifiesto del móduloCreating the module manifest

Por último, utilice el cmdlet New-ModuleManifest para definir un archivo <ResourceName>.psd1 para el módulo de recursos personalizados.Finally, use the New-ModuleManifest cmdlet to define a <ResourceName>.psd1 file for your custom resource module. Al invocar este cmdlet, haga referencia al archivo del módulo de script (.psm1) que se describe en la sección anterior.When you invoke this cmdlet, reference the script module (.psm1) file described in the previous section. Incluya Get-TargetResource, Set-TargetResource y Test-TargetResource en la lista de funciones que se deben exportar.Include Get-TargetResource, Set-TargetResource, and Test-TargetResource in the list of functions to export. A continuación se muestra un archivo de manifiesto de ejemplo.Following is an example manifest file.

# Module manifest for module 'Demo.IIS.Website'
#
# Generated on: 1/10/2013
#

@{

# Script module or binary module file associated with this manifest.
# RootModule = ''

# Version number of this module.
ModuleVersion = '1.0'

# ID used to uniquely identify this module
GUID = '6AB5ED33-E923-41d8-A3A4-5ADDA2B301DE'

# Author of this module
Author = 'Contoso'

# Company or vendor of this module
CompanyName = 'Contoso'

# Copyright statement for this module
Copyright = 'Contoso. All rights reserved.'

# Description of the functionality provided by this module
Description = 'This Module is used to support the creation and configuration of IIS Websites through Get, Set and Test API on the DSC managed nodes.'

# Minimum version of the Windows PowerShell engine required by this module
PowerShellVersion = '4.0'

# Minimum version of the common language runtime (CLR) required by this module
CLRVersion = '4.0'

# Modules that must be imported into the global environment prior to importing this module
RequiredModules = @("WebAdministration")

# Modules to import as nested modules of the module specified in RootModule/ModuleToProcess
NestedModules = @("Demo_IISWebsite.psm1")

# Functions to export from this module
FunctionsToExport = @("Get-TargetResource", "Set-TargetResource", "Test-TargetResource")

# Cmdlets to export from this module
#CmdletsToExport = '*'

# HelpInfo URI of this module
# HelpInfoURI = ''
}

Compatibilidad con PsDscRunAsCredentialSupporting PsDscRunAsCredential

Nota

PsDscRunAsCredential es compatible con PowerShell 5.0 y versiones posteriores.PsDscRunAsCredential is supported in PowerShell 5.0 and later.

La propiedad PsDscRunAsCredential se puede usar en el bloque de recursos de configuraciones de DSC para especificar que el recurso se debe ejecutar bajo un conjunto especificado de credenciales.The PsDscRunAsCredential property can be used in DSC configurations resource block to specify that the resource should be run under a specified set of credentials. Para más información, consulte DSC de ejecución con las credenciales de usuario.For more information, see Running DSC with user credentials.

Para tener acceso al contexto de usuario desde un recurso personalizado, puede usar la variable automática $PsDscContext.To access the user context from within a custom resource, you can use the automatic variable $PsDscContext.

Por ejemplo, el código siguiente podría escribir el contexto de usuario bajo el cual se ejecuta el recurso en el flujo de salida detallado:For example the following code would write the user context under which the resource is running to the verbose output stream:

if (PsDscContext.RunAsUser) {
    Write-Verbose "User: $PsDscContext.RunAsUser";
}

Reinicio del nodoRebooting the Node

Si las acciones realizadas en la función Set-TargetResource requieren un reinicio, puede usar una marca global para indicar al LCM que reinicie el nodo.If the actions taken in your Set-TargetResource function require a reboot, you can use a global flag to tell the LCM to reboot the Node. Este reinicio se produce inmediatamente después de completarse la función Set-TargetResource.This reboot occurs directly after the Set-TargetResource function completes.

Dentro de la función Set-TargetResource, agregue la siguiente línea de código.Inside your Set-TargetResource function, add the following line of code.

# Include this line if the resource requires a system reboot.
$global:DSCMachineStatus = 1

Para que el LCM reinicie el nodo, la marca RebootNodeIfNeeded debe establecerse en $true.In order for the LCM to reboot the Node, the RebootNodeIfNeeded flag needs to be set to $true. El ajuste ActionAfterReboot debe establecerse también en ContinueConfiguration , que es el valor predeterminado.The ActionAfterReboot setting should also be set to ContinueConfiguration , which is the default. Para obtener más información sobre la configuración del LCM, consulte Configuración del administrador de configuración local o Configuración del administrador de configuración local (v4).For more information on configuring the LCM, see Configuring the Local Configuration Manager, or Configuring the Local Configuration Manager (v4).