Coming across a nice article in MSDN about Extending Windows PowerShell With Custom Commands that I paste a short overview of it here :
There are some pretty significant differences between a Windows PowerShell cmdlet and commands in other standalone shell environments. For instance,
· a cmdlet is an instance of a Microsoft® .NET Framework class; it is not a standalone executable.
· Cmdlets generally output objects rather than text and should not format their output.
· A cmdlet processes its input objects from an object pipeline rather than from a stream of text.
· A cmdlet should not parse its own arguments and it should not specify a presentation for errors.
· Finally, cmdlets are record-oriented and generally process a single object at a time.
To declare a .NET class as a cmdlet, you attribute the class with the CmdletAttribute attribute (which is the only required attribute for any cmdlet). When you specify the CmdletAttribute attribute, you must specify a verb and noun name pair, which will be used as the name of the cmdlet. This should describe what the cmdlet does and what sort of resource the cmdlet works with.
To declare parameters for a cmdlet, you must first define the properties that represent the parameters. To inform the Windows PowerShell runtime that a property is a cmdlet parameter, you add a ParameterAttribute attribute to the property definition.
In order to use these new cmdlets, you need to add them to the Windows PowerShell environment. Windows powerShell has the ability to dynamically add cmdlets to the session via a snap-in. To avoid potential confusion with MMC snap-ins, a Windows PowerShell snap-in is called a PSSnapIn.
To create a PSSnapIn, you need to write a bit of code that will perform two tasks. First, it provides identification for your snap-in so it can be distinguished from other snap-ins installed on your system. Second, it provides information for properly installing the snap-in and for creating the appropriate registry entries to allow Windows PowerShell to find the assembly.