Monthly Archive

Monthly Archives: February 2009

Module Manifests

When we looked at modules we used Export-Module at the end of the module file to control which functions were made visible.  This becomes a little awkward if we have a large number of functions that we may want to use in differing combinations.

The solution is to use a module manifest.  This is a file that looks something like this

# Module manifest for module 'user'
# Generated by: Richard Siddaway
# Generated on: 22/02/2009

# These modules will be processed when the module manifest is loaded.
NestedModules = 'user.psm1'

# This GUID is used to uniquely identify this module.
GUID = 'b55021a4-5a21-4cf6-9b76-29eef95db0cf'

# The author of this module.
Author = 'Richard Siddaway'

# The company or vendor for this module.
CompanyName = 'Macdui'

# The copyright statement for this module.
Copyright = '(c) Richard Siddaway'

# The version of this module.
ModuleVersion = '1.0'

# A description of this module.
Description = 'Module of scripts for working with AD user accounts'

# The minimum version of PowerShell needed to use this module.
PowerShellVersion = '2.0'

# The CLR version required to use this module.
CLRVersion = '2.0'

# Functions to export from this manifest.
ExportedFunctions = 'new-password'

# Aliases to export from this manifest.
ExportedAliases = '*'

# Variables to export from this manifest.
ExportedVariables = '*'

# Cmdlets to export from this manifest.
ExportedCmdlets = '*'

# This is a list of other modules that must be loaded before this module.
RequiredModules = @()

# The script files (.ps1) that are loaded before this module.
ScriptsToProcess = @()

# The type files (.ps1xml) loaded by this module.
TypesToProcess = @()

# The format files (.ps1xml) loaded by this module.
FormatsToProcess = @()

# A list of assemblies that must be loaded before this module can work.
RequiredAssemblies = @()

# Lists additional items like icons, etc. that the module will use.
OtherItems = @()

# Module specific private data can be passed via this member.
PrivateData = ''


I generated this one on Windows 7.  Use New-Module manifest without any parameters and you will be prompted for the required information.  The rest can be filled in using your favourite editor.  The CTP3 version uses slightly different names in some places so the two aren’t completely compatible.

The manifest can be tested

PS> Invoke-History 59
Test-ModuleManifest ./user2.psd1

Name              : user2.psd1
Path              : C:\Scripts\wip\user2.psd1
Description       : Module of scripts for working with AD user accounts
Guid              : b55021a4-5a21-4cf6-9b76-29eef95db0cf
Version           : 1.0
ModuleBase        : C:\Scripts\wip
ModuleType        : Manifest
PrivateData       :
AccessMode        : ReadWrite
ExportedAliases   : {}
ExportedCmdlets   : {}
ExportedFunctions : {}
ExportedVariables : {}
NestedModules     : {}

Notice the use of invoke-history to rerun a previous command.

That is the basics of modules covered.  Next task is to add some functions and modify the manifest so that I can use it to create users

Technorati Tags: ,

LiveMeeting – Last Call

7pm GMT on Thursday February 26th sees Rolf Masuch presenting on using PowerShell as Active Directory Login Script.  Details here!43CFA46A74CF3E96!2079

Technorati Tags: ,

Windows 7

Just installed Windows 7 on an old laptop – 0.75GB RAM single core.  It works a treat and is reasonably responsive.  It is more than enough for Office type applications and Internet.  Well impressed as Vista wouldn’t even look at this machine.

Looks like I’ve just extended the life time of that machine.

Few issues with drivers that I’m still resolving but nothing thats a show stopper.

Best of all it has PowerShell v2 installed.

Technorati Tags:

PowerShell UG March

The March meeting will be on Thursday 26th March at 6.30pm

Location:  Microsoft Offices in Reading (TVP) Memphis room


Jonathan Medd on the AD cmdlets in Windows Server 2008 R2

Alan Renouf on VMWare’s VI toolkit

plus there will be an introduction to Regular Expressions in PowerShell

Don’t forget Thursdays Live Meeting

Technorati Tags: ,

PowerShell Modules II

Last time we created a script file with three functions

new-password which controls the creation of a new password

get-randchar which generates a random character from a given character set

add-character which adds one of more characters of a given type to the password using get-randchar

Oops I made the mistake of calling it add-characters in the original script.  The convention is that nouns are always singular.

At the moment our three functions are in a .ps1 file that we can dot source to load the functions.  This loads all three functions but I only really want new-password to be visible.

An easier way to load functionality is to use the Import-Module cmdlet.  First off we need to turn our script into a module.  Ok change the name from user.ps1 to user.psm1.  Now we can use

Import-Module ./user.psm1

to load the functions.  We can see what is loaded by using

PS> Get-Module

ModuleType Name                      ExportedCommands
---------- ----                      ----------------
Script     user                      {add-characters, new-password, get-randchar}

One of the good things about using modules is that Remove-Module will unload the functions.  So we’ll do that and have a look at what else might be available with modules

PS> Get-Command *module*

CommandType     Name
-----------     ----
Cmdlet          Export-ModuleMember
Cmdlet          Get-Module
Cmdlet          Import-Module
Function        Load-Modules
Cmdlet          New-Module
Cmdlet          New-ModuleManifest
Cmdlet          Remove-Module
Cmdlet          Test-ModuleManifest

Export-ModuleMember looks interesting.  It will control the module members such as functions, aliases and variables that are exported by the module – that is they are made available. So we add a last line to the module.

Export-ModuleMember -Function new-password

After importing the module we have

PS> Get-Module

ModuleType Name                      ExportedCommands
---------- ----                      ----------------
Script     user                      new-password

If we do dir function:  we will only see our new-password function

By using modules we can control which functions are “published” and which functions remain in the background as invisible worker functions. As we add more functions into our module we just add to the list of functions being exported.

The module can be made even more flexible by creating a module manifest which is the subject of the next post.

Technorati Tags: ,,,

Thursday – Live Meeting

Don’t forget

7pm GMT on Thursday February 26th sees Rolf Masuch presenting on using PowerShell as Active Directory Login Script.  Details here!43CFA46A74CF3E96!2079

Technorati Tags: ,

PowerShell advanced function parameters

One annoying error I have just stumbled over.  When using the Parameter keyword don’t put a space after it.  If you do this

[Parameter (Position=0,HelpMessage="The length of password. Default is random between 8 and 12")]

you will get this error

Cannot find type for custom attribute 'Parameter '. Please make sure the assembly containing this type is loaded.
At C:\Scripts\wip\password.ps1:29 char:20
+         [Parameter  <<<< (Position=0,HelpMessage="The length of password. Default is random between 8 and 12")]
    + CategoryInfo          : InvalidOperation: (Parameter :Token) [], RuntimeException
    + FullyQualifiedErrorId : CustomAttributeTypeNotFound

for it to run correctly you need to use

[Parameter(Position=0,HelpMessage="The length of password. Default is random between 8 and 12")]

notice that the opening ( comes immediately after the word Parameter

One to watch

PowerShell ISE syntax errors

One thing I’ve noticed with the ISE is that if you have a syntax error such as mismatched brackets or forget a closing “ on a string all of the colour syntax highlighting disappears after the error – the text is all black (or whatever colour you are using).  Helps spot the errors.

Technorati Tags: ,,

PowerShell v1 to v2 changes

Jeffrey left a comment on this post!43CFA46A74CF3E96!2084.entry regarding discovery of WMI classes.  He pointed out that if the line of PowerShell is changed to

Get-WMIObject -NameSpace root -Recurse -List *Printer*

that you can check all namespaces in one hit.  Recurse! where did that come from.

Checked the help file for Get-WmiObject and couldn’t see anything about recurse – but it is mentioned in the release notes. Must read the release notes more carefully.

There are a ton of changes between v1 and v2 and it can be difficult to keep track of them all.  One thing I do is download the v1 graphical help from and keep it on the desk top.  It is always handy to refer back to the v1 help to check for changes and I can compare the help for v1 and v2 easily.  Note that the v2 help isn’t always complete – functionality has to be produced before it can be documented.

The other good source of information is and

PowerShell is getting bigger and better every time we turn around. Hopefully these resources will help to keep track of the changes.

Technorati Tags: ,,

Discovering WMI

One thing that seems to come up rather frequently on the newsgroups is what WMI class do I need to use to do X.

The really confusing thing about WMI is knowing just what is available. I have done far more with WMI since discovering PowerShell than I ever did with VBScript. That’s for 2 reasons. Firstly WMI is massively easier to use with PowerShell and it is easier to find out what you need to use.

WMI is arranged in a hierarchy of namespaces.  Most of the useful stuff can be found in the default namespace ‘root\cimv2’  We can find out what is available quite easily by using

Get-WmiObject -List

This will generate a long list of classes.  If you have an idea of what you want to look at then we can try something like

Get-WmiObject -List *printer*

which will return all of the classes relating to printers.  WMI classes are named fairly sensibly so it is easy to vary the search if you don’t quite get what you need.

Other good ways for discovering WMI – use PowerGUI – it has a WMI browser or download wmiexplorer from

Which ever way you decide to follow to discover WMI – it will be a big part of your PowerShell tool kit.

Technorati Tags: ,