a reference application that has been designed from the ground up to scale to
the needs of medium-to-large business applications. It demonstrates a range of architectural
and design patterns, including repository patterns, Model-View-ViewModel (MVVM)
presentation style, view composition, multi-screen navigation, data-binding, reusable
UI components, validation, and multiple EntityManagers for sandbox editing and
reference app, we’ve kept TempHire manageable and limited its scope to
something that highlights our enterprise design decisions without too many
distractions. TempHire demonstrates a single Resource Management module in
action, but you can see how additional modules (Scheduling, Customer Management,
etc., etc.) could easily be built on its framework.
(line of business applications or LOBs) typically have task-oriented UIs and
complex, cross-functional, workflows. They need multiple views and require
considerable navigation. Given only a few screens, screen composition,
decomposition, and data-binding to complex data models can get out of hand in a
need to able to read, modify, and create data, so determining how to shuttle
data back and forth between the UI and the back-end becomes yet another
challenge. There’s a lot of tedious code involved in turning all that raw data
into business objects and moving them to and from the client.
Putting all of
the pieces together is enough of a challenge on traditional, relatively static,
desktop clients; but more and more frequently, product requirements demand that
these apps go cross-platform and work on desktops, tablets, and multiple mobile
How do you
design and write LOB apps that can handle real-world complexity? How do you
build apps that can be easily maintained and extended over multiple years? How
do you go cross-platform without hiring an army of developers to rewrite your
code for multiple clients?
designed to be a completely modular single-page application (SPA). It’s written
still be using tomorrow.
reduces complexity by leveraging frameworks like Durandal
for presentation and libraries like Breeze
for data management, so developers can focus on solving business problems rather
than the plumbing and wiring.
through the use of proven architecture and design patterns, multiple developers
can work independently on specific views, models, and workflows without
impacting other modules.
TempHire under the hood
is one way to do it—a way we’ve had success with and are happy to share with
(entities, and business logic) and various server side components (services,
DomainModel is the main model for all of the application
data. TempHire’s domain model contains all of its entity classes, an entity
base class, and a DbContext file.
at AddressType as an example of one of Temphire’s entity classes. It’s a Code
First class that has four properties.
uses a base class that all the entities, directly or indirectly, inherit from
(EntityBase.cs). The nice thing about Code First is that TempHire can add
common functionalities to the base class that will be applied to all of the
entities in the domain model. Because these functions are in the base class,
TempHire doesn’t need to add them to derived classes. Everything is
You can see
this in action by the way that TempHire handles concurrency checking. It’s
located in the base class and is inherited by every entity.
demonstrates how we map TempHire’s domain model to a database using
EntityFramework Code First. TempHire tells EF what its entitysets are, and sets
a few initialization strategies (e.g.
To be very clear, we’ve built TempHire as a demo app ... and in this context,
this makes sense. Don’t drop your database in a production application!
uses projections and DTOs where applicable to improve performance and to move
complex queries to the server, where implementing them in LINQ is a lot easier.
You can see this in action on the master details screen:
you’ll see grids like this populated by entities, but we don’t do that here. Instead,
this grid uses a projection query that cherry picks the information from an
object graph, condenses it, and sends it down the wire. Projections are a simple
way to enhance performance, and your customers who are connecting via an EDGE
network will be happy you did.
domain model behind us, let’s take a look inside the app itself.
The App folder contains the core components of the TempHire
client: Durandal, Client Services, ViewModel code, the HTML Views, and main.js,
the script that bundles the app’s scripts into a single package.
We’re assuming you’re familiar with the basics, so the most
interesting components here are likely App/Durandal and App/ Services.
Durandal, Rob Eisenberg’s excellent SPA framework, leverages
Knockout and Require. Durandal takes care of the front-end plumbing and makes
screen composition and management fast and easy. Even better, Durandal promotes
architecture practices that will positively impact scalability and long term
maintenance. Long story short, Durandal saves a ton of time and hassle in
regards to architecturally sound front-end development.
primary services … most of which revolve around Temphire’s reliance on the Unit
of Work (UOW) pattern.
Entitymangerprovider.js offers a CreateManager method for
TempHire to call whenever it needs a new EntityManager instance—something it
does frequently as each UOW must spin up a new EntityManager. Logger.js takes
care of TempHire’s logging functions, Repository.js is responsible for the
configuration of UOW Repositories, and Unitofwork.js is responsible for the
configuration of the UOW themselves.
App_Start contains BreezeWebApiConfig.cs, BundleConfig.cs,
and InfrastructureConfig.cs. These files run at the beginning of the server
launch sequence and register their applicable routes. BreezeWebApiConfig routes
Breeze client requests to the Breeze controller, and
registers the resource bundles via the
BundleConfig helper class. Additional
infrastructure configuration can be added here later.
All of TempHire’s content files (CSS and images) are stored
in the appropriately named Content folder. This is a good time to mention that
TempHire uses Twitter Bootstrap,
an excellent template for quickly standing up a modern front-end.
HTML, CSS, UI elements, responsivity—yeah, Bootstrap takes
care of all of that.
The default controller is responsible for delivering the common metadata. Query
and Save logic is to the respective module controllers.
The LookupBundle is a DTO used to ship global read-only entities such as lookup
data to the client in one shot. A client requests this data once at the
beginning and holds it in a global cache. Every
EntityManager when first
created is pre-seeded with this global lookup data.
ResourcMgtController defines the query and save endpoints for the resource
management module. Each module gets its own controller in order to keep their
size manageable and combine related functionality in one place.
Much as like we did client-side, the server-side also uses
the unit of work pattern to structure the query and save logic and keep it
external to the controllers. This way the controllers stay small enough and the
business logic is encapsulated in the corresponding server-side unit of work.
concerned by seeing so many libraries, please stop reading this article and read
to John Papa’s Why all
TempHire tick include:
adds front-end pizazz with a variety of widgets, transitions, buttons, etc. It
should go without saying that they all work seamlessly with the Twitter
Bootstrap CSS (See Content). The various GUI elements are documented at twitter.github.io.
excels at data management and takes care of the Model –the M in MVVM. Breeze
queries, saves, and manages all data interactions between client and server. Breeze
EntityManagers make writing TempHire’s Unit of Work patterns
(entities) that match the shape of the data coming from the remote service. It
adds business rules and infrastructure that support validation, change
tracking, and navigation to related entities. Breeze navigation properties
automate traversal of the object graphs that are implicit in a relational model
so you can walk the graph, from a customer to its orders, and from an order to
its line items. Breeze tracks users’ changes and validates them with rules,
some of which may have been propagated to the client from the server.
If you store data in a database, query and save data as
complex object graphs, and share graphs across multiple views—and want to do it
jQuery is a
dependency for some of TempHire’s libraries and templates. Bootstrap, Breeze, Durandal,
and Sammy rely on one bit of jQuery or another.
the data-binding and dependency tracking for the presentation layer—the ViewModel—the
VM in MVVM. Even better, it is intimately tied to Require and Sammy via the
Durandal framework, making much of the front-end wiring easier.
Moment is our
go-to library when working with date and time (parsing, validating,
assists in managing asynchronous operations through CommonJs promises.
Sammy is a small,
yet powerful, framework for building SPAs like TempHire. (Sammy refers to them
as single-page AJAX applications, but SPAJAX is a bit of a mouthful.) TempHire
uses Sammy primarily for its navigation and routing functionality.
displays process and error notifications in "toast" windows that
float up from the lower right to let you know what TempHire is doing at any
All of TempHire’s
persistence ignorance is built into the server-side services using Unit of Work
Unit of Work
The UOW is a
design pattern that encapsulates anything from simple tasks to complex workflows.
The UOW can be short or long lived, may involve retrieving data, modifying
data, creating new data, performing business logic, checking business rules,
and saving or rolling back changes.
is spun up for each UOW and takes care of the configuration, authentication,
and connection details, while the UOW’s Repository handles the business logic
that governs access to a specific type of entity.
UOWs make it
possible to highly optimize the fetching strategy for a given entity type.
i.e. A Repository
for a static type such as Color can be optimized to load all colors on
the first request and serve future requests directly from the cache instead of
making additional trips to the server.
UOWs can be
shared between ViewModels if different parts of the UI work with the same data,
but each UOW remains a unique sandbox.
uses UOWs as transaction boundaries—each with customized responsibilities that lead
to an organized codebase that’s easier to maintain and improve over time.
What about the back-end?
an ASP.NET Web Application. The server hosts all the client-side assets as well
as an ASP.NET MVC4 Web API service that queries and saves to a SQL Server
database with the help of an Entity Framework Code First model. We used ASP.NET
because it’s quick and effective for enterprise developers familiar with the
Microsoft stack. It’s also helpful that Breeze ships with components that ease
development of Web API and Entity Framework back-ends.
prefer a Rails or Java backend, or NoSQL database, you’re ok too. TempHire is a
can deliver web assets and data services.
to the TempHire sample, you can find more information about building SPAs at www.breezejs.com, including:
with your team to build a customized
training course that's tailored to the needs of your team and project.
actively developed by IdeaBlade. Follow @BreezeJS
on Twitter and Like us on