Skip to content

Instantly share code, notes, and snippets.

@trayburn
Last active December 17, 2015 05:29
Show Gist options
  • Save trayburn/5558458 to your computer and use it in GitHub Desktop.
Save trayburn/5558458 to your computer and use it in GitHub Desktop.
Powershell Scaffolding Example

PowerShell Scaffolding

Amir's RRYN Version (RRYN == Ruby Rake Yaml Nokogiri)

Setup

First, assuming you've not done a bunch of PowerShell before, lets get you setup with the minimums (in my opinion)

  • Set your execution policy, if you haven't already. You can choose Unrestricted if you prefer, RemoteSigned is a minimum for PSGet.
Set-ExecutionPolicy RemoteSigned
(new-object Net.WebClient).DownloadString("http://psget.net/GetPsGet.ps1") | iex
  • Install PSake (pronounced Sake, like the rice-wine)
install-module psake
import-module psake
  • Personally I setup an alias for PSake
New-Alias psake Invoke-psake

PSake Commands

Run the model task, add a Person (which I made a default) :

psake model

Run the model task, add an AwesomeClass :

psake Model -properties @{name="AwesomeClass"}

Document all tasks:

psake .\default.ps1 -docs
@{
website_port = 80
website_deploy_directory = 'C:\inetpub\website'
solution_name = 'ASolution'
mvc_project = 'AProject'
database = '(local)\SQLEXPRESS'
}
Include ".\utilities.ps1"
properties {
$config = &".\config.ps1"
$config | %{ Set-Variable -Scope 1 -Name $_ -Value $config[$_] }
$mvc_project_directory = $config.mvc_project
# Provide a default (could be done in config.ps1)
# which can be overriden at command line by -Properties argument.
$name = "Person"
}
task model -depends setup `
-description "adds a dynamic model class to your mvc project" `
{
#error validation, did they pass the name argument?
Assert ($name -ne $null) "name parameter required, usage: Invoke-Psake model @{`$n=`"Person`"}"
#create the template, if it doesn't exist already
$path = "$mvc_project_directory\Models\$name.cs"
Assert ((Test-Path $path) -eq $false) "File already exists"
New-Model | Set-Content $path
#add class to cs project
Insert-CompileNode Models $name
}
task clean {
Remove-Item $mvc_project_directory -Recurse -Force -ErrorAction SilentlyContinue
}
task setup -depends clean { .{
mkdir ".\$mvc_project_directory"
mkdir ".\$mvc_project_directory\Models"
cp ".\TestProject.csproj" "$mvc_project_directory\$mvc_project.csproj"
} | Out-Null}
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{5FDF5393-022B-4F00-BF60-34A9A0D806DC}</ProjectGuid>
<OutputType>Exe</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>ConsoleApplication1</RootNamespace>
<AssemblyName>ConsoleApplication1</AssemblyName>
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<PlatformTarget>AnyCPU</PlatformTarget>
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<PlatformTarget>AnyCPU</PlatformTarget>
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="Castle.Core">
<HintPath>..\packages\Castle.Core.3.2.0\lib\net45\Castle.Core.dll</HintPath>
</Reference>
<Reference Include="Castle.Facilities.Logging">
<HintPath>..\packages\Castle.LoggingFacility.3.2.0\lib\net45\Castle.Facilities.Logging.dll</HintPath>
</Reference>
<Reference Include="Castle.Services.Logging.NLogIntegration">
<HintPath>..\packages\Castle.Core-NLog.3.2.0\lib\net40\Castle.Services.Logging.NLogIntegration.dll</HintPath>
</Reference>
<Reference Include="Castle.Windsor">
<HintPath>..\packages\Castle.Windsor.3.2.0\lib\net45\Castle.Windsor.dll</HintPath>
</Reference>
<Reference Include="NLog">
<HintPath>..\packages\NLog.2.0.1.2\lib\net45\NLog.dll</HintPath>
</Reference>
<Reference Include="System" />
<Reference Include="System.Configuration" />
<Reference Include="System.Core" />
<Reference Include="System.Xml.Linq" />
<Reference Include="System.Data.DataSetExtensions" />
<Reference Include="Microsoft.CSharp" />
<Reference Include="System.Data" />
<Reference Include="System.Xml" />
<Reference Include="Topshelf">
<HintPath>..\packages\Topshelf.3.1.1\lib\net40-full\Topshelf.dll</HintPath>
</Reference>
<Reference Include="Topshelf.NLog">
<HintPath>..\packages\Topshelf.NLog.3.1.1\lib\net40-full\Topshelf.NLog.dll</HintPath>
</Reference>
</ItemGroup>
<ItemGroup>
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<ItemGroup>
<None Include="app.config" />
<None Include="bin\Debug\ConsoleApplication1.exe.config" />
<None Include="bin\Debug\ConsoleApplication1.vshost.exe.config" />
<None Include="bin\Debug\ConsoleApplication1.vshost.exe.manifest" />
<None Include="bin\Debug\NLog.config" />
<None Include="bin\Debug\Templates.Service.exe.config" />
<None Include="NLog.config">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<Content Include="bin\Debug\ConsoleApplication1.vshost.exe" />
</ItemGroup>
<ItemGroup>
<Folder Include="bin\Release\" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
Other similar extension points exist, see Microsoft.Common.targets.
<Target Name="BeforeBuild">
</Target>
<Target Name="AfterBuild">
</Target>
-->
</Project>
function Insert-CompileNode {
param($dir, $file)
$project = (gi ".\$mvc_project_directory\$mvc_project_directory.csproj").FullName
$node = "<Compile Include='$dir\$file.cs' />"
$doc = ([xml](Get-Content $project))
$doc | `
Select-Xml "//x:ItemGroup[x:Compile]" -Namespace @{"x"=$doc.Project.xmlns} | `
Select-Object -ExpandProperty Node -First 1 | `
% { $_.InnerXml += $node; $doc.Save($project) }
}
function New-Model {
@"
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using Oak;
namespace $mvc_project_directory.Models
{
public class $name : DynamicModel
{
public $name(object dto) : base(dto) { }
public $name() { }
//IEnumerable<dynamic> Validates() { }
//IEnumerable<dynamic> Associates() { }
}
}
"@
}
@amirrajan
Copy link

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment