Monthly Archive

Categories

PowerShellGet

A use for default parameters – default powershellget repository

When you use Find-Module by default all repositories are searched

£> Find-Module -Name Pester | ft Version, Name, Repository -a

Version Name   Repository
------- ----   ----------
3.2.0   Pester PSGallery
3.2.0   Pester PowerShellModules

 

If you don’t give a module name that could be a lot of data to sort through. If you are running an internal repository you may want to check that repository first and only use other repositories if that one doesn’t contain the module.

 

£> Find-Module -Name Pester -Repository PowerShellModules  | ft Version, Name, Repository -a

Version Name   Repository
------- ----   ----------
3.2.0   Pester PowerShellModules

 

This means that you have to type the repository name each time. It would be better if you could make a particular repository the default.  One way to do this is to define default parameters. This functionality was introduced in PowerShell 3.0

 

£> $PSDefaultParameterValues.Add("Find-Module:Repository", 'PowerShellModules')

£> $PSDefaultParameterValues

Name                           Value
----                           -----
Find-Module:Repository         PowerShellModules

£> Find-Module -Name Pester | ft Version, Name, Repository -a

Version Name   Repository
------- ----   ----------
3.2.0   Pester PowerShellModules

 

You can override the default if you wish

£> Find-Module -Name Pester -Repository PSGallery  | ft Version, Name, Repository -a

Version Name   Repository
------- ----   ----------
3.2.0   Pester PSGallery

 

You can do the same for install-module so that it will default to your internal repository

£> $PSDefaultParameterValues.Add("Install-Module:Repository", 'PowerShellModules')

£> Install-Module -Name Pester -Force -Verbose
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Using the specified source names : 'PowerShellModules'.
VERBOSE: Getting the provider object for the OneGet Provider 'NuGet'.
VERBOSE: The specified Location is 'http://localhost:81/nuget/PowerShellModules' and OneGetProvider is 'NuGet'.
VERBOSE: In PSModule Provider - 'Get-InstalledPackage'.
VERBOSE: The specified Location is 'NuGet' and OneGetProvider is 'NuGet'.
VERBOSE: Downloading module 'Pester' with version '3.2.0' from the repository
'http://localhost:81/nuget/PowerShellModules'.
VERBOSE: NuGet: Installing 'Pester 3.2.0'.
VERBOSE: NuGet: Successfully installed 'Pester 3.2.0'.
VERBOSE: Module 'Pester' was installed successfully.

 

-Force was used as the module is already installed.

 

Your default parameters now look like this

£> $PSDefaultParameterValues

Name                           Value
----                           -----
Find-Module:Repository         PowerShellModules
Install-Module:Repository      PowerShellModules

 

Add the two lines

$PSDefaultParameterValues.Add("Find-Module:Repository", 'PowerShellModules')

$PSDefaultParameterValues.Add("Install-Module:Repository", 'PowerShellModules')

 

To your profile and your defaults will be available every time you start PowerShell

Accessing your PowerShellget repository from another machine

So far the new PowerShellGet repository has been accessed from the local machine. You need to register the new repository on each machine from which you want to access it.

Register-PSRepository -Name PowerShellModules -SourceLocation http://W12R2DSC:81/nuget/PowerShellModules -InstallationPolicy Trusted

 

The only change to is substituting the name of the server for localhost in the source location URI.

 

NOTE: you will need to ensure that the Windows firewall is either off or allows the appropriate traffic through to the server hosting you repository

 

You can use the new repository

PS C:\Windows\system32> Get-PSRepository | ft Name, SourceLocation -AutoSize

Name              SourceLocation
----              --------------
PSGallery         https://www.powershellgallery.com/api/v2/
MSPSGallery       http://search.microsoft.com/default.aspx
PowerShellModules http://w12r2dsc:81/nuget/PowerShellModules

 

And see the modules

PS C:\Windows\system32> Find-Module -Name Pester | ft -a

Version Name   Repository        Description
------- ----   ----------        -----------
3.2.0   Pester PSGallery         Pester provides a framework
3.2.0   Pester PowerShellModules Pester provides a framework

 

And install modules

PS C:\Windows\system32> Install-Module -Name pester -Repository PowerShellModules

 

PS C:\Windows\system32> Get-Module -ListAvailable pest* | ft -a

    Directory: C:\Program Files\WindowsPowerShell\Modules

ModuleType Version Name   ExportedCommands
---------- ------- ----   ----------------
Script     3.2.0   Pester {Describe, Context, It, Should...}

Working with multiple PowerShellGet repositories

In http://blogs.msmvps.com/richardsiddaway/2015/01/04/creating-a-powershellget-repository/  I showed how to create a repository to use with PowerShellGet.  At the end of that article PowerShellGet would search all of the defined repositories for a module

£> Find-Module -Name Pester | Format-Table Version, Name, Repository -AutoSize

Version Name   Repository
------- ----   ----------
3.2.0   Pester PSGallery
3.2.0   Pester PowerShellModules

 

If you delete the Pester module and want to re-install it you need to specify the repository otherwise you get an error:

£> Install-Module -Name Pester -Verbose
VERBOSE: The -Repository parameter was not specified.  PowerShellGet will use all of the registered repositories.
VERBOSE: Getting the provider object for the OneGet Provider 'NuGet'.
VERBOSE: The specified Location is 'https://www.powershellgallery.com/api/v2/' and OneGetProvider is 'NuGet'.
VERBOSE: Getting the provider object for the OneGet Provider 'NuGet'.
VERBOSE: The specified Location is 'http://search.microsoft.com/default.aspx' and OneGetProvider is 'NuGet'.
VERBOSE: Getting the provider object for the OneGet Provider 'NuGet'.
VERBOSE: The specified Location is 'http://localhost:81/nuget/PowerShellModules' and OneGetProvider is 'NuGet'.
WARNING: 'Pester' matched module 'Pester/3.2.0' from provider: 'PSModule', repository
'https://www.powershellgallery.com/api/v2/'
WARNING: 'Pester' matched module 'Pester/3.2.0' from provider: 'PSModule', repository
'http://localhost:81/nuget/PowerShellModules'
OneGet\Install-Package : Unable to install, multiple modules matched 'Pester'. Please specify a single -Repository.
At C:\Windows\system32\WindowsPowerShell\v1.0\Modules\PowerShellGet\PSGet.psm1:615 char:21
+             $null = OneGet\Install-Package @PSBoundParameters
+                     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (Microsoft.Power....InstallPackage:InstallPackage) [Install-Package], E
   xception
    + FullyQualifiedErrorId : DisambiguateForInstall,Microsoft.PowerShell.OneGet.CmdLets.InstallPackage

 

£> Install-Module -Name Pester -Repository PowerShellModules -Verbose
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Using the specified source names : 'PowerShellModules'.
VERBOSE: Getting the provider object for the OneGet Provider 'NuGet'.
VERBOSE: The specified Location is 'http://localhost:81/nuget/PowerShellModules' and OneGetProvider is 'NuGet'.
VERBOSE: In PSModule Provider - 'Get-InstalledPackage'.
VERBOSE: Performing the operation "Install-Module" on target "Version '3.2.0' of module 'Pester'".
VERBOSE: The specified Location is 'NuGet' and OneGetProvider is 'NuGet'.
VERBOSE: Downloading module 'Pester' with version '3.2.0' from the repository
'http://localhost:81/nuget/PowerShellModules'.
VERBOSE: NuGet: Installing 'Pester 3.2.0'.
VERBOSE: NuGet: Successfully installed 'Pester 3.2.0'.
VERBOSE: Module 'Pester' was installed successfully.

Creating a PowerShellGet repository

In this post - http://blogs.msmvps.com/richardsiddaway/2014/12/21/delivering-powershell-code-with-the-november-preview/ – I showed how to use PowerShellGet, which is a feature new to PowerShell 5.0 to install PowerShell modules. By default PowerShelget uses the PowerShell gallery at https://www.powershellgallery.com as its source.

 

I don’t feel comfortable installing modules direct from a public gallery so I want my own.  I suspect that many organizations will want to use their own module repository rather than something on the Internet over which they have no control.

 

There are a number of options for setting up your own gallery.

You could create an online nuget feed. This is described in this post from the PowerShell team:
http://blogs.msdn.com/b/powershell/archive/2014/05/20/setting-up-an-internal-powershellget-repository.aspx

 

You could create your own nuget repository – an example of doing this can be found here - http://learn-powershell.net/2014/04/11/setting-up-a-nuget-feed-for-use-with-oneget/

 

After reading http://asaconsultant.blogspot.no/2014/05/build-your-local-powershell- module.html I decided to start with ProGet (http://inedo.com/proget/pricing) as it seemed simple and was installed locally so I could take it with me to do demos.

 

To keep things even simpler I went with the free version and used the download that also  installs SQL Express. The installer also can create a service INEDOPROGETSVC to host the web service ProGet will use. Set the Service to use the LocalSystem account so that it can access the location to which the modules will be published.

 

The ProGet default feed is nuget but you want your own for this game.  Its not obvious how to do this but open Proget administration page - http://localhost:81/administration

 

I’m using port 81 as this is running on my DSC server.

 

Click manage feeds and you’ll find a button labelled Create New Feed. Press the button.

You have 3 choices

A nuget feed

A chocolately feed

a npm feed (private registry)

Lets go with nuget.

 

After supplying a name and description I went with the defaults to complete the feed creation.

 

At this point PowerShellget can’t see the new repository so you need to register it.

£> Register-PSRepository -Name PowerShellModules -SourceLocation http://localhost:81/nuget/PowerShellModules -Installati
onPolicy Trusted

 

And it now shows in my list of PowerShell repositories

£> Get-PSRepository | fl Name, SourceLocation

Name           : PSGallery
SourceLocation : https://www.powershellgallery.com/api/v2/

Name           : MSPSGallery
SourceLocation : http://search.microsoft.com/default.aspx

Name           : PowerShellModules
SourceLocation : http://localhost:81/nuget/PowerShellModules

 

You need to set a location to which modules will be published

Set-PSRepository -Name PowerShellModules -PublishLocation 'http://localhost:81/nuget/PowerShellModules'

 

Now to try and publish a module.

 

I’m going to use the Pester module I downloaded in the previous article:

 

£> Publish-Module -Name Pester -NuGetApiKey "Admin:Admin" -Repository PowerShellModules -Verbose
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Module'Pester' was found in 'C:\Program Files\WindowsPowerShell\Modules\Pester'.
VERBOSE: Loading module from path 'C:\Users\Richard\AppData\Local\Temp\409922302\Pester\Pester.psm1'.
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Repository details, Name = 'PowerShellModules', Location = 'http://localhost:81/nuget/PowerShellModules';
IsTrusted = 'True'; IsRegistered = 'True'.
VERBOSE: Using the specified source names : 'PowerShellModules'.
VERBOSE: Getting the provider object for the OneGet Provider 'NuGet'.
VERBOSE: The specified Location is 'http://localhost:81/nuget/PowerShellModules' and OneGetProvider is 'NuGet'.
VERBOSE: Performing the operation "Publish-Module" on target "Version '3.2.0' of module 'Pester'".
VERBOSE: Successfully published module 'Pester' to the module publish location
'http://localhost:81/nuget/PowerShellModules'.

 

The -NuGetApiKey "Admin:Admin"  is the default and you’d want to change that for a production system.

 

Finally test the repository contents

£> Find-Module -Repository PowerShellModules

Version    Name                                Repository
-------    ----                                ----------
3.2.0      Pester                              PowerShellModules