Command line shells / scripting languages

[#pshmshel]: Pash/“Monad Shell” (“MSH”)/PowerShell
Open Source options
Release by Microsoft

Microsoft has released PowerShell 6.0 as open source, using the “MIT License” (PowerShell's License), and is available for Linux (and Windows 8.1 / Server 2012 R2, and newer).

This is discussed by Jeffrey Snover and “Hey, Scripting Guy! Blog” “Open Source PowerShell – Part 1”.

Pash
...

This section has not been thoroughly reviewed yet. Proceed as if information here is still exploratory. A blog entry recommends Ryan Paul's guide (on Ars technica) to Monad Shell (which was later renamed to PowerShell).

If a downloaded script is not functioning because of code signing, review the online help that is referenced. Alternatively, there is an option to remove the restrictions. However, that does pose potential security concerns. The whole point of the restrictions is that Microsoft recommends that people do not run untrusted code. If a review of the code has deemed it safe, a workaround may be adjust the restrictions. The most flexible, lenient may come from running “ Set-ExecutionPolicy unrestricted ”. (Once the signing restrictions are no longer a problem, because signing has occurred or because restrictions have been lifted, then the script can be run.) For more details, run “ man about_signing ” (or equivilent: “ help about_signing ” or, as PowerShell recommends when trying to run a restricted script, “ get-help about_signing ”) and/or “ man Set-ExecutionPolicy ”. For some online documentation, see: Online documentation for PowerShell's Set-ExecutionPolicy.

Some Microsoft Products come with an icon that runs a specialized version of PowerShell. The following list is provided as examples (and, especially over time, may not be all-inclusive):

Microsoft Exchange Shell

Microsoft Exchange 2007 has an “Exchange Management Shell” which uses PowerShell. (At least if this version has a high enough service pack, it also has an “Exchange Management Console” which is a graphical interface, more similar to the “Exchange System Manager” from Microsoft Exchange 2003.)

Microsoft Download Center: Exchange Management Shell Quick Reference for Exchange 2010

Using Powershell with SharePoint

Microsoft SharePoint 2010 also contains a SharePoint shell. (This may not have been the first versions to contain the shell.

With SharePoint specifically, it may be advisable to run the shell as an Administrator so that all the needed commands work. (Perhaps they don't exist? Or maybe they just don't seem to find any data?

How to list all SharePoint 2010 PowerShell Commands. Briefly, they are:

Get-Command –PSSnapin "Microsoft.SharePoint.PowerShell" | format-table name > C:\SP2010_PowerShell_Commands.txt
If you would like a little more detail, then try this one:
Get-Command –PSSnapin "Microsoft.SharePoint.PowerShell" | select name, definition | format-list > C:\SP2010_PowerShell_Commands.txt
Note: You may also type gcm as the alias for Get-Command.

TechNet's Index of SharePoint Server 2010 Windows PowerShell cmdlets

(Note: This text may benefit from some further clean-up.) TechNet: SharePoint 2010 Products administration by using Windows PowerShell references using Add-PSSnapin (and %CommonProgramFiles%).

TechNet Magazine article: The 10 Things to Do First for Windows 7 has some info on PowerShell, such as mentioning that although PowerShell 2 comes with Windows Server 2008 R2, Exchnage servers using Exchange 2007 may require version 1.1 of PowerShell.

The commands to list other commands, mentioned in the SharePoint section, do seems interesting. Perhaps they may be adapted to show other commands that are specific to a program, like the commands available from Exchange Management Shell? Get-Command –PSSnapin

[#winscrho]: Windows Scripting Host
Name
Wikipedia's article on Windows Script Host: section about “Available scripting engines” says, “It was originally called Windows Scripting Host, but was renamed for the second release.”
Status

Google Groups forum post says, “WSH and the related COM based scripting engines/runtime are in 'sustained engineering' mode meaning only serious bugs (like security exposures or data corruption issues) are considered for bug fixes. No future releases are planned.”

A perfect example of this may be running a command line from Windows Scripting Host being at risk of crashing (in some cases, at least if a work-around is not implemented) being a critically stopping error, but not being expected to be fixed.

The section about VBScript in WSH provides some text from Microsoft staff that indicates a preferred successor.

[#wshengin]: Scripting Engines (Overview)

WSH is not exactly a scripting language, but rather a method to use scripting engines. Each scripting engine may support a programming language. To see a list of available scripting engines, see Wikipedia's article on Windows Script Host: section about “Available scripting engines”. (These scripting engines may be bundled with other products. Some might not be compatible with every platform that WSH has been supported on.)

However, WSH does supply a rather common set of objects. Many common tasks are implemented in WSH using objects. (Other languages may often implement those same tasks using called functions, instead of using WSH's objects.) The JavaScript and VBScript implementations for some tasks may involve using the exact same WSH object. The approach to interact with an object, such as creating an object, and other tasks like comparing variables, will follow the rules of the language being used. The language may determine the syntax for how information gets sent to an object. The object, however, determines what information needs to be sent. So, there may often be some strong similarities between JavaScript code in WSH and VBScript code in WSH, but the individual implementations also have their differences so that each language remains unique.

These objects may often be similar to Visual Basic, and hence online documentation about Visual Basic may often provide some solid clues about how these objects are designed to work.

WSH does support a file format called Windows Script File (which uses files that use the filespec of *.WSH) which allows multiple languages to be specified in a single file. Alternatively, some additional file extensions may be recognized as being associated with a specific language, in which case WSH may simply use the appropriate language.

(This topic is also discussed a bit by Using WSH //E: parameter.)

MSDN: Windows Script Interfaces provides some of the details for creating a scripting engine. The page states, “Windows Script engines can be developed for any language or run-time environment, including” Lisp, and some other languages. (However, that may just describing what is possible, and not anything that has actually been done yet. No support for Lisp was mentioned by Wikipedia's WSH article's section about “Available scripting engines”.)

Code samples

See the Windows Scripting Host section.

There is more information in the Windows Scripting Host section. (Check out that section if further details about WSH are desired.)

[#javascpt]: JavaScript

Information is available at TOOGAM's Software Archive: Page About Programming Languages: JavaScript section.

[#vbscript]: VBScript

Information is available at TOOGAM's Software Archive: Page About Programming Languages (section about VBScript) and a tad of information at Job Paths.

Language specifications

Information is available at TOOGAM's Software Archive: Page About Programming Languages (section about VBScript)

The following may also be helpful to pick this language up quickly.

Functions in VBScript
(The following may need formatting and/or CSS adjustments.)

Functions:
	Functions start with:
	Function fcnName(optional-comma-separated-list-of-variables
	Then they end with:
	End Function
	The return value involves using a variable that is named after the
	function.  This variable needs no declaration other than the line that
	starts defining the function.  So, if a function is named fcnName, then
	one may return a value by using:
	fcnName = retValue
	It can be nice to declare a value called retValue to store whatever gets
		returned.  Then, at the end of the function, set the real return
		value, using the above line of example code.  By doing this, if
		there becomes a cause to rename the function, this can be done
		by changing the name of the function, and the assignment at the
		end.  If there are multiple lines during the function that affect
		the return value, they won't all need to be changed as well.

		Perhaps an Execute statement could allow
sSelfFcnName to be defined at the top?

MSDN
page discussing VBScript's ability to execute code from memory (comparing to
JavaScript).

This guide doesn't have a strong indication of when to use parenthesis for
calling a function.  In some cases they are required, and in some cases they
need to not exist.  A factor may be whether a function is simply being called
on a line by itself, or whether a variable (in the code that calls the function)
is having its value set to whatever gets returned by the function call.

Optional parameters are not supported by VBScript.  There may be some different
approaches to dealing with that.
	http://www.4guysfromrolla.com/webtech/100301-1.shtml

Loops
Quite a few guides may suggest using DO...WHILE instead of WHILE...WEND. It seems there may have been some official guidance from Microsoft to recommend doing things the new way. Well, the WHILE...WEND code from BASIC works just as well, and can be more appropriate in many/most cases, so don't be afraid to use it.

The following is some further information which was figured out through experience, and which might not be part of the documentation that provides the official language specification.

Using explicit variables

It is recommended to place the following at the top of each file:

Option Explicit

Doing so can cause some problems, particularly when dealing with pre-existing code that did not follow this guideline. However, it can help help tremendously with some other problems that are more difficult to deal with, and so it is an especially great idea to use this for any new code. One such problem could be accidental code re-use. Another is thinking that a variable has one scope, when it really has another. That thinking could cause a fresh new variable to be used, when it is expected that the value of another variable is used.

This code might be able to executed within a function, but experience with WSH seems to indicate that an error occurs from setting the “Option” to “explicit” when the “Option” was already set to “Explicit”. This error does not seem to occur if one library file sets the option to explicit even if the option was already set in another file. So, once per file may be safer. (This has the side effect of also meaning that this option ends up being set for all of the functions in the file, which may often be good programming practice.)

Variable initializing

A variable cannot be given an initial value during initialization. However, declarations do not need to happen before executable code. Therefore, it may be a somewhat common practice to use a compound statement, which means a single line of text with multiple statements separated by a colon. e.g.:

Dim simpleCounter : simpleCounter = 0
File handling

This may differ for web browsing. The following guide is meant for WSH.

(This guide is currently insufficient; find another. This text is simply a placeholder. First, create an object.

Some documentation may refer to constant named values, like a value for the name ciForReading which is set to 1. Those values may not be part of the language specification, so define the names as needed (and make sure that the correct values then get passed to the needed functions). Technet: Visual Basic for Applications Reference: Visual Studio 6.0: OpenTextFile Method shows a value of ForAppending being set to 8, but then the example shows a value of ForAppending being set to 3.

Better techniques

There's a lot of bad code out there. There are some problems that, because they are so frequently being violated by a bunch of example code, are worth pointing out.

One is that a lot of code provides very minimal, and even non-existent, error-handling.

The other is leaving things unwrapped up. Much of the code may just leave files open, or objects set. That might function okay due to some garbage collection, but there is a case to be made to the benefits of old-school manual handling (which was more common when such manual handling was often more required). An explicit statement to free up an object's resources can free an object's resources and also help to clearly show that the object is no longer needed. That sort of coding style may improve readability, by being a bit self-documenting in nature. In the case of a tiny program, leaving a file opened may have no immediately noticed impact, but just leaving a file opened forever until the program exits can be unnecessarily inconsiderate. For instance, if a file is opened on a network share, it may be nice to stop using the remote fileserver when there is no longer any need for the file to be opened.

(Perhaps files are closed automatically when a filesystem object is set to Nothing? If so, that may help to explain why it seems that many files are not closed in many pieces of example code.)

Example code here could be nice. e.g., dealing with a file: error handling, and freeing up resources

Using a main function

Another great idea is to make a main (which might have a name like main or, to reduce the unlikely chance of a conflict with a function from another language, perhaps use a name like VBSmainFcn (which stands for VBScript main function).

In the C language, this was required, as the C compiler would run whatever code was in the main function. In VBScript, this is often not needed, as code may just be run globally when the file's code is being loaded. That may be great for small code run within a web browser, and less great for larger programs that involve structured code being loaded from a file. One bit of code that may make sense to run at a global value is a statement that helps to initialize a global variable. However, even that code may often be able to go into an initialization function which gets called from a main function. (In some cases, though, immediate initialization may just seem more sensible, perhaps so that people viewing the code can immediately see what value is intended.)

By placing code in a main function, the main function can easily be commented out. Or, its name may be changed to a new function name, if the initially intended program ends up later becoming code that is just a subset (a.k.a. a part of) a larger program. If manual indenting is needed, then causing this to be a function won't require manual indentation.

Then, somewhere (perhaps just after the main function), include a statement to call the main function. This globally executed code should probably do very little: perhaps just call the main function, get any return value, and quit. Or, instead of just quitting, pass the return value back to the operating system.

[#vbslibs]: Libraries in VBScript

Using libraries may be beneficial. (That statement could be expanded on, by describing some of the benefits.)

The method to load a library might vary based on how VBScript is being used: i.e. whether VBScript is used from WSH, or from Microsoft Internet Explorer (or perhaps some other method?). These different approaches are needed mainly for the simple reason that files may be accessed differently in a web browser compared to using VBScript in an environment such as WSH.

VBScript Libraries with WSH

(Information about the general topic of interacting with files in VBScript is discussed in the section about Windows Scripting Host.)

For VBScript within WSH, the following may work:

The language can be finessed into supporting external libraries using ExecuteGlobal.

Perhaps see: MSDN page discussing VBScript's ability to execute code from memory (comparing to JavaScript).

Thanks to Mark Alexander Bain's guide which helped show the basic concepts.

If you, as the reader, are looking for information about how to re-use code, then you might appreciate a simple re-usable example. Consider placing the following at the top of your main code file.

Note: This file has not currently been tested. A similar file had been known to work, but if there are typos/syntax errors/etc. in this file, they may still need to be corrected.
' Each file should have a comment describing what it does

Option Explicit
Function stdInitThisFile()
' version 0.11vb
' Home page for this code is at CyberPillar.com at
' dirsver/1/mainsite/techns/coding/scriptin/scriptin.htm#vbslibs

' Definining variable names (and setting values for constants)
const sSelfFcnName="stdInitThisFile"
const ciForReading=1 ' This const int value to be like
' the constant value that is documented at
' http://msdn.microsoft.com/en-us/library/6ee7s9w2.aspx
const sDefStdLibFileName = "stdlib.vbs"
Dim oFirstFSO
Dim oFirstFileObj
Dim sFirstImportedCode
Dim sStdLibFileName
Dim iRetValue

' Setting any additional initial values
sStdLibFileName = sDefStdLibFileName

' Load the standard library
Set oFirstFSO = CreateObject("Scripting.FileSystemObject")
On Error Resume Next ' e.g. file might not exist
oFirstFileObj = oFirstFSO.OpenTextFile(sStdLibFileName, ciForReading, false)
' .OpenTextFile parameters are documented by Microsoft at
' http://msdn.microsoft.com/en-us/library/314cz14s.aspx
' Third parameter value of false means to not create file.  (A setting of
'   true might make more sense when .OpenTextFile() is used to
'   open the file for writing.)
sFirstImportedCode = oFirstFileObj.ReadAll
oFirstFileObj.Close
Set oFirstFSO = Nothing
ExecuteGlobal sFirstImportedCode

' Run a standard initialization function that exists in that library
stdIniSeq()

' Exit this function
iRetValue = 0
Execute "" & sSelfFcnName & " = " iRetValue
End Function

Function mainFcn()
' This comment should explain what this function does

' Definining variable names (and setting values for constants)
const sSelfFcnName="mainFcn"
Dim iRetValue

' Load the standard library
stdInitThisFile()

' Check for arguments from the command line.
' (WScript.Arguments.Count definitely
' does equal WScript.Arguments.Length)
If ( WScript.Arguments.Count > 0 ) Then
' The first argument is WScript.Arguments.Item(0)
' The second argument is WScript.Arguments.Item(1)
End If

' Additional code goes here!



' Exit this function
iRetValue = 0
Execute "" & sSelfFcnName & " = " iRetValue
End Function

WScript.Quit mainFcn()

One thing to customize in all that is the referenced filename. The point of naming this function after the file is so that other files don't have duplicate function names.

Make a file called stdlib.vbs (or some other customized filename). Naturally, that file should start with a comment. Also, either make sure that file has a function called stdIniSeq or else change the relevant part of the example. Obviously, things may be more interesting if additional code is added to mainFcn().

That process of loading a file may be trimmed down further, as shown by Mark Alexander Bain's guide which does even less error checking, and fewer variables, simply using ExecuteGlobal on a line right after the FSO object is created. Better yet may be to include some additional error checking, like checking that VarType(sFirstImportedCode) is set to vbString, and has a non-zero length, and that it contains an expected marker (which may be tested by using InStr). If any of those things are not true, then it may be better to exit gracefully than to try running the ExecuteGlobal command, nor the stdIniSeq function (that is custom, and which apparently wasn't successfully imported).

Then, it would make sense if the standard library had code to be able to load another file. This way, other files can easily load more libraries with just a single line of text. The calling code can simply check for one simple return value, instead of needing to perform multiple checks.

Another thing that may make sense to put into the standard library are commonly used global variables, such as “ const ciForReading=1 ” (to match MSDN guide to Visual Basic 6: section on the OpenTextFile Method). Then that constant could even be used by the script that loads other text files.

Another thing may be declaring the definition variables like a global verbosity value. This is discussed in the section about including (debugging) output.

Revision History
version 0.11vb
  • Added version number.
  • Made other non-functional changes: changed comments, and changed the names of some const(s)/variable(s) to reflect data type (e.g., changed (from ForReading to ciForReading).
  • Replaced errorneous reference from “Set firstFileFSO = Nothing” to “Set oFirstFSO = Nothing”. This now cleans up memory as intended, rather than declaring a new variable. This is expected to not have any impact, in practice. However, it fixes a bug (making the code work as intended, and better).
version 0.10vb

First version posted to ][CyberPillar[]

(End of section about VBScript)
PERL

PERL has quite a bit of support for processing text, such supporting the usage of a “regular expression” (“RegEx”). At the time of of this writing, PERL 5 is also built into a number of Unix operating systems. See: PERL.