Wednesday, March 21, 2012

Finding The Folder the .NET Utilities Live in - Using PowerShell

I am playing around with some PowerShell V3 stuff and needed to use Ngen.exe to do a native generation of an assembly and move it to the Global Assembly Cache. So where is it? I could have wandered around in the Windows folder, but instead decided to ask .NET itself, using PowerShell.

The .NET class System.Runtime.InteropServices.RuntimeEnvironment contains several static methods that return information about the CLR environment.  There are three that are of possible interest to the IT Pro:

FromGlobalAccessCache – this static method tests an assembly to determine if it ewas loaded from the GAC.

GetRuntimeDirectory – this static method returns the folder name where the CLR was installed. This folder contains Ngen, the C# complier, and other .NET tools.

GetSystemVersion – this method returns the version number of the .NET Framework

 

From PowerShell Version 2, this looks like:

 

image

If you are using the beta version of PowerShell V3, you might see this:

image

File under: Interesting things you can do with .NET and PowerShell.

Wednesday, March 07, 2012

PowerShell Version 3–Updatable Help (continued)

In a recent blog article I discussed the new updatable help feature of PowerShell V3. In that post I described the Update-Help cmdlet and shows how you use that cmdlet to up date your help information. The Update-Help cmdlet knows how to go online to find, download and install updated help information for both the core PowerShell modules plus any additional modules on your system. The PowerShell V3 module feature enables Get-Help to know (or be told!) where to look for updated material for each module, and does what is needed!

But what if you are offline, or you are in an air-gap network, isolated from the Internet. Well, obviously, in that situation, Update-Help can not go online and get the necessary updates. But PowerShell does provide a cmdlet, Save-Help, that can get the necessary help information and can store it. You can then copy somewhere Update-Help can then find – in the case of an airgap network, you could copy the help information to a memory stick, then use sneaker-ware to copy that material onto the airgap network.  Let’s take a look at both these aspects.

To save the help files, you use Save-Help, specifying a destination path (where you want the files saved). Optionally, you can specify the UI culture for which you want to get updated help. Specifying the –Verbose switch provides more output describing what Save-Help is doing. By default, you can run Save-Help or Update-Help just once per day (per machine). To over ride this, use the –force parameter.

Here’s what Save-Help looks like in my Windows 7 workstation:

 

SNAGHTML1f74f896

As you can see from this screenshot, PowerShell gets the files and stores them in the path folder, which then looks like this:

SNAGHTML1f79c392

Each PowerShell module has the two files that make up the extensible help for that module:

  • An XML file – this identifies the UI version of the help content (found in the XML).
  • A cab file – containing updated MAML and about_* files. Each file in the cab file represents something to be moved (later) by update help.

Each pair of files is named using a simple naming convention of : <module name>_<module guid>_<ui culture>_<helpinfotype, where <helpinfotype> is either HelpContent (in which case the file has a .CAB extension), or HelpInfo (in which case the file has a .XML extension).

You will notice that when I got the help, Save-Help could not find help for the module TFL. That’s mainly because that help information has not yet been written and saved in EN-US locale (well, not yet anyway!). I will do another blog post at some point where I explain how to add updatable help to your module.

To install this help on the air-gap network or machine, or one you want to update offline, you first have to save the files to somewhere you can later access them from the network/machine. As I suggest above, a USB memory stick can be used to transport them (or CD, etc). Once you have the files moved to their appropriate place, you use Update-Help, specifying the SourcePath parameter and providing the path to where the help files are available. The update would look something like this:

SNAGHTML1f8d8193

The Update-Help cmdlet (when verbose is specified), displays the XML files parsed and whether or not the associated HelpInfo file was processed and the help files in the CAB file that have been moved to their appropriate location.

 

Technorati Tags: ,,

Pluralsight Course–Formatting with PowerShell

I’ve just finished creating my latest course for Pluralsight, entitled Formatting with PowerShell. The course looks at how you can get great output from PowerShell  - including both defaults and what you can do to improve your output.

Formatting, to my mind, is the art and science of presenting data to your target audience. Great looking output not only is easier to read and consume, but it often gives (possibly unearned) credibility!  PowerShell does a lot of things by default, making it the superior tool for the IT Pro. This course shows you how you can get the most out of what PowerShell provides by default, but also what you can do to over ride these defaults.

The course has 6 modules:

Module 1 – Introducing .ToString(). The core of PowerShell (and .NET) formatting is the .ToString() method. I regard the .ToString() method as the basis for all formatting in PowerShell, so it’s important to understand this .NET feature. The module looks as using .ToString to format numbers, dates, time spans and enums.

Module 2 – Composite Format Strings. This is a feature, leveraged from within .NET that I use a lot. We look at what makes up a composite format string and how to use the –f operator to format strings.

Module 3 – Formatting In the Pipeline. This module looks at how you can use the Format-* commands to format objects coming from the pipeline.

Module 4 – Using Hash Tables. Hash tables can be used to improve the output, particularly output generated by Format-Table and Format-List. We look at these hash tables and provide examples as to how they work.

Module 5 – Format Files and Display XML. Default formatting in PowerShell is based on format files and display XML. This module looks at how you can write your own format files, both to change default output and to create new views for your own, or existing, data types.

Module 6 – Other Output Mechanisms. This final module looks at the other ways you can data out of PowerShell, including using the Out-* cmdlets, CSV and CliXML for persisting objects and both HTML and Office document output.

Each module has demos, best practices and provides a great summary. The course material includes the slides and all the demos which you get depending on what level of Pluralsight membership you have.

The course is finished and is going through the production phase which shouldn’t take too long – I expect the course to be on the web site this week. I have to say, the guys at Pluralsight are pretty good not only about making sure the course is high quality, but that all the bits are where you want them! I’m impressed overall with their people and their process. They make me want to write more material for them!

And a call out to TechSmith (www.techsmith.com). The course is recorded using Techsmith’s Camtasia and the screen shots captured using Techsmith’s SnagIt product. I could not have recorded this course without these two great products. If you are developing presentation or training course material, you should be looking at these two products. Once you have them, you’ll fall in love with them!  Thanks TechSmith!!

Sunday, March 04, 2012

Invoking a PowerShell Command from within a program–How Do They DO That?

One of the aspects of the Monad Manifesto was its advocating building GUIs on top of PowerShell. For some devs and fewer IT Pros, the mechanism is pretty clear and straightforward. But for a lot, it’s a bit of a black art. In this article, I’ll look at how they do that, but I’ll demostrate by doing it in PowerShell (with a pointer to seeing it in C#).

Running PowerShell within your executable program (irrespective of it being a GUI or a console application), involves 3 objects:

  • Runspace – a runspace is the operating environment pipelines. A pipeline runs within a runspace.
  • Pipeline – a pipeline is used to invoke commands.
  • Command – a cmdlet or script that gets added to a pipeline to run in a run space

Each of these three objects are found within the System.Management.Automation.RunSpaces namespace and are pretty easy to create and manage. The descriptions of these objects in MSDN are a little thin in and could usefully be improved with more examples.

Here’s a script that illustrates this (analysis is below the script)

###
#   Create a PowerShell runspace and open it
$rs = [System.Management.Automation.Runspaces.RunspaceFactory]::CreateRunspace()
$rs.open()

#   Create a Pipeline
$Pipeline= $rs.CreatePipeline()

#   Create a command and add parameters
$cmd = New-Object system.management.automation.runspaces.command "Get-Process"
$cmd.Parameters.Add("Name", "Power*")

#   Add the first command to the Pipeline
$Pipeline.Commands.Add($cmd)

#   Invoke the pipeline
$collection = $pipeline.invoke()

#   See what's there
$collection
###

So what does this script do? Well first, it uses the runspace factory ( a feature built into .NET)  to create a new runspace on the local machine. Once created, the script opens the runspace for use.

Next we use the runspace object to create a new pipeline. We create a new  command object using New-Object. The command object is meant to run the  Get-Process  cmdlet and has a parameter (-Name) which for this run will have a value of ‘Power*’). 

After the command is added to the pipeline, the pipeline is invoked. Invoking the pipelines involves PowerShell, in effect, to run the Get-Process cmdlet with the appropriate parameters and return a result. That result, which is the same as you get running the command locally, is an array of objects that match the globbed name parameter (i.e. it would match PowerShell, PowerShell_ISE, PowerPoint, etc).

If you want the pipeline to have more than one command, that’s easy too. Suppose you wanted to support the output we obtained above? In other words, suppose you want to get the effect of “Get-Process –Name Power* | Sort-Object –Property CPU”? That’s easy. Just before invoking the pipeline above, just add the following:

#    Create a second command and add parameters
$cmd2 = new-object system.management.automation.runspaces.command "Sort-Object"
$cmd2.Parameters.Add("Property", "CPU")

#    Add the second command to the Pipeline
$pipeline.Commands.Add($cmd2)

It’s actually pretty easy, if you understand how to manage the three key objects involved. If you think about it, the sequence the script goes through is pretty much what PowerShell itself is doing when you are sitting at the console. The console is a little more complex, but most of the real magic is in the runspace itself and that is something the script and developers in general just leverage the feature.

An interesting aspect here is that all three objects are created using different approaches. The runspace is created by a static method on the runspace factory class, the pipeline was obtained by calling the runspace object’s method, CreatePipeline, and the command object(s) are created using New-Object.

So where might this be useful to an IT Pro. Probably not a lot of direct use – since PowerShell is doing all this for you (i.e. creating the run space, managing the pipeline and pipeline commands within, and marshal the output from the execution into something sensible at the console).  But I hope this might be of assistance to developers that are getting into PowerShell for the first time and want to integrate it into their applications.

Friday, March 02, 2012

PowerShell Version 3 Updatable Help Content

PowerShell has always had good in-box help. Each cmdlet has extensive documentation, complete with syntax and parameter details and plenty of good examples. As with all documentation, updating the help content has not been easy – or as easy as you might imagine.

With the decision to move PowerShell inside Windows, the help text has become almost read-only. If you think about the relative importance of changing help text post release, updates are not critical, so they don’t go out as part of the monthly update cycle. They don’t meet the bar for a Service Pack either. The bottom line for V2 in-box help text is that it’s effectively frozen till Win8 ships. The PowerShell team have partly worked around this by updating the on-line help, and giving the Get-Help cmdlet the ability to display, nearly seamlessly, the on-line help (i.e. use the –Online parameter to Get-Help).

For Version 3, PowerShell has updateable help content. To update your help text, you just type Update-Help and the cmdlet goes on-line and pulls down help not only for the core PowerShell cmdlets, but also for any module you have loaded on your system! That’s really cool!! This ships today with the new Version 3 update for earlier OSs and the new Win8 client/server beta.

As with many great features, there come some provisos and gotcha:

  • Help content is not installed by default. When you implement the MSU to add PowerShell 3 CTP to your older system or when you load Windows 8, there is only a bare skeleton of help information available. Much of this tells you to update your help. This decision is not going to change – you have to run Update-Help to update help. Microsoft may, I understand, consider doing some things via say Group Policy, but that’s not been confirmed.
  • UI Locale matters to Update-Help. Update-Help will look for help contents in the same language as your current locale. This is a problem for the Win8 beta since the number of languages supported by the beta is limited. I want en-GB content, based on my current locale, but there is none. There is, en-us, so I must specify explicitly the UI culture of the help I want to download.
  • You need admin rights to run Update-Help successfully. So use an elevated PowerShell prompt.
  • You need Internet access to get to the help information. You can, however, get the help content from the internet, place it somewhere, then use the –SourcePath or the –LIteralPath parameters to tell Update-Help where to find the Help source information.
  • Update-Help provides minimal output by default. Use the –Verbose parameter to Update-Help to see more of what’s going on.
  • Update-Help limits usage to once a day. By default, you cant’ update help more than once per day. This is to minimise the load on the MS servers providing this information. You and force Update-Help to run by specifing the –Force parameter to Update-Help.

WIth all this said here’s what Update-Help looks like on my system:

Before…

image

Updating Help:

image

And after…

image

In summary. PowerShell has updatable help and will use it moving forward. There are some small tricks to making it work for you, especially during the Win8 beta phase. But it’s a great feature and I love it already.

Thursday, March 01, 2012

PowerShell V3 Beta now available for down-level Operating Systems

Unless you’re in a cave deep in the moutains somewhere (in which case you won’t read this anyway!), you know that Microsoft has now released the first beta of Windows 8 client and server. Personally, I downloaded the server beta yesterday and am busy playing with it. Over the weekend, I will load it native on my laptop (brave man that I am).

One of the key features for me of both the server and client editions is the new beta of PowerShell V3. Microsoft has also poduced versions of the PowerShell beta for Vista/Server 2008 and Windows 7/Server 2008 R2. These contain all the same builtin cmdlets as you get with WIndows 8, without the addons only contained in WIndows 8. I am using this build now on my main workstations that are not yet running Windows 8.

You can get these beta builds at http://www.microsoft.com/download/en/details.aspx?id=28998. Note there are separate builds for the 2 OS sets and for 32 vs 64 bit systems. Be careful over which version you download.  And read the release notes carefully (when MS publishes them).

So far this new build continues the excellent work done in the past and is rock solid for me, albeit with a few areas where I think there’s more work that needs doing. Performance, for example, in a few places is not what it should be. And the debate over how help should be added into to box continues (I’ll document this issue in a blog post tomorrow). This all bodes very well for V3 being a great addition to the family!

So if you are using an older OS, consider downloading and using the latest PowerShell update. If nothing else, the new ISE is so good, it’s really worth it. Naturally, exercise due caution as this is a beta, etc. Having said that, it’s an excellent next step that I’ve put on all my key machines.