Public/New-PsModule.ps1

function New-PsModule
{
  <#
    .Synopsis
      Creates a new powershell module in the user's module folder
    .DESCRIPTION
      Using plaster and pester for proper scaffolding this function
      creates a couple of files and folders:
       Data/
       Internal/
       Public/
       Tests/
       Module.psd1
       Module.psm1
       readme.md
    .EXAMPLE
      New-PsModule AwesomePowershellModule
      New-PsModule AwesomePowershellModule "C:\modules\path"
      New-PsModule AwesomePowershellModule "C:\modules\path" "Module description..."
      New-PsModule AwesomePowershellModule "C:\modules\path" "Module description..." "0.0.1"
      New-PsModule AwesomePowershellModule "C:\modules\path" "Module description..." "0.0.1" "Author Name"
  #>

  [CmdletBinding(SupportsShouldProcess=$true)]  
  param (
    [Parameter(Mandatory=$true, 
      ValueFromPipeline=$true,  
      ValueFromPipelineByPropertyName=$true)]
    [string]$ModuleName,
    [string]$ModulePath="",
    [string]$ModuleDesc="Great module...",
    [string]$Version="0.0.1",
    [string]$Author=$env:UserName
  )  
    
  BEGIN{
    . "$PSscriptRoot\Get-PsModuleBuilderPath.ps1"

    if((!$ModulePath) -or (Confirm-IsMissing $ModulePath -Directory)) {
      $ModulePath = Get-PsModuleBuilderPath
    }

    $plasterManifest = "$ModulePath\$ModuleName\Data\plasterManifest.xml"

    $whatifMessage = @"
Creating the following:
  - $ModulePath\$ModuleName\
  - $ModulePath\$ModuleName\Internal\
  - $ModulePath\$ModuleName\Public\
  - $ModulePath\$ModuleName\Test\
  - $ModulePath\$ModuleName\Data\
  - $ModulePath\$ModuleName\Data\plasterManifest.xml
  - $ModulePath\$ModuleName\$ModuleName.psd1
  - $ModulePath\$ModuleName\$ModuleName.psm1
  - $ModulePath\$ModuleName\readme.md
"@

  }#begin
  PROCESS{

    if ($psCmdlet.ShouldProcess("New module: $ModuleName", $whatifMessage)) { 
      Write-Debug $whatifMessage

      if (Confirm-IsMissing $plasterManifest -File) {
        Write-UserPlasterManifest $ModulePath $ModuleName $Author
      }

      Invoke-Plaster -TemplatePath "$PSscriptRoot\..\Data\MetaModule" `
        -DestinationPath "$ModulePath\$ModuleName" `
        -ModuleName $ModuleName `
        -ModuleDesc $ModuleDesc `
        -ModuleVersion $Version `
        -ModuleAuthor $Author `
        -NoLogo `
        -Force

@"
# $ModuleName
 
A Powershell module...
"@
 | Set-Content "$ModulePath\$ModuleName\readme.md"
    }

  }#process
  END{}#end
}

function Confirm-IsMissing {
  param(
    [string]$ModulePath,
    [switch]$File,
    [switch]$Directory
  )
  
  if ($File) {
    return -not (Test-Path $ModulePath -PathType Leaf)
  }
  
  if ($Directory) {
    return -not (Test-Path $ModulePath -PathType Container)
  }

  throw "Please specify -File or -Directory..."
}

function Write-UserPlasterManifest {
  param(
    [string]$ModulePath,
    [string]$name,
    [string]$Author
  )

  Write-Debug "Creating $ModulePath\$name\Data..."
  New-Item -Path "$ModulePath\$name\Data" -ItemType Directory -Force | Out-Null
  
  $plasterManifest = @{
    Path            = "$ModulePath\$name\Data\plasterManifest.xml" 
    TemplateName    = "$Author-manifest" 
    TemplateType    = "Item" 
    Id              = (New-Guid).Guid 
    TemplateVersion = "0.0.1" 
    Title           = "$Author's Module Builder" 
    Description     = "Building modules up to '$Author' standards" 
    Author          = "$Author"
  }
  
  Write-Debug "Creating plaster manifest $ModulePath\$name\Data\plasterManifest.xml..."
  New-PlasterManifest @plasterManifest 
}