Specter targets the .NET CLI by creating specifications using the Boo programming language. The use of Boo's syntactic macro ability and extension methods allows for almost natural language specs, as seen in this example :

namespace Specter.Examples.Stack

import Specter.Framework

context "An empty stack":

	stack as Stack

	setup:
		stack = Stack()

	specify { stack.Push(42) }.Must.Not.Throw()

	# -- Long version
	# specify "Must complain when sent top":
	#	{ stack.Top }.Must.Throw(typeof(StackUnderflowException))
	# -- Shorthand version:
	specify { stack.Top }.Must.Throw(typeof(StackUnderflowException))

	specify { stack.Pop() }.Must.Throw(typeof(StackUnderflowException))

The spec is expanded by syntactic macros (context, setup, specify, subject, teardown) into a standard .NET class at compile time.

Specifications can be compiled in two modes :

Standalone mode

When compiled as an executable assembly, the spec will be a standalone runner you can execute to display results.

NUnit mode

When compiled as a library (dll), the spec can be run through existing NUnit tools (see below) as well as through the specter-console command.

When compiled as a library, NUnit attributes applied to the class and methods allow it to be "executed" within NUnit, just like any other test fixture. Therefore, you can reuse all your existing continuous integration tools. Go to the NUnit Integration page for more information.

The departure from using explicit classes and methods with attributes (like normal NUnit code) reduces the spec down to an almost pure form – effectively a simple domain specific language for specification. Also with the subject macro you can specify objects which are not implemented yet.

Compare:

[Test]
public void StackCountMustEqual42()
{
    Assert.AreEqual(42, stack.Count)
}

with just,

specify stack.Count.Must == 42

The specify macro can also extract a human readable string from the code, describing the specification! This means error messages reported by NUnit make sense to read, without having to write them yourself.

A key part of Specter is the Must extension method available on all .NET types. Must provides access to many different assertions you can make about your objects. Go to the Assertion features page to see what assertions Specter provides.

Writing the spec in Boo leaves you free to write your application code in any .NET language. This means you can write the spec with Specter and have it run against a C# or VB.NET application implementation, for example.