Powershell 5 | Powershell 6 | Powershell 7 | Modules

BACKGROUND

Powershell v5: comes with Windows-10 and only works on Windows. Scripting language only.
Powershell Core (aka v6):  used for .NET development. Installable on all systems Windows, Mac, Linux.
Powershell v7: separate install. Co-exist install with v5. One SHELL for both Windows and .Net.


MODULES

Modules are packages that contains PowerShell items, such as cmdlets, providers, functions, workflows, variables, and aliases. Modules are kept and found in repositories or repos. In the repos, they are listed out as Script, Binary, Manifest.
get-module
[get-psresource]

You will notice that there is one called PackageManagement v1.0.0.1. This is the default for Windows 10, Powershell v5.


PACKAGEPROVIDERS | POWERSHELLGET v1

Packageproviders allows Powershell to handle a variety of package management system (apt-get, yum, winget, etc). This is needed because there are different types of providers. To explain, let's look at the builtin providers which are found with:
get-packageprovider

It will output:
msi: Microsoft Installation
msu: Microsoft Update
powershellget: From online gallery/repository.
programs: From Add/Remove Programs

Unlike YUM where all items are .rpm or APT-GET where all items are .deb, Powershell can handle multiple items as shown above (.msi, .msu, .nupkg); this is why there is a need for different packageproviders.

Take note that there is one called PowerShellGet v1.0.0.1. This is the default for Windows 10, Powershell v5.

To see other providers:
find-packageprovider

Perhaps you want Powershell to handle .nupkg packages. In this case, you would have to install the NuGet PackageProvder.

To install other providers, use the following which will allow Powershell to handle .nupkg extensions:
install-packageprovider nuget

[get-PSResourceProvider does not exist because PSResourceGet only supports NuGet repositories, so it can only handle .nupkg packages.]

 

REPOS | REPOSITORIES | GALLERIES | PACKAGESOURCE

Repositories (aka Repos, aka galleries) is a collection of packages of a certain kind.

PSGallery: self publish repo for PowerShell users. While this is a MS platform, it is not trusted automatically as there is no code review.
NuGet: self publish repo for PowerShell and .Net users for .nupkg packages. While this is a MS platform, it is not trusted automatically as there is no code review.
Chocolatey: chocolately is an independent provider free from large corporation regulation.

get-packagesource [PackageManagement v1.4.8.1]
get-psrepository [PowerShellGet v2.2.5]
get-psresourceRepository [Microsoft.PowerShell.PSResourceGet v1.0.0.0]

To install a packagesource, you will need to assign a useful name as well as know the location of the repo:
(Note that this is the outdated location. This exercise will allow us to show how to register, unregister & set. Keep going):
Register-PackageSource -Name NuGet.org -Location "http://www.nuget.org/api/v2" -ProviderName Nuget
[Register-PSResourceRepository]


UPDATING THE DEFAULT PACAKGEMANAGEMENT, POWERSHELLGET v2

As pointed out above, both the module of PackageManagement and PowerShellGet are at v1.0.0.1. While this is the default in Powershell v5 in Windows 10, both are outdated. As a result, the problem with this default version is that it is limited and does not return the correct packages.

You can verify this by:
Get-Module PowerShellGet, PackageManagement -ListAvailable

Let's update both the module of PackageManagement and PowerShellGet.

Use the following to update:
Find-Module PowerShellGet, PackageManagement |Install-Module –Force

Next, we have to exit Powershell because it is being used. Once reloaded, Powershell will pickup the new module versions of PackageManagement and PowerShellGet.

To be sure no other updates are available, let's update the modules:
Update-Module -Name Packagemanagement
Update-Module -Name PowerShellGet

Now when we inspect the modules, we can see that both versions are available:
Get-Module PowerShellGet, PackageManagement -ListAvailable

But only the newest version is loaded:
Get-Module PowerShellGet, PackageManagement

Note that updating the module will also update the PackageProvder of NuGet to v3.0.0.1 (as of this writing):
get-packageprovider

This is interesting because v3.0.0.1 is not published, only v2.8.5.208:
Find-PackageProvider -Name NuGet

If we were to install this PackageProvider manually, it would downgrade it to v2.8.5.208:
Find-PackageProvider -Name NuGet |Install-PackageProvider -Force
(NOTE: If you happen to do this, just install the PackageManagement module again, like this: Find-Module -Name PackageManagement |Install-Module –Force)

 

INSTALL REPO | INSTALL REPOSITORY | INSTALL GALLERY

For the next step of upgrading the NuGet repo, we can see it is using the v2 location:
get-packagesource
[get-PSResourceRepository]

But there is a newer version of Nuget for newer clients, so we need to update this to the v3 location. To do so, let's remove the v2 location; this is called unregister:
unRegister-PackageSource NuGet
[Unregister-PSResourceRepository NuGet]

Now, let's add the v3 location; this is called register:
Register-PackageSource -Name Nuget.org -Location "https://api.nuget.org/v3/index.json" -ProviderName NuGet
[Register-PSResourceRepository -Name Nuget.org -uri "https://api.nuget.org/v3/index.json"]

Note that we could have used the following to set the Nuget repo location, but we are going through the unregister/register exercise to become familiar with the process:
set-packagesource -Name Nuget.org -Location "https://api.nuget.org/v3/index.json"
[Set-PSResourceRepository -Name Nuget.org -uri "https://api.nuget.org/v3/index.json"]

Or we could install GitHub repo:
Set-PSResourceRepository -name "MyGitHubFeed" -Uri "https://nuget.pkg.github.com/MyGitHubOrg/index.json"

Or we could install JFrog repo:
Set-PSResourceRepository -name "MyJFrogFeed" -Uri "https://myjfrogaccount.jfrog.io/artifactory/api/nuget/v3/nuget/index.json"

Or we could install MyGet repo:
Set-PSResourceRepository -name "PublicMyGetFeed" -Uri "https://www.myget.org/F/mypackagefeed/api/v3/index.json"

 

SEARCH POWERSHELL MODULE | FIND POWERSHELL MODULE (OR SCRIPT)

A module adds ability to Powershell. For example, you cannot run Powershell WSUS commands on a Powershell that doesn't have the WSUS module installed. The same for PSWindowsUpdate.
A script automates something in Powershell. You can craft a Powershell script but maybe someone has already done the work for you.
A package is either a module for Powershell or code for .NET

To search for a powershell package, module or script in the repositories, the command is:
find-package <name-here>
find-module <name-here>
find-script <name-here>
[find-psresource <name-here>]

Rarely do you know the actual name, so use asterisks as wildcards, like this:
find-package *foo*
find-module *foo*
find-script *foo*
[find-psresource *foo*]

The beauty of this is that the find-command will search all the repos as once. It will return the package name, version, source-repo and summary.

This can lead to many results, so we can narrow down the search to a specific repo:
find-package *xaml* -providername NuGet

As another example, let's say you are looking for tools to help with ADFS Relying Party Trusts. So, you might try any of the following:
find-package *adfs*
find-module *adfs*
find-script *adfs*
[find-psresource *adfs*]

Also let's search another way:
find-package *party*
find-module *party*
find-script *party*
[find-psresource *party*]

You can see the results for find-package includes: .NET, modules. But not scripts.
You can see the results for find-module includes: modules. But not .NET, scripts.
You can see the results for find-script includes: scripts. But not .NET, modules.
You can see the results for find-psresource includes .NET, modules and scripts.

COMMAND MODULE .NET SCRIPT MODULE OF ORIGIN DE FACTO  
find-package Y Y N PackageManagement PowershellGet v1  
find-module Y N N PowerShellGet PowershellGet v2  
find-script N N Y PowerShellGet PowershellGet v2  
find-psresource Y Y Y Microsoft.PowerShell.PSResourceGet PowershellGet v3  

 

A visual way of searching is by going to the repo websites:
https://www.powershellgallery.com/https://www.nuget.org/

 

INSTALLATION OF POWERSHELL MODULE | INSTALLATION OF POWERSHELL SCRIPT

To install a module:
Install-Module PSWindowsUpdate
[Install-PSResource PSWindowsUpdate]

To install a script:
Install-Script Copy-RelyingPartyTrust
[Install-PSResource Copy-RelyingPartyTrust]

The install commands will give a warning note because as stated above, while this is a MS platform, it is not trusted automatically as there is no code review.

 

Microsoft.PowerShell.PSResourceGet (aka PowerShellGet v3)

Microsoft.PowerShell.PSResourceGet is the new package management solution for PowerShell. With this module, you no longer need to use PowerShellGet and PackageManagement. However, it can be installed side-by-side with the existing PowerShellGet module.
I noted all the PowerShellGet-v3 commands in brackets above [].

Install-Module Microsoft.PowerShell.PSResourceGet

This is a new module that was released in October 2023. To see the details:
get-installedmodule Microsoft.PowerShell.PSResourceGet |fl

There is a list of commands that I added with brackets:
get-command -module Microsoft.PowerShell.PSResourceGet

This module is unified in the sense that is finds/gets/installs/uninstalls both modules & scripts with a single command rather than find-module/find-script | get-module/get-script | install-module/install-script. This is shown in the table above.

Note that it does not recognize currently installed modules/scripts via PowerShellGet or PackageManagement eventhrough they may be present.


INSTALLATION OF POWERSHELL 7

There are a few ways to install PowerShell v7:

1-Winget:
winget install PowerShell

2-PDQ:
PowerShell is available in the PDQ Library/Repo. Simply download the PowerShell Package and deploy to as many systems as needed.

3-PowerShell:
PowerShell-v5 can be used to install Powershell-v7 with the following one-liner:
Invoke-Expression "& { $(Invoke-RestMethod https://aka.ms/install-powershell.ps1) } -UseMSI"

Or use the shorthand alias:
iex "& { $(irm https://aka.ms/install-powershell.ps1) } -UseMSI"

4-GitHub
You can manually download the msi file at GitHub:
wget https://github.com/PowerShell/PowerShell/releases/download/v7.1.4/PowerShell-7.1.4-win-x64.msi -outfile PowerShell-7.1.4-win-x64.msi
msiexec.exe /i "PowerShell-7.1.4-win-x64.msi" ALLUSERS=1 /qn /norestart /log output.log

Once installed, PowerShell-v5 and PowerShell-v7 will co-exist and run at the same time.


INSPECT ENVIRONMENT

To inspect some of PowerShell items, run the following:

$env:psmodulepath -split(';')

To see the current version:
$PSVersionTable

To list the modules in the current session:
get-module
[get-psresource]

To get the modules that are installed on the system through PowerShellGet from the PSGallery repo:
get-installedmodule
get-installedscript
[get-psresource]

To get the modules that are installed on the system but not yet imported into the current session. Note that Get-Module looks for available modules in the path specified by the $env:PSModulePath environment variable as listed above:
get-module -listavailable

Some modules are built-in modules and automatically installed with Powershell.

You will see in the list is PowerShellGet. The PowerShellGet module is the module used to discovering, installing, updating and publishing other PowerShell modules.
To get the commands in a module:
Get-Command -Module
Get-Command -Module PackageManagement
Get-Command -Module PowerShellGet
Get-Command -Module Microsoft.PowerShell.Core
[get-command -module Microsoft.PowerShell.PSResourceGet]

To find what command belongs to a module:
get-command <command-here>

For example, see the difference in the following:
get-command get-packagesource
get-command get-psrepository
get-command Get-PSScriptFileInfo

Putting those together, if you are working with a command, we can find all the related commands:
get-command -module (get-command command-here).source
ie: get-command -module (get-command get-adSyncScheduler).source

To get help with the commands:
Get-Help <command-here>
man <command-here>

And to import a module into the session:
Import-Module
[Import-PSGetRepository]

To get the repos that are available on the system:
get-packagesource
get-psrepository
get-psresourcerepository

 

 

NOTES

https://4sysops.com/archives/how-to-install-and-upgrade-to-powershell-71/
https://docs.microsoft.com/en-us/powershell/module/powershellget/?view=powershell-7.1
https://www.red-gate.com/simple-talk/sysadmin/powershell/managing-packages-using-windows-powershell/https://www.youtube.com/playlist?app=desktop&list=PLyJiOytEPs4etH7Ujq7PU7jlOlHL-9RmV
https://learn.microsoft.com/en-us/powershell/gallery/powershellget/install-powershellget?view=powershellget-2.x
https://learn.microsoft.com/en-us/powershell/module/microsoft.powershell.psresourceget/?view=powershellget-3.x