PowerShell

Executing hidden or private functions from PowerShell Modules

When you write PowerShell modules, there's a high chance you will have conflicts with either existing system commands (you should avoid that) or with someone else's modules. There are also times when someone wants to use a private function from a module that only exports essential functions. Here's a couple of ways how to deal with those scenarios.

Discovering hidden PowerShell commands

For this article, I'll use something you should never, or very rarely do. I will create a small function called Get-Date and therefore overwrite PowerShell one.

function Get-Date {
    param(
        [string] $Something
    )
    Write-Host "This function does something $Something"
}

Get-Date -Something 'Else'

Now for the remaining of the PowerShell session whenever you will try to use Get-Date for something, it will be my function that shows up rather than the built-in one. This may be less than great. How can you deal with a scenario where you have two or more commands from different modules having the same name?

Get-Command Get-Date -All | Format-Table -Property CommandType, Name, ModuleName -AutoSize

The command above allows you to find out all modules that have precisely the same function as you want to execute. It shows that right now Get-Date can be found without any module (which is correct because I've copy/pasted that function into PS Session) and there's a built-in cmdlet Get-Date from Microsoft.PowerShell.Utility. So how can we get it to work without renaming our function or someone else's function in a module you just downloaded? Well, there are two ways to do it.

Import-Module Microsoft.PowerShell.Utility -Prefix 'Test' 
Get-TestDate

Use Prefix in Import-Module command to define your prefix. This gives you the ability to set something useful for you without going to the developer of some module and complaining that his function conflicts with your function or someone else's function. For example, in Dashimo, I have a function called Table. The same function name is in PScribo module. All you have to do to fix this clash of functions is to use Import-Module PScribo -Prefix PScribo to be able to use both modules even at the same time.

Import-Module Dashimo
Import-Module PScribo -Prefix PScribo

# Dashimo
Dashboard {
     Table -
}

# PScribo
Document {
      PScriboTable
}

So that's one way, and it's pretty straightforward. The second way is actually to call a command by its module name.

Microsoft.PowerShell.Utility\Get-Date 

Calling private functions from PowerShell modules

Sometimes developer of PowerShell module creates a function that he then uses that function across his module but hides it, so it's not accessible when someone installs and imports it. I have created several PowerShell modules that have Public one or two commands and then Private, non-accessible functions that I didn't want to expose. But what if you wanted to use some of those functions? What if the function was so good that you wanted to use it in your code without “extracting” that function from someone else's code (which may or may not be as simple as copy/paste). Fortunately, there is a way to do it:

Get-Command -Module PSWinDocumentation.AD 

As you can see my PSWinDocumentation.AD PowerShell module has only two exported functions. That was intentional and something I've done on purpose. However, that module has about 100 small, internal, private functions that I use to deliver results. If for some reason you would like to use any of those functions in your code you can either copy/paste it from my GitHub repository into your own and use the function to suit your needs or call it like that.

$Features = Import-Module -Name 'PSWinDocumentation.AD' -PassThru
& $Features { Get-WinADDomain | Format-Table -AutoSize }

Notice that again I'm using Import-Module, but the magic here is about PassThru switch. You can utilize any of the private functions that way. In my case, I'm calling Get-WinADDomain. Notice that I'm using & (ampersand)& is the call operator which allows you to execute a command, a script, or a function.

So instead of copying some functions from other modules, you can use that instead.

Przemyslaw Klys

System Architect with over 14 years of experience in the IT field. Skilled, among others, in Active Directory, Microsoft Exchange and Office 365. Profoundly interested in PowerShell. Software geek.

Share
Published by
Przemyslaw Klys

Recent Posts

Active Directory Replication Summary to your Email or Microsoft Teams

Active Directory replication is a critical process that ensures the consistent and up-to-date state of…

2 weeks ago

Syncing Global Address List (GAL) to personal contacts and between Office 365 tenants with PowerShell

Hey there! Today, I wanted to introduce you to one of the small but excellent…

5 months ago

Active Directory Health Check using Microsoft Entra Connect Health Service

Active Directory (AD) is crucial in managing identities and resources within an organization. Ensuring its…

7 months ago

Seamless HTML Report Creation: Harness the Power of Markdown with PSWriteHTML PowerShell Module

In today's digital age, the ability to create compelling and informative HTML reports and documents…

8 months ago

How to Efficiently Remove Comments from Your PowerShell Script

As part of my daily development, I create lots of code that I subsequently comment…

8 months ago

Unlocking PowerShell Magic: Different Approach to Creating ‘Empty’ PSCustomObjects

Today I saw an article from Christian Ritter, "PowerShell: Creating an "empty" PSCustomObject" on X…

9 months ago