How to share a Powershell psm1 across Azure Functions - powershell

You can create a modules folder and place a psm1 file there for auto loading. Is there a way to share that psm1 across functions in the same App Service?

Yes, you may move your modules folder up the directory tree and place it under wwwroot, e.g. D:\home\site\wwwroot\mymodules. Auto-loading will not occur in this setup, so you will need to explicitly add the Import-Module command in your PowerShell script, e.g.
Import-Module "D:\home\site\wwwroot\mymodules\MyScript.psm1";
If you suspect that MyScript.psm1 is already installed on the system and need to override it with your version, add the -Global flag as follows
Import-Module "D:\home\site\wwwroot\mymodules\MyScript.psm1" -Global;

Related

Can I run powershell commands without installing module?

I would like to run a script that requires to use commands from the GroupPolicy module. However, this module is not guaranteed to be installed on every machine and some machines might be stand alone. Can I have have the module copied over with my scripts and run commands from it, without installing the module?
Can I have have the module copied over with my scripts and run commands from it, without installing the module?
Yes. Installing a module in PowerShell simply means placing it one of the directories listed in the $env:PSModulePath environment variable, which allows PowerShell to discover it and import (load) it on demand, as part of the module auto-loading feature
However, you're free to copy modules elsewhere, as long as the code that relies on them knows their path and loads them with an explicit Import-Module call.
For instance, if you bundle your script with a GroupPolicy subdirectory containing that module, the script could import it as follows:
# $PSScriptRoot contains the calling script's directory.
Import-Module $PSScriptRoot\GroupPolicy

Powershell : Executing custom function on remote servers

i have custom functions list, and another config file that is going to be used by the functions, my goal is to run those functions on remote servers, considering that some functions call other function from within them that's why i can't use the method below to call functions that are loaded in the local session.
invoke-command -scriptblock ${function:foo}
is it possible to make a module out of it and then make that module get imported automatically on system boot rather than user logon.
any suggestions on how to accomplish the main goal ?
Well, if you want to install Powershell Module on the system just copy it to appropriate directory.
Installing Modules for all Users in Program Files
If you want a module to be available to all user accounts on the computer, install the module in the Program Files location.
$EnvProgramFiles\WindowsPowerShell\Modules\<Module Folder>\<Module Files>
Reference: https://msdn.microsoft.com/en-us/library/dd878350(v=vs.85).aspx
Install Modules in PSModulePath whenever possible, install all modules in a path that is listed in the PSModulePath environment variable or add the module path to the PSModulePath environment variable value.
The PSModulePath environment variable ($Env:PSModulePath) contains the locations of Windows PowerShell modules. Cmdlets rely on the value of this environment variable to find modules.
By default, the PSModulePath environment variable value contains the following system and user module directories, but you can add to and edit the value.
$PSHome\Modules (%Windir%\System32\WindowsPowerShell\v1.0\Modules)
# This location is reserved for modules that ship with Windows. Do not install modules to this location.
$Home\Documents\WindowsPowerShell\Modules (%UserProfile%\Documents\WindowsPowerShell\Modules)
$Env:ProgramFiles\WindowsPowerShell\Modules (%ProgramFiles%\WindowsPowerShell\Modules)

How do I import a new PowerShell cmdlet?

I've written a PowerShell cmdlet in C#.
Where do I copy the library at this point?
And how do I import it into PowerShell so that I can use it?
There are two ways to load your new cmdlet.
Import Cmdlets Using Modules. Here you either put your cmdlet DLL into a system-recognized path that will allow you to load a module with a simple name (e.g. Import-Module MyModule), or you can put it in an arbitrary directory for which you need to specify a complete path (e.g. Import-Module C:\code\MyModule.dll). If you have only a single DLL and no dependencies, you can actually give the DLL as shown. Typically, though, you will also want to create a manifest using New-ModuleManifest (creating, e.g., a MyModule.psd1 file) then pass that psd1 file rather than the dll to Import-Module.
Create a Windows PowerShell Snap-in. This requires writing one additional C# class, quite small, that provides the glue necessary to treat your cmdlet as a snap-in. Then you have to register the snap-in with the installutil program and finally load the snapin with Add-SnapIn. (See also How to Register Snap-ins...)
Curiously, almost all articles that talk about writing cmdlets suggest the snap-in approach, but this is simply because that technique has been available since PowerShell version 1, while modules did not come along until version 2. Everything I have read, though, suggests essentially that the snap-in approach is deprecated to the simpler--and more flexible--module approach.

Must Powershell modules be placed in separate folders?

Using PowerShell 2.0
According to what I've read online, user-created powershell modules must each reside in their own directory. For example if I create a module called MyModule.psm1 it must reside in a folder called MyModule and reside in any directory listed in $env:PSModulePath.
If I have many modules for a project, it seems silly to me to have to create a separate folder for each one. Is this really necessary? Why? Any elegant way around it?
If you want to just have the .psm1 file, you can import it by giving the path to the file itself rather than just the name of the module.
For example:
import-module c:\mymodules\folder\themodule.psm1
With this technique you can have as many modules as you want in the same folder. I don't know that I'd recommend this, but it does work.
PowerShell modules can consist of more than one file, for instance for providing multi-language help or by splitting the functionality into several files. So yes, it's necessary.
It's not ideal, but you could create junctions (MSDN) using Sysinternals junction.exe. That would allow you to store all of the actual data in one folder, but reference it using different paths.
[MSDN] Hard Links and Junctions
Assume that you had three (3) stand-alone .psm1 module files in a folder named Modules in your $env:UserProfile\Documents\WindowsPowerShell\Modules directory.
You can use several junction.exe commands to create junctions (links) that point to the "real" Modules folder on the filesystem.
$ModulePath = '{0}\Modules' -f (Split-Path -Path $Profile.CurrentUserCurrentHost -Parent);
junction.exe $ModulePath\Foo $ModulePath\Modules;
junction.exe $ModulePath\Bar $ModulePath\Modules;
junction.exe $ModulePath\Trevor $ModulePath\Modules;
Here is what it looks like when you navigate into one of the junctions, for example, Foo.
As far as Windows PowerShell is concerned, you are in the Foo directory, which matches the Foo.psm1 file name. It should ignore the rest of the files in that folder.
Now, you can run Get-Module -ListAvailable, and you should see a list of the modules in your user module directory.

How to ship powershell module to production environment?

I have written all my powershell functions in a ps1 file.
In another ps1 file ,it is being dot sourced and function are being called.
When i look for better methods i came to know that putting all the functions as modules (.psm1) is better option.
But for .ps1 file i can simply it in a folder and ship it.
With .psm1 file ,it says i have to add it to particular location so that it can be imported.
how to provide .psm1 file to customer then ? should we instruct them to copy to the mentioned location before using it ? (if we don't ship via msi)
Technically you can import psm1 files via path but that isn't the best user experience. If you put the file in a folder under either $home\documents\WindowsPowerShell\Modules or $pshome\Modules then the user can import based on just the name of the psm1 file. Finally, you can put the psm1 file in any location you want and if you modify the PSModulePath environment variable to include that directory, PowerShell will search for modules in that dir.