Revista CODE
Revista CODE
Revista CODE
NOV
DEC
codemag.com - THE LEADING INDEPENDENT DEVELOPER MAGAZINE - US $ 5.95 Can $ 8.95
2015
TABLE OF CONTENTS
Features
10 CRUD in HTML, JavaScript, and jQuery
Paul begins a new series on working within HTML and the Web API with
this close-up look at JavaScript and jQuery. Youll learn some of the juicy
details, but youll also get a good overview of what these technologies
can do for you.
Paul D. Sheriff
18
Legal Notes: Trade Secrets
Whats the difference between a trade secret and a patentable idea?
What about copyrighthow does that work into the equation?
John makes it all clear with a focus on trade secrets.
John V. Petersen
Sahil Malik
30
The Bakers Dozen: A 13-Question Pop Quiz of
SQL Server Items
If youve ever wondered how your SQL Server knowledge stacked up, youll want
to take Kevins unofficial test. He explains both the right and wrong answers,
so no matter what your skills are, youre bound to learn something new.
Kevin Goff
40
Building a Weather App using OpenWeatherMap
and AFNetworking
Take a look at third-party applications and code before sitting down to develop
because the tools you need to build your masterpiece might already be
available. Jason shows us some clever shortcuts as he builds a weather app.
Jason Bender
Bilal Haidar
Columns
8 Managers Corner: The Long View!
Take your company to the next level when you consider all of
a clients requests. No one can see the future, but its possible
that the unreasonable thing that your client asks for is your
best guess at how to grow your own business.
Mike Yeager
Departments
6 Editorial
17 Advertisers Index
73 Code Compilers
Jeffrey Palermo
Sponsored by:
US subscriptions are US $29.99 for one year. Subscriptions outside the US pay US $44.99. Payments should be made in US dollars drawn on a US bank. American Express,
MasterCard, Visa, and Discover credit cards are accepted. Bill me option is available only for US subscriptions. Back issues are available. For subscription information, send
e-mail to subscriptions@codemag.com or contact customer service at 832-717-4445 ext 028.
Subscribe online at codemag.com
CODE Component Developer Magazine (ISSN # 1547-5166) is published bimonthly by EPS Software Corporation, 6605 Cypresswood Drive, Suite 300, Spring, TX 77379 U.S.A.
POSTMASTER: Send address changes to CODE Component Developer Magazine, 6605 Cypresswood Drive, Suite 300, Spring, TX 77379 U.S.A.
Canadian Subscriptions: Canada Post Agreement Number 7178957. Send change address information and blocks of undeliverable copies to IBC, 7485 Bath Road, Mississauga,
ON L4T 4C1, Canada.
Table of Contents
codemag.com
ONLINE QUICK ID 00
EDITORIAL
A Psychopath Maintains
Your Code
For the last two issues, I spent time reflecting on various lessons and concepts that Ive learned in my
two and a half decades as a software developer. This editorial officially turns this duo of articles into
a trilogy. For this issues treatise on software development, Ill explore an infrequently discussed yet
ever-important topic: technology choice as it applies to application maintainability.
There is an old saying among software developers: Always code as if the person who ends up
maintaining your code is a violent psychopath
who knows where you live.
Over the last two months, Ive encountered two
codebases in which I wish I could take on the role
of psychopath and stalk the homes of the developers who created these monstrosities. Whats
my issue with these particular codebases? Two
words: over engineering. Each of these projects
had a rather simple set of requirements but were
so over-engineered that they were practically unmaintainable.
Lets talk about each project individually.
The first project had a rather simple set of requirements:
Read two types of comma-separated files
(CSV) found in a specified directory.
Read each row from the file.
Transform and attach lookup data to each
record processed.
Create an Excel output file from the transformed data.
That seems like a pretty simple set of requirements, right?
The codebase for this project was a conglomeration of new trinkets and shiny bobbles, aggregated into a Rube Goldberg set of steps in order to
complete what seemed a simple set of tasks. The
project used reactive extensions to throw events
when files were added to a folder, and for each
type of file it processed, it started a new multithreaded task. It also used an aggregation pattern to collect exceptions, and so on and so forth.
My major problem was that it took a simple process and convoluted/abstracted it into an eventdriven spaghetti monster. It made more sense to
rewrite it than to try and make modifications to
the code.
The second application was a Web portal for a
mobile application. It had another simple set of
requirements:
Editorial
In my initial statement, I said that I would cover technology choices as they apply to software maintainability. Hopefully, with the two examples provided,
you can see how two rather simple projects can become costly to understand (which is a pre-requisite
for maintainability) because the developers made
poor technological choices. Every time you choose
a particular set of tools, you need to consider the
long-term maintenance costs for that tool or set of
tools. Every new tool/technique increases the learning curve for the next developer (probably not you).
So my advice to you is: Keep your technology
footprint as small as possible (reduce the learning curve) and choose the right tool for the job
(just not the one you want to learn).
Rod Paddock
codemag.com
MANAGERS CORNER
Managers Corner:
The Long View
Nobody wants -inch drill bits, a marketing professor once told me. People want -inch holes.
Ill never forget those words. I use them as a reminder that I shouldnt be selling my customers what I
have, but providing them with what they need and want. A few years back, I lost a bid to a competitor
because the client wanted one-stop shopping.
It wasnt enough to develop a great website for
them. They wanted it built, hosted, monitored,
maintained, updated, and scaled. We didnt have
a data center and didnt want to get into the data
center business, so instead, I pitched a proposal
where we developed the software and theyd contract with a cloud provider for the hosting. It was
a less expensive option for the customer and gave
them full control, but it wasnt what they wanted.
They didnt just need a website, they needed a
broad solution and our competition did a better
job of delivering it. Looking back, it was shortsighted on my part and the loss of that contract
began shaping the approach to software development that I have today.
Today, we dont sell software; we sell long-term relationships to handle our clients system needs. Unlike software applications, these system needs dont
have a completion date. Once initial delivery of the
software is made, theres a new feature, a next project, a new requirement that needs to be addressed.
Businesses have to constantly adjust and evolve,
and so do their systems. The systems need to be
up and running and handle whatevers thrown at
them, and that requires proactive monitoring and
scaling. Delivering software to the cloud, usually
Microsoft Azure in our case, gave us the capabilities
we previously lacked. Hosting, monitoring, scaling, updates, and new features are all now part of
the products we offer. Its good for our customers
because theyre purchasing a solution where they
dont have to worry about all the care and feeding
of the solution, which frees them up to concentrate
on whatever they do best. Its good for us because
we have a steadier revenue stream, recurring revenue, and new sources of revenue.
These new capabilities have fundamentally
changed our understanding of what we do. Certainly, many new customers come to us looking
for us to write software, but thats becoming an
outdated notion. Upon further discussion with
our customers, the appeal of purchasing a solution including much more than software becomes
apparent. The idea of getting out of the IT business is appealing to more companies and, in addition to the shedding of some headaches, the savings it can offer is a powerful motivator.
SPONSORED SIDEBAR:
CODE Framework:
Free, Open Source,
and Fully Supported
CODE Framework is
completely free and open
source with no strings
attached. But that doesnt
mean that the framework is
unsupported! Contact us with
any questions; well never
charge you for answering
a few questions in email.
For those looking for more
sophisticated and handson support, we also offer
premium support options.
http://codeframework.
codeplex.com/
Mike Yeager
I wish that Id been pro-active in seeing and capitalizing on this trend, but as is often the case,
Managers Corner
codemag.com
Paul D. Sheriff
PSheriff@pdsa.com
www.PDSAServices.com
Paul D. Sheriff is the President
of PDSA, Inc. PDSA develops
custom business applications
specializing in Web and mobile
technologies. PDSA, founded
in 1991, has successfully
delivered advanced custom
application software to a wide
range of customers and diverse
industries. With a team of
dedicated experts, PDSA delivers cost-effective solutions,
on-time and on-budget, using
innovative tools and processes
to better manage todays complex and competitive environment. Paul is also a Pluralsight
author. Check out his videos at
http://www.pluralsight.com/
author/paul-sheriff.
Add a Product
The HTML page I use to illustrate these concepts is
shown in Listing 1. This HTML creates an empty table
with a <thead> for the headers of each column in the
table. There are three columns: product name, introduction date, and URL. Note that theres no <tbody> for this
table. Ive left the <tbody> element off on purpose to illustrate how you check for that in jQuery, and add the
<tbody> element, if necessary.
10
<thead>
<tr>
<th>Product Name</th>
<th>Introduction Date</th>
<th>URL</th>
</tr>
</thead>
</table>
</div>
</div>
</div>
codemag.com
Once the user adds the data in the input field, they click
on the Add button. In response to this click event, the
productUpdate() function is called, as shown in the following code snippet.
function productUpdate() {
if ($("#productname").val() != null &&
$("#productname").val() != '') {
// Add product to Table
productAddToTable();
// Clear form fields
formClear();
Figure 1: List products by adding rows to a table when the page loads.
// Focus to product name field
$("#productname").focus();
}
}
Delete a Product
Once youve added a few products, youll most likely need
to delete one or more of those products. Add a Delete
button to each row of the table, as shown in Figure 3.
This requires you to modify the <thead> element by adding a new <th> element with the word Delete, as shown
in the following snippet.
12
<table id="productTable"
class="table table-bordered
table-condensed table-striped">
<thead>
<tr>
<th>Product Name</th>
<th>Introduction Date</th>
codemag.com
"<td>http://bit.ly/1SNzc0i</td>" +
"</tr>"
);
$("#productTable tbody").append(
"<tr>" +
"<td>Build your own Bootstrap Business
Application Template in MVC</td>" +
"<td>1/29/2015</td>" +
"<td>http://bit.ly/1I8ZqZg</td>" +
"</tr>"
);
}
</script>
Listing 3: Retrieve values from input fields and build a row for a table
function productAddToTable() {
// First check if a <tbody> tag exists, add one if not
if ($("#productTable tbody").length == 0) {
$("#productTable").append("<tbody></tbody>");
}
"<tr>" +
"<td>" + $("#productname").val() + "</td>" +
"<td>" + $("#introdate").val() + "</td>" +
"<td>" + $("#url").val() + "</td>" +
"</tr>"
);
<th>URL</th>
<th>Delete</th>
</tr>
</thead>
</table>
Delete a Row
codemag.com
"<td>" +
"<button type='button' " +
"onclick='productDelete(this);' " +
"class='btn btn-default'>" +
"<span class='glyphicon
glyphicon-remove' />" +
"</button>" +
"</td>" +
"</tr>"
);
}
trol, you can use the jQuery function parents() to locate the buttons containing <tr> tag. Once you locate
the <tr> tag, use the remove() function to eliminate
that row from the table, as shown in the following code:
function productDelete(ctl) {
$(ctl).parents("tr").remove();
}
Edit a Product
Youve learned how to add and delete rows from an HTML
table. Now, turn your attention to editing rows in an
HTML table. Just like you added a Delete button to each
row in your table, add an Edit button as well (Figure 4).
Once more, you need to modify the <thead> element by
adding a new <th> element with the word Edit, as shown
in the following code snippet.
<table id="productTable"
class="table table-bordered
table-condensed table-striped">
13
<th>Delete</th>
</tr>
</thead>
</table>
<thead>
<tr>
<th>Edit</th>
<th>Product Name</th>
<th>Introduction Date</th>
<th>URL</th>
When the user clicks on the Edit button in the table, store
the current row of the table in a global variable. Define a
variable called _row within the <script> tag but outside
of any function, so its available to any function within
this page.
<script>
// Current product being edited
var _row = null;
</script>
Figure 3: Add a Delete button to allow a user to delete a row from the table.
Listing 5: Build an Edit button in JavaScript
function productBuildTableRow() {
var ret =
"<tr>" +
"<td>" +
"<button type='button' " +
"onclick='productDisplay(this);' " +
"class='btn btn-default'>" +
"<span class='glyphicon glyphicon-edit' />" +
"</button>" +
"</td>" +
"<td>" + $("#productname").val() + "</td>" +
"<td>" + $("#introdate").val() + "</td>" +
14
codemag.com
codemag.com
Figure 4: Add an Edit button to allow a user to edit a single row in the table.
client-side code. At some point, you are going to have to
send the data back to the server and retrieve data from it
as well. Most of us assign a primary key (unique number)
to each row of data. Lets now modify the page to use
data- attributes to keep track of primary keys on the rows
of data in the HTML page.
15
Listing 6: Use data- attributes to hold the primary key for each row
function productBuildTableRow(id) {
var ret =
"<tr>" +
"<td>" +
"<button type='button' " +
"onclick='productDisplay(this);' " +
"class='btn btn-default' " +
"data-id='" + id + "'>" +
"<span class='glyphicon glyphicon-edit' />" +
"</button>" +
"</td>" +
"<td>" + $("#productname").val() + "</td>" +
"<td>" + $("#introdate").val() + "</td>" +
Sample Code
You can download the sample
code for this article by visiting my
website at http://www.pdsa.com/
downloads. Select PDSA Articles,
then select Code Magazine
CRUD in HTML from the dropdown list.
You can delete the _row variable that you created earlier,
as youre now going to use these ID variables to keep
track of which row is being added or edited.
These two new variables are used to build the row to add
or update in your HTML table. Lets modify the productBuildTableRow() function (Listing 6) to accept a parameter called id to which you pass either of those two variables. This unique number is added into a data- attribute
on both the Edit and the Delete buttons.
Update a Row
When the user clicks on the updateButton, the productUpdate() function is still called. However, you need to
modify this function to use the _activeId variable and
pass that value to the productUpdateInTable() function
you wrote earlier.
function productUpdate() {
if ($("#updateButton").text() == "Update") {
productUpdateInTable(_activeId);
}
else {
productAddToTable();
}
// Clear form fields
formClear();
When the user clicks on the Edit button in the table, call
the productDisplay() function passing in the Edit button. Extract the data- attribute containing the unique ID
and assign it to the _activeId variable, as shown in the
following code.
function productDisplay(ctl) {
var row = $(ctl).parents("tr");
var cols = row.children("td");
_activeId = $($(cols[0]).
children("button")[0]).data("id");
$("#productname").val($(cols[1]).text());
$("#introdate").val($(cols[2]).text());
$("#url").val($(cols[3]).text());
// Change Update Button Text
$("#updateButton").text("Update");
}
// Add changed product to table
$(row).after(productBuildTableRow(id));
// Remove original product
$(row).remove();
16
...
_activeId = $($(cols[0]).
children("button")[0]).data("id");
codemag.com
replace that row in the table with the contents that the
user entered in the input fields on this form.
Each time you add a new row to the table, place the value
in the _nextId variable into the data- attributes for the
new row. Change the productAddToTable() function as
shown below.
function productAddToTable() {
// Does tbody tag exist? add one if not
if ($("#productTable tbody").length == 0) {
$("#productTable")
.append("<tbody></tbody>");
}
Paul D. Sheriff
SPONSORED SIDEBAR:
Need Help?
Looking to convert your
application to a new
language, or need help
optimizing your application?
The experts at CODE
Consulting are here to
help with your project
needs! From desktop to
mobile applications, CODE
developers have a plethora
of experience in developing
software and programs
for different platforms. For
more information visit www.
codemag.com/consulting or
email us at info@codemag.com.
Notice how you pass the _nextId variable to the productBuildTableRow() function. After this new product row is
created, increment the _nextId variable so that the next
product you add gets the next unique ID.
Summary
In this article, you learned to create Add, Edit, and Delete
rows in an HTML table using JavaScript and jQuery. Hav-
ADVERTISERS INDEX
Advertisers Index
/n software
www.nsoftware.com
www.1and1.com
11
www.apps-world.net
75
Aspose
www.aspose.com
CODE Consulting
www.codemag.com/consulting
21
CODE Divisions
www.codemag.com
76
CODE Framework
www.codemag.com/framework
31
CODE Staffing
www.codemag.com/staffing
69
dtSearch
www.dtSearch.com
47
http://ravendb.net
www.izenda.com
Izenda
LEAD Technologies
www.leadtools.com
38
SXSW Interactive
www.sxsw.com
59
Advertising Sales:
Tammy Ferguson
832-717-4445 ext 026
tammy@codemag.com
codemag.com
17
John V. Petersen
johnvpetersen@gmail.com
codebetter.com/johnpetersen
@johnvpetersen
John is a graduate of the Rutgers University School of Law
in Camden, NJ and has been
admitted to the courts of the
Commonwealth of Pennsylvania
and the state of New Jersey.
For over 20 years, John has
developed, architected, and
designed software for a variety
of companies and industries.
John is also a video course author for WintellectNOW. Johns
latest video series focuses on
legal topics for the technologist. You can learn more about
this series here: http://bit.ly/
WintellectNOW-Petersen. If you
are new to WintellectNOW, use
promo-code PETERSEN-14 to
get two weeks of free access.
18
codemag.com
The same goes for the Coca Cola formula. Often, companies require any visitor to their premises to sign an NDA
that forbids any disclosure of anything the visitor sees on
the premises. All of this may seem over-reaching and draconian. Nevertheless, these efforts have been regarded as
reasonable and necessary for the protected subject matter to be regarded as a trade secret.
Its all about legal standing and the Uniform Trade Secrets
Act (UTSA). The standard UTSA text can be found here:
http://www.uniformlaws.org/shared/docs/trade%20secrets/utsa_final_85.pdf. Statutes, whether they are state
or federal, enumerate both the law and the remedies a
plaintiff may be entitled to should they seek relief under
the statute. Before you can seek statutory relief, the statute must first apply. Whether a statute applies is a burden
for the plaintiff to carry. For example, lets assume you
have some process, method, or program that you regard
as a trade secret and you believe that somebody has misappropriated a trade secret. What damages are you entitled to? That depends in part on whether the UTSA, as
adopted by your state, applies. This is where we go back
to the three factor test outlined above.
Note: Most, but not all, states have adopted the UTSA.
New York, North Carolina, and Massachusetts havent
adopted the UTSA. Nevertheless, these states have laws
on the books that adopt much of the operative language.
Texas is the most recent state to adopt the UTSA; which
it did in 2013.
What if you are, or have the potential to be, a defendant
in a law suit? Inevitably, the other side, through a court
order, will demand that you produce certain documents,
including complete interrogatories, and perhaps submit
to a deposition. What if a portion of the information
sought is something you consider a trade secret? To prevent disclosure, the defendant bears the burden to establish that the information sought is a trade secret. What if
the action is around the information itself? For example,
what if the plaintiff alleges that the trade secret was misappropriated by the defendant? This presents an interesting situation because it would seem the defendant would
have no choice but to disclose the trade secret details as
well as information concerning how they developed the
secret. As it turns out, the answer here is not always clear.
First, trade secrets are a matter of state law. That means
that although each state may have adopted the UTSA, the
possibility always exists that from state to state, there
can be some variation, no matter how slight, over what
defines a trade secret. Second, each state has its own set
of court decisions (case law) that interprets its states
trade secret act. In the case of Pennsylvania, where I live,
in 2003, the Third Circuit Court of Appeals ruled that a
plaintiff bears the burden that the defendant did not independently develop the alleged misappropriated trade
secret. Does that mean the defendant doesnt have any
burden? The answer is no, but the burden that the defendant carries is light. All the defendant has to produce is
some evidence that the trade secret was independently
developed. Once that burden is carried, the burden then
shifts to the plaintiff. For more information on the Moore
v. Kulicke Soffa Industries, Inc. case (a good example of
this burden-carrying), see http://caselaw.findlaw.com/
us-3rd-circuit/1361597.html.
codemag.com
19
Summary
It should be fairly apparent now that trade secrets are an
important aspect of intellectual property law and business. If you think you have one, the burden is on you to
protect it. Things like NDAs and employment agreements
are reasonable measures to help protect such information, processes, and methods. At the same time, you also
should take practical measures to control access as to
who has direct contact and knowledge of these secrets.
Be sure to consult your locality, whether thats your
states or countrys laws around trade secret protections.
In the USA, although there is the Uniform Trade Secrets
Act (UTSA), theres currently no standard trade secret enforcement. The UTSA is simply a model template.
20
Whats next?
John V. Petersen
codemag.com
codemag.com
Title article
21
NameMalik
Sahil
Autor
www.winsmarts.com
www.internet.com
@sahilmalik
asdfasdfasdfasdfker, a .NET
Sahil
Malik
is a Microsoft
MVP,
author,
consultant
and trainer.
INETA speaker, a .NET author,
Sahilasfasdfasdfasdfasdfasdfdconsultant,
and trainer.
fainings are full of humor and
Sahil
loves
interacting
withfind
felpractical
nuggets.
You can
low
realtrainings
time. Hisattalks
moregeeks
aboutinhis
and
trainings are full of humor
http://wwasdfasdfasfasdfasdf
and practical nuggets. You can
find more about his training at
http://www.winsmarts.com/
training.aspx.
His areas of expertise are crossplatform mobile app development, Microsoft anything, and
security and identity.
A Superset of JavaScript
TypeScript is a superset of JavaScript. This means that
introducing TypeScript to your current JavaScript code is
easyjust rename the .js file to .ts, and youre good to go.
Of course, by simply renaming a file you, dont get the full
power of TypeScript. But by simply renaming the file to .ts
and continuing to write JavaScript like youve always done,
you begin to start getting some of the advantages of Typescript. These advantages are, of course, dependent upon
the IDE you use, but for the purposes of this article, Ill talk
about Visual Studio 2015 or Visual Studio code.
For instance, consider the very simple add function, as
shown below,
function add(a, b) {
return a + b;
}
As you can tell, this is plain JavaScript. Because you renamed the file to .ts, the IDE begins to understand the
code better, and allows you to refactor the code easily.
Just right click on the add text, and youll see a menu,
as shown in Figure 1.
You can easily rename a variable or function name. You can
also peek or go to the definition. You can find all references. In other words, you have the power of a higher-level
language, such as C#. If this were plain JavaScript, youd
be stuck doing error-prone string replacement. Try out the
same code in a JavaScript file for a trip back to the 1990s.
Additionally, the IDE also warns you if youre not passing in the parameters properly. For instance, if your add
function expects two parameters but youre accidentally
passing in only one, you get a nice red squiggly line, as
shown in Figure 2.
Not only that, the IDE is able to judge the variable types, even
if you dont specify their data types. In doing so, itll then help
you avoid common mistakes that are otherwise syntactically
perfect JavaScript code. This can be seen in Figure 3.
Static Typing
22
codemag.com
This way, you can use the features of ES6 today and write
reliable code right now.
There are many other examples. I suggest visiting http://
es6-features.org/ and checking out everything ES6 offers.
Many of those offerings are usable today in JavaScript. As
a simple example, let me pick just one of those features,
called Arrow Functions. Arrow Functions is a shorthand
for writing full functions, much like Lambda expressions
in C#.
For instance, examine the code below that is ES6 code,
but that can be written in a TypeScript file:
var odds = evens.map(v => v + 1);
codemag.com
23
faces today. Each example is better than the next. Ill let
you try them in ES6 in your own time. Before I leave this
topic, though, let me show one other example.
The above is ES6 code, but the let keyword ensures that
the inner i variable in the for loop doesnt interfere with
the same-named variable outside the loop. TypeScript allows you to write exactly the same code, and run it and
take advantage of it in browsers that dont support ES6
yet. TypeScript converts the above code into the following:
var i = 10;
for (var i_1 = 1; i_1 < 10; i_1++) {
}
IntelliSense
IntelliSense is a big deal. Ive touched upon this in the Static Typing section above. It gets even better! You could write
interfaces or classes, for instance, as shown here:
interface animal {
animalName: string;
}
24
codemag.com
rich intelliSense, making your code a lot more meaningful, as can be seen in Figure 8.
You can see how powerful this can be, especially when
authoring large libraries and complex interdependent JavaScript/TypeScript code. It gets even better than that.
Much better!
These days, you almost never write JavaScript from
scratch. You always stand on someone elses shoulders
by using libraries and frameworks, such as jQuery and
AngularJS. For nearly every library you care about, the
community has written .d.ts or definitely typed files, that
give you IntelliSense for those third-party libraries.
For instance, for AngularJS, Id simply add a line at the
top of my code as shown here:
codemag.com
25
SPONSORED SIDEBAR:
HTML Mentoring
Need help with an HTML
project? CODE Consultings
special introductory offer
gives you full access to a
CODE team member for 20
hours to receive assistance
for your project needs.
Mentoring and project
roadblock resolutions with
CODEs guidance are a perfect
partnership. And now, CODE
Consultings Introductory
Packages are only $1,500thats
half price! Email info@codemag.
com to set up your time with a
CODE specialist, today!
Object-Oriented Features
Okay, raiseYourHand(); if you: ILikeObjectOrientedCode. I thought so!
JavaScript isnt object oriented. Its weird-oriented. It
likes prototypes, which are sort of like object-oriented
and inheritance, but not quite. In fact, prototypal inheritance is confusing. If youre a top notch OO developer,
prototypal inheritance actually makes it difficult for you
to understand whats going in.
TypeScript solves that problem too. It brings concepts
such as inheritance, interfaces, classes, etc. into JavaScript in the manner in which youd expect them to behave. For instance, consider this code:
interface foodItem {
foodName: string;
calories?: number;
}
It simply declares an interface, which says that the object implementing this interface must have a required
property of type string called foodName, and an optional
number property called calories.
26
interface newFoodItem {
(foodName: string, calories: number): foodItem;
}
codemag.com
There are a number of interesting concepts in play in Listing 1. Ive defined a function that implements an interface.
Additionally, the array is guaranteed to have only variables
matching a certain predefined data type. This means that you
dont have to do onerous typechecking or null and undefined
checks. You could, of course, take this further and create a
single interface thats both a function and has properties
of the function. Just imagine how difficult or error prone it
would be to achieve the same in plain old JavaScript!
Now pause and think for a moment: How would you implement all that stuff in the preceding paragraph in plain JavaScript? Im serious, stop reading, and think through how you
would implement this in JavaScript. Its complicated, isnt
it? Im sure youre thinking in terms of prototypes, returning
various properties of prototypes, all cleverly placed to mimic
class properties. Youre probably also thinking of how you
would implement static variables. Its doable, but not easy!
Modules
Modularizing code is yet another important code organization tool I like to use. Modularization is important
because it lets you split your code into multiple files, and
else {
return this.newSound;
}
}
}
var dog: Animal = new Animal();
dog.makeSound();
// Woof
var cat: Animal = new Animal("cat", "meeow");
cat.makeSound();
// meeow
codemag.com
return this.newSound;
}
};
Animal.standardSound = "Woof";
return Animal;
})();
var WildAnimal = (function (_super) {
__extends(WildAnimal, _super);
function WildAnimal() {
_super.apply(this, arguments);
}
return WildAnimal;
})(Animal);
var dog = new Animal();
dog.makeSound(); // Woof
var cat = new Animal("cat", "meeow");
cat.makeSound(); // meeow
27
add(1, 2);
// returns 3
add(1, 2, 3);
// returns 6
add(1, 2, 3, 4, 5); // returns 16
You can therefore conditionally load modules by surrounding this import statement inside if blocks. You cant
do that in compiled languages.
Function Parameters
Ive touched upon the power that TypeScript brings to
function parameters earlier in this article but it deserves
its own section. Earlier in this article, I mentioned a simple add function that adds two numbers. Id mentioned it
because theyre statically typed: you cant pass in strings.
28
What if I did want to pass in strings, and get a concatenated string back?
Summary
JavaScript sucksI think Ive made that abundantly clear.
Also, you cant avoid JavaScriptI think Ive made that
abundantly clear as well. Writing complex and reliable JavaScript is possible. In this article, I showed that the first
step to this promised land is by using TypeScript.
As amazing as TypeScript is, theres one big disadvantage:
It needs to be transpiled. In other words, the code you
write isnt the code that runs. You write some code, it
gets converted into JavaScript, and that generated JavaScript runs in the browser. This introduces some friction, especially while debugging. It requires you to set
up your development environment considering how and
when the TypeScript code gets transpiled into JavaScript.
Certainly, you dont want this transpilation to happen on
the fly in production. These transpiled files are built and
shipped ahead of time. This makes TypeScript perhaps not
as flexible as JavaScript. Not to mention that hitting a
breakpoint in TypeScript requires complex workarounds
such as sourcemaps. And lets be honest, not all browsers
understand all of that.
Still, given the huge advantages that TypeScript brings,
this is a minor downside that I would gladly overlook. In
fact, Id go as far as saying: TypeScript is the best way of
writing JavaScript today.
Also, because TypeScript is a superset of JavaScript,
theres really no reason not to write TypeScript. In my
next article, Ill talk about another fundamental building
block of good JavaScript, which is MVC, Angular, TDD etc.
TypeScript is the best way to write Angular 2 code. In fact,
the alternative of writing it in plain JavaScript is so bad,
Id argue that its the only way to write Angular 2 code.
That and more in my next article. Until then, happy coding!
Sahil Malik
codemag.com
codemag.com
Title article
29
After roughly ten years and roughly 50 Bakers Dozen articles, Ive decided that its time to shake it up a little.
For now and (at least) the immediate future, Im going
to present 13 test-style questions (or scenarios) on database topics, and see how readers do with the questions.
Even if youre not specifically looking for ideas for test
questions, the example questions might help you with
various database programming tasks.
30
1: Scalar Variables
Example B
DECLARE @CompanyNameString varchar(100)
SET @CompanyNameString =
(SELECT CompanyName FROM ControlTable )
SELECT @CompanyNameString
codemag.com
some test data. The data stores two vendors in the master table and two orders in the order table (one for each vendor).
By default in SQL Server, what does SQL Server store for the two
variables after the code executes? (Select only one answer.)
a. One row
b. Two rows
c. Zero rows
d. The query generates an error message.
Suppose you create the following test table, which contains an identity column that SQL Server generates. You
insert a row into the table.
CREATE TABLE dbo.TestTable1
(IdentityKey int identity, Name varchar(100))
INSERT INTO dbo.TestTable1 values ('Kevin')
Suppose you create a basic Vendor Master table and a related Order table, with orders for vendors. Heres the DDL and
codemag.com
Youd like to know and capture what SQL Server generated as an identity value for the INSERT, regardless of
any other processes. You use both the SCOPE_IDENTITY()
function and the @@IDENTITY system global variable.
SELECT SCOPE_IDENTITY()
SELECT @@IDENTITY
31
How many rows does this query return? (Select only one
answer.)
a. Four rows
b. Six rows
c. Seven rows
d. Zero rows
e. The query generates an error message.
Figure 2: The first eight rows of the Purchasing.Vendor table
the desired value of 1 and the other returns something
other than a value of 1.
Suppose you create a table with the following DDL structure, including an identity column:
CREATE TABLE dbo.TestIdentity
(IdentityValue int identity,
IdentityName varchar(100))
Now suppose you insert two rows into the table. If you
query the table after executing the inserts, you clearly
see the values of 1 and 2 for the identity values.
SELECT FactInternetSales.ProductKey,
SUM(FactInternetSales.SalesAmount) AS AnnualSales
FROM FactInternetSales
JOIN DimDate on ShipDateKey = DateKey
WHERE DimDate.CalendarYear = @YearToRun
GROUP BY FactInternetSales.ProductKey
ORDER BY FactInternetSales.ProductKey
Suppose you query the Purchasing.Vendor table in AdventureWorks. The first eight rows (in Name order) look like
Figure 2:
Suppose you want to retrieve all rows where the vendor
name begins with the word American. You execute the
following lines of code that uses the LIKE statement and
the wild card character (%) at the end of the lookup value.
DECLARE @TestValue varchar
SET @TestValue = 'American%'
select * from Purchasing.Vendor
where name like @TestValue
32
You want to retrieve the products that dont exist in the fact
table. Assume that the Product Key in the fact table permits
null values. You write two different queries: one uses NOT
EXISTS and the other uses NOT IN. Which of the two queries
codemag.com
Select all statements that are true about database indexes in SQL Server. (There can be more than one correct
statement.)
a. A SQL Server table can have many non-clustered
indexes, but cannot have more than one clustered
index.
b. A SQL Server table can have many clustered indexes,
but cannot have more than one non-clustered index.
c. The only way to establish uniqueness in a SQL Server
table for a specific column is to define the column as
a Primary Key.
d. A column for a clustered index can be a different column than the column you define as the Primary Key.
e. Non-clustered indexes can also include non-key columns to optimize queries that frequently retrieve
those columns in addition to the key columns.
Take special note that the Product dimension table contains columns for an effective date and an expiration date.
The requirement here is to preserve historical changes in
the table, for historical reporting purposes. For instance,
a product might sell at $49.95 for a year, and then might
see a price increase the following year. Analysts might
want to report on sales under the old price as well as
the new one. In the data warehouse, you store each version as a separate row with a separate surrogate key. You
use the surrogate key in effect at the time of the sales
transaction when you post sales to the fact table. This is
known in the data warehousing world as a Type 2 Slowly
Changing Dimension. (In a Type 1 scenario, you dont
care about preserving history).
OK, now populate some data. Start with an INSERT of one
product, when the company first introduces the product.
INSERT INTO dbo.OLTPproduct
VALUES ('ABCDE', 'USB 64 GB Thumb Drive',
49.95, CAST( '7-1-2015' AS DATE))
codemag.com
33
Youd like to use the When Matched clause when you encounter a row in the source that matches a row in the target (based on the ProductKey), and then perform both an
update and an insert to the product dimension. However,
the MERGE statement doesnt allow you to perform both
an UPDATE of the old row (to retire the old version) and
an INSERT of the new version of the product row (with the
new price). SQL Server only allows one DML statement for
the WHEN MATCHED condition.
So heres the question: Is there some way you can still use
the MERGE statement to retire the old version of the row
AND insert a new version of the row when you detect a price
change? Or do you need to look at another approach?
34
codemag.com
codemag.com
table with an identity column by piping in a SELECT statement that returns multiple rows? As you saw in the Scalar
Variables question, you cant redirect multiple rows into
a single scalar value, and both SCOPE_IDENTITY() and
@@IDENTITY return single scalar values. So how would
you determine all the identity values in that situation?
Fortunately, Microsoft addressed this situation back in
SQL Server 2005 with the OUTPUT statement. You can
capture/redirect all of the identity values that SQL Server
generates on multi-row INSERT (or for that matter, any
and all columns from the inserted table) by using OUTPUT
as follows:
CREATE TABLE dbo.IdentityTest
(IdentityValue int identity,
Name varchar(100))
GO
INSERT INTO dbo.IdentityTest (Name)
OUTPUT Inserted.IdentityValue
VALUES ('Kevin
Writing Tests
'), ('Steven')
-- This will return 1 and 2
35
Some developers make this mistake with Date and DateTime values as well. Suppose, in this example, the OrderDate column stored DateTime values, and the table contained rows with an order date of 1-31-2010 at 2 PM. In
this example, SQL Server implicitly casts the value of 131-2010 as 2010-01-31 00:00:00.000, which means
that the query wont pick up orders throughout the day
on 1-31-2010. In other words, the query wont return any
rows beyond midnight for the ending date range.
SELECT * FROM Purchasing.PurchaseOrderHeader
WHERE OrderDate BETWEEN '1-1-2010'
AND '1-31-2010'
-- If OrderDate is a datetime, this won't return
-- a value of 1/31/2010 at 2 PM
The moral of the story here is to be careful using BETWEEN, especially when you specify values that represent
some subset of the values that SQL Server is storing.
For the IDENTITY Values and Uniqueness question (question 8), the answer is no. Actually, its emphatically NO!
An IDENTITY column by itself will not guarantee uniqueness. A DBA or developer can turn off identity value generation and manually insert a row, even one for a duplicate
value. Granted, it would be wrong to do so, but the point is
that SQL Server wont constrain a column as unique simply
because you designated the column as an identity column.
SET IDENTITY_INSERT dbo.TestIdentity ON
INSERT INTO DBO.TESTIDENTITY
(IdentityValue, IdentityName)
For the NOT IN vs NOT EXISTS and Performance question (question 10)-over the years, theres been substantial debate about using EXISTS vs IN, and NOT EXISTS vs
NOT IN. Some argue that EXISTS provides more flexibility
when dealing with a check on multiple columns, whereas
others argue that IN is simpler if the query is only checking for an intersection with one value. Some argue that
36
SELECT @ColumnValue =
replace( @ColumnValue,
POValues.OldPOValue,
POValues.NewPOValue)
from @POValues POValues
RETURN @ColumnValue
end
GO
UPDATE SomeTable SET AddrLine =
[dbo].[ReplacePOBox] (AddrLine)
codemag.com
(
MERGE dbo.DimProduct Targ
USING dbo.OLTPProduct Src
ON Src.ProductSKU = Targ.ProductSKU
WHEN NOT Matched
THEN INSERT (ProductSKU, ProductName,
ProductPrice, CurrentFlag,
codemag.com
Final Thoughts
Kevin S. Goff
37
Jason Bender
Jason.bender@rocksaucestudios.com
www.jasonbender.me
www.twitter.com/TheCodeBender
OpenWeatherMap (openweathermap.org) is a publicaccess weather API that serves over a billion forecast
requests per day. Powered by the OWM platform, OpenWeatherMap provides a variety of weather details for over
200,000 cities worldwide using data from over 40,000
weather stations. Using this API, developers can easily
access current weather information, hour-by-hour forecasts, or even daily forecasts up to 16 days in advance.
The service offers flexibility as well, allowing responses to
be retrieved in XML, JSON, or HTML.
For the purposes of this demonstration, youll work with
the current weather and weekly seven-day forecast using
JSON as the response type. You can access the documentation for the various API endpoints offered, including
ones not covered in this article, at http://openweathermap.org/api.
The Endpoints
OpenWeatherMap provides
a variety of weather details
for over 200,000 cities
worldwide using data from
over 40,000 weather stations
API Usage
40
The base URL to get the future weather forecast for a set
amount of days, and a set location, looks like this:
http://api.openweathermap.org/data/2.5/
forecast/daily
Furthermore, when calling forecast/daily, you can request a specific number of days to get a forecast for. In
this demo, youll ask for seven days worth of data by ap-
codemag.com
The Data
Once one of the forecast requests is sent, the service responds with the corresponding information. The default
response type is JSON, but you can opt to receive information in XML or HTML, depending on your needs. Lets
take a look at the response format for the two calls previously explained. Listing 1 shows a sample JSON response
object from the call to get current weather for Cairns, AU,
and Listing 2 shows the response format of a daily forecast call for Shuzenji, JP.
The default metric for numerical values from the API,
and also the metric used in the sample responses shown
in Listing 1 and 2, is Kelvin. You can format the call to
the API to return data in Imperial (Fahrenheit) or Metric
Figure 1: Initial project settings when creating the sample project in Xcode
Listing 1: JSON response for current weather info from OpenWeatherMap
{
"coord":{ "lon":145.77, "lat":-16.92},
"weather":[{
"id":803,
"main":"Clouds",
"description":"broken clouds",
"icon":"04n"
}],
"base":"cmc stations"
"main": {
"temp":293.25,
"pressure":1019,
"humidity":83,
"temp_min":289.82,
"temp_max":295.37
},
"wind::{
codemag.com
"speed":5.1,
"deg":150
},
"clouds":{"all":75},
"rain":{"3h":3},
"dt":1435658272,
"sys":{
"type":1,
"id":8166,
"message":0.0166,
"country":"AU",
"sunrise":1435610796,
"sunset":1435650870},
"id":2172797,
"name":"Cairns",
"code":200
}
41
"min":293.52,
"max":297.77,
"night":293.52,
"eve":297.77,
"morn":297.77
"code":"200",
"message":0.0032,
"city":{
"id":1851632,
"name": "Shuzenji",
"coord":{
"lon":138.933334,
"lat":34.966671
},
"country":"JP"
},
"cnt":10,
"list":[{
"dt":1406080800,
"temp":{
"day":297.77,
},
"pressure":925.04,
"humidity":76,
"weather":[{
"id":803,
"main":"Clouds",
"description":"broken clouds",
"icon":"04d"
}],
}]
}
@end
(Celsius) as well. Date and time stamps use the UNIX epoch format (the number of seconds elapsed since January 1, 1970). In this example, youll convert those times
to the devices local time zone and store them as NSDate
objects. Notice that the weather component of each response has an id and an icon field. The ID is unique to
each specific weather condition in the system and the
icon coordinates to a graphical representation of the
corresponding condition. In Listing 1, for example, the
icon field maps to a value of 04n. Using the URL format provided in the documentation, you can access an
image icon representing the current weather condition
at http://openweathermap.org/img/w/04n.png. Further documentation on all weather conditions and icon
mappings can be found at http://openweathermap.org/
weather-conditions.
The list array in Listing 2 is the most noticeable difference between the two response formats. That list
contains an entry for each day of the forecast. In this
example, youll ask for a seven-day forecast, so that list
array has seven entries, whereas Listing 1 only shows
detailed information for the current date and time.
AFNetworking
AFNetworking is an open-source networking library for
iOS and Mac OSX. Its built atop the URL Loading System
42
found in the Foundation framework and offers a featurerich API that includes many useful features such as serialization, support for reachability, and various UIKit
integrations. Its currently one of the most widely used
open-source iOS projects with nearly 20k stars, 6k forks,
and 240+ contributors on Github (https://github.com/
AFNetworking/AFNetworking).
AFNetworking is currently
one of the most widely used
open-source iOS projects with
nearly 20k stars, 6k forks, and
240+ contributors on Github.
codemag.com
Lets Code It
Getting Started
Once saved, launch terminal and navigate to the root folder for your project. Make sure that the project is closed in
Xcode and run the following command in terminal:
pod install
} else {
// handle no results
}
} failure:^(AFHTTPRequestOperation*
operation, NSError *error) {
// handle error
}
AFHTTPRequestOperationManager *manager =
[AFHTTPRequestOperationManager manager];
[manager GET:URL parameters:nil success:
^(AFHTTPRequestOperation* operation, id responseObject) {
if (responseObject) {
completionBlock(responseObject);
];
}
Figure 2: Settings when creating the weather object model to store weather data
codemag.com
43
strate how to interface with the API. You can follow the
same structure to store any of the remaining data points
that arent used in this sample.
Weather Model
The next step involves creating the radar class that gathers the information needed to populate this weather
object. That radar class retrieves the weather data as a
JSON object. Once you code that (in the next section),
youll loop back and create an initializer method on this
Using CocoaPods
The official CocoaPods website
can be found at http://
cocoapods.org/.
Additionally a comprehensive
tutorial on how to use CocoaPods
can be found at http://www.
raywenderlich.com/64546/
introduction-to-cocoapods-2.
Figure 3: The sample application using the weather library from this article
Listing 5: WeatherRadar.hdeclare weather radar functions headers
/**
* Returns weekly forecasted weather conditions
* for the specified lat/long
*
* @param latitude
Location latitude
* @param longitude
Location longitude
* @param completionBlock Array of weather results
*/
- (void)getWeeklyWeather:(float)latitude longitude:(float)longitude
completionBlock:(void (^)(NSArray *))completionBlock;
44
/**
* Returns realtime weather conditions
* for the specified lat/long
*
* @param latitude
Location latitude
* @param longitude
Location longitude
* @param completionBlock Weather object
*/
- (void)getCurrentWeather:(float)latitude longitude:(float)longitude
completionBlock:(void (^)(Weather *))completionBlock;
codemag.com
initWithDictionary:weather isCurrentWeather:FALSE];
[weeklyWeather addObject:day];
}
completionBlock(weeklyWeather);
}];
}
- (void)getCurrentWeather:(float)latitude longitude:(float)longitude
completionBlock:(void (^)Weather *))completionBlock {
// formulate the url to query the api to get current weather
NSString* url = [NSString stringWithFormat:
@"http://api.openweathermap.org/
data/2.5/weather?units=imperial
&cnt=7&lat=%f&lon=%f", latitude, longitude];
weather model to take the JSON data and parse it into the
appropriate properties that you just created.
Weather Radar
codemag.com
45
[dictionary[@"temp"][@"max"] intValue];
if (temperatureMax) {
_temperatureMax = temperatureMax;
}
if (self) {
/*
* Parse weather data from the API into this weather
* object. Error check each field as there is no guarantee
* that the same data will be available for every location
*/
int humidity =
[dictionary[@"humidity"] intValue];
if (humidity) {
_humidity = humidity;
}
float windSpeed =
[dictionary[@"speed"] floatValue];
if (windSpeed) {
_windSpeed = windSpeed;
}
}
/*
* weather section of the response is an array of
* dictionary objects. The first object in the array
* contains the desired weather information.
* this JSON is formatted the same for both requests
*/
NSArray* weather = dictionary[@"weather"];
if ([weather count] > 0) {
NSDictionary* weatherData = [weather objectAtIndex:0];
if (weatherData) {
NSString *status = weatherData[@"main"];
if (status) {
_status = status;
}
int temperatureMax =
[dictionary[@"main"][@"temp_max"] intValue];
if (temperatureMax) {
_temperatureMax = temperatureMax;
}
int humidity =
[dictionary[@"main"][@"humidity"] intValue];
if (humidity) {
_humidity = humidity;
}
float windSpeed =
[dictionary[@"wind"][@"speed"] floatValue];
if (windSpeed) {
_windSpeed = windSpeed;
}
}
else {
int temperatureMin =
[dictionary[@"temp"][@"min"] intValue];
if (temperatureMin) {
_temperatureMin = temperatureMin;
}
}
}
}
return self;
int temperatureMax =
46
codemag.com
/**
* Takes a unic UTC timestamp and converts it
* to an NSDate formatted in the device's local
* timezone
*
* @param date Date to be converted
*
* @return
Converted date
*/
-(NSDate *)utcToLocalTime:(NSDate*)date {
NSTimeZone *currentTimeZone =
[NSTimeZone defaultTimeZone];
NSInteger secondsOffset =
[currentTimeZone secondsFromGMTForDate:date];
return [NSDate dateWithTimeInterval:
secondsOffset sinceDate:date];
}
Youve now completed both the WeatherRadar and Weather classes. Simply initialize a WeatherRadar object from
anywhere in your application and call either getCurrentWeather or getWeeklyWeather to retrieve the desired
weather information.
Practical Application
AFNetworking on Github
The official github for
AFNetworking can be found
at https://github.com/
AFNetworking/AFNetworking
Full documentation for
AFNetworking can be found at
http://cocoadocs.org/docsets/
AFNetworking/2.6.0/
Wrapping Up
I hope that over the course of this article, you gained
a basic understanding of the services offered by OpenWeatherMaps API and how to use those to add weather
forecasting to any iOS application. If you need a more
complex weather breakdown, be sure to visit OpenWeatherMap.com for full API documentation. The sidebars for
this article have links to additional resources that may be
of use as well.
codemag.com
Jason Bender
47
Jeffrey Palermo
jeffrey@clear-measure.com
JeffreyPalermo.com
@JeffreyPalermo
Jeffrey Palermo is a Managing Partner and CEO of Clear
Measure, an expert software engineering firm based in Austin,
TX with employees across North
America. Jeffrey has been recognized as a Microsoft MVP for
10 consecutive years and has
spoken at national conferences
such as Tech Ed, VS Live, and
DevTeach. Hes the purveyor of
the popular Party with Palermo
events and is the author of
several books, articles, and
hundreds of pithy Twitter quips.
A graduate of Texas A&M University, an Eagle Scout, and an
Iraq war veteran, Jeffrey likes
to spend time with his family of
five out at the motocross track.
48
codemag.com
Tool
Description
Location
Contains the code required to bootstrap and run an application including the compilation system, SDK
tools, and the native CLR hosts
OSS/GitHub
A set of command line utilities to update and configure which runtime (DNX) to use
OSS/GitHub
Entity Framework
OSS/GitHub
Enables the developer to build and publish an ASP.NET 5 Web or console application to a Docker
container running on a Linux or Windows virtual machines
VSIX/Extension
TypeScript
OSS/GitHub
Tool
Description
Location
Community
Has all the features of Express and more, and is still free for individual developers, open source
projects, academic research, education, and small professional teams
Community
Community
Creates standard-based, responsive websites, Web APIs, or real-time online experiences using ASP.NET
Community
Provides the core tools for building compelling, innovative apps for Universal Windows Platform.
Windows 10 is required.
Community
Community
Professional w/ MSDN
Professional developer tools and services for individual developers or small teams
Professional
Enterprise w/ MSDN
Enterprise-grade solution with advanced capability for teams working on projects of any size or
complexity, including advanced testing and DevOps
Enterprise
Code
Code editing redefined. Build and debug modern Web and cloud applications. Code is free and
available on your favorite platform: Windows, Max OS X, or Linux
Non-Windows Web
Visual Studio has long provided features around deployments and the management of server environments.
Visual Studio Online even keeps analytics and recordkeeping around deployment processes moving through
an organization. These packages have histories going
back ten years or more, but much of this historical tooling requires the Visual Studio GUI to be useful. Very
little of it was supported for execution from the command line.
codemag.com
With Visual Studio 2015, the provisioning and deployment tooling executes through the output windows with
chained PowerShell commands. And tooling planned for
release early next year also makes use of PowerShell
for the actual work. With this change to how Microsoft
composes automated tooling, developers have every
tool available to them for inclusion in continuous integration builds and in continuous delivery deployment
pipelines.
Microsoft has also changed its mindset over the years regarding third-party tools. Visual Studio has long provided
some extensibility points for other companies to develop
add-ons for the IDE, but seven years ago, Microsoft first
shipped some open-source libraries directly with Visual
Studio. The 2015 edition takes this approach to the extreme by moving some of its own products to GitHub.com
as the official source repository and distributing them
as extensions to Visual Studio. Table 1 shows some of
the Microsoft products that are fully open-sourced and
shipped via a Visual Studio extension or as a library
through Nuget. The descriptions come straight from the
relevant documentation for the tool.
49
that feature, and others, in detail below. Those integrating with Visual Studio Online to use the automated load
testing capabilities will need to use the Enterprise edition, but most types of applications can be easily developed with the Professional edition.
Figure 2: The detailed feature matrix for the main Visual Studio 2015 editions
ern development practices and modern architectures.
Ten years ago, business applications had largely moved
from desktop client-server applications to Web applications running on large and small Web server farms and
used through Web browsers. Responsive Web techniques
were young, and the entirety of the application ran in the
website processes save for some heavy off-line processing
that had to be accomplished in the form of a batch job or
series of batch jobs.
50
codemag.com
and pre-production server environments. Continuous Integration, a technique that was new ten years ago, is an
expected staple of the development process now. Strenuous suites of automated tests pound on every build of the
application, which now must be called a software system
because its made up of multiple autonomous application components, each running in a separate process and
able to be run on separate servers or cloud infrastructure.
The ability to change and deploy any part of the software system is the hallmark of modern development.
Visual Studio has improved integration across the board
with tools that help make this need a reality. Although
continuous delivery is a new concept for most teams, the
entire industry is moving toward it out of necessity, and
Visual Studio 2015 plays well in that environment. The
eventual destination of a modern software system is cloud
infrastructure, whether its Amazon AWS, Microsoft Azure,
or Windows Azure Pack hosted by Rackspace.
The last mile of Agile software development is Continuous Delivery. Continuous Integration and short devel-
codemag.com
Figure 5: After signing in to Azure, configure the subscription for this application.
opment iterations are the normal staples of developer
education in 2015. Figure 3 shows a developer training
class where Continuous Integration is mentioned briefly
on the way to deeper topics. Developers routinely work
side-by-side in close collaboration while developing
software.
51
52
process of automating software system operations. Monitoring, alerting, and issue resolution are all tasks that
operations professionals have long performed. The DevOps movement quickly automated all of these, creating automated systems of operating complex software systems.
Deploying is one task that falls under the umbrella of operations. Continuous Delivery is the process of deploying
so frequently to production that releasing new revisions
of the software becomes a concept that is less and less
interesting. It removes the notion of a maintenance windows or a release event. Organizations all release software at various frequencies, even if all of them employ
Continuous Delivery.
Infrastructure as Code is an important concept in Continuous Delivery. This concept is the tag line for automatically provisioning servers from code stored in source
control right beside the application code. Rather than de-
codemag.com
codemag.com
53
Figure 10: Docker is now provisioned in Azure with a container for the application.
Once this process is complete, youll surely be interested
in logging into the Microsoft Azure portal to see the cloud
resources that were provisioned and configured based on
these commands and scripts that were run. Figure 13
shows the portal.
As you can already see, Visual Studio 2015 blurs the lines
between the code and the infrastructure. Its tight integration with Azure and PowerShell cause the boundaries
between the technologies to blur.
Previous editions of Visual Studio placed a great deal of emphasis on designers and tooling that made it easier to write
code. Visual Studio 2015 is a demonstration that the code
is the center of the universe. Instead of trying to write the
code for you, Visual Studio 2015 tries to help you work with
and understand the code better. This starts with source control. Here in late 2015, Git has become the de facto standard
for modern source control. Figure 14 shows how to use the
GitHub extension to connect to GitHub from within the IDE.
You can then clone the repository from the GitHub repository, as shown in Figure 15.
Figure 11: You can publish an application in a new container on an existing Docker server.
serves as a good demonstration for which commands to
run and in what order. From this starting point, a proper
Continuous Delivery pipeline can be created so that a
development team has a repeatable process for pushing changes to the software system while keeping each
autonomous application component separate from the
others. In this fashion, each can be replaced without
disturbing the others.
54
Once you have the repository cloned, and for every new
project, you can use the GitFlow Visual Studio extension
to initialize and use the GitFlow source control workflow
for every feature, release, and hotfix over time. Figure 16
shows how access to the GitFlow capability is right where
it belongs, inside the Team Explorer window.
Beyond modern source control integration, Visual Studio
2015 Professional edition includes the CodeLens feature
that was previously only available in the Enterprise or
Premium editions of Visual Studio. CodeLens has also
been enhanced to provide:
codemag.com
Figure 12: PowerShell scripts copy the application and complete the deployment.
Figure 13: The Azure portal shows the resources created by the Docker provisioning.
codemag.com
55
Figure 14: Team Explorer support connecting to modern source control systems
56
codemag.com
Listing 1: The Visual Studio configuration used in this article includes some useful extensions
Microsoft Visual Studio Enterprise 2015
Version 14.0.23107.0 D14REL
Microsoft .NET Framework
Version 4.6.00079
GitHub.VisualStudio 1.0
A Visual Studio Extension that brings the GitHub Flow into Visual Studio.
1.0
14.0.20723.0
0.9
Microsoft.Pex.VisualStudio
Pex
1.0
GenerateUnitTest 1.0
Generates unit test code for methods in classes under test.
GitFlow.VS.Extension 1.0
Visual Studio extension that integrates GitFlow
0.6
14.0.23121.00 D14OOB
Listing 2: ASP.NET 5 uses a very different project file than previous versions
{
"commands": {
"web": "Microsoft.AspNet.Hosting --config hosting.ini"
},
"webroot": "wwwroot",
"userSecretsId":
"aspnet5-ClearMeasure.Bootcamp.UI-559290c5. . . ",
"version": "1.0.0-*",
"dependencies": {
"Microsoft.AspNet.Mvc": "6.0.0-beta6",
"Microsoft.AspNet.Mvc.TagHelpers": "6.0.0-beta6",
"Microsoft.AspNet.Authentication.Cookies": "1.0.0-beta6",
"Microsoft.AspNet.Diagnostics": "1.0.0-beta6",
"Microsoft.AspNet.Diagnostics.Entity": "7.0.0-beta6",
"Microsoft.AspNet.Server.IIS": "1.0.0-beta6",
"Microsoft.AspNet.Server.WebListener": "1.0.0-beta6",
"Microsoft.AspNet.StaticFiles": "1.0.0-beta6",
"Microsoft.AspNet.Tooling.Razor": "1.0.0-beta6",
"Microsoft.Framework.Configuration.Abstractions": "1.0.0-beta6",
"Microsoft.Framework.Configuration.Json": "1.0.0-beta6",
"Microsoft.Framework.Configuration.UserSecrets": "1.0.0-beta6",
"Microsoft.Framework.Logging": "1.0.0-beta6",
"Microsoft.Framework.Logging.Console": "1.0.0-beta6",
"Microsoft.VisualStudio.Web.BrowserLink.Loader": "14.0.0-beta6",
"ClearMeasure.Bootcamp.Core": "1.0.0-*",
"ClearMeasure.Bootcamp.Dnx.DependencyInjection": "1.0.0-*"
},
codemag.com
"frameworks": {
"dnx46": { }
},
"exclude": [
"wwwroot",
"node_modules",
"bower_components"
],
"publishExclude": [
"node_modules",
"bower_components",
"**.xproj",
"**.user",
"**.vspscc"
],
"scripts": {
"prepublish": [ "npm install", "bower install", "gulp clean",
"gulp min" ]
}
57
Stack
Server
Req/sec
Load Params
Impl
Observations
ASP.NET 4.6
perfsvr
65,383
perfsvr
276,727
hello.html containing
HelloWorld
perfsvr
231,609
hello.html containing
HelloWorld
ASP.NET 5 on WebListener
(kernel cached)
perfsvr
264,117
Just app.Run()
ASP.NET 5 on WebListener
(non-kernel cached)
perfsvr
107,315
Just app.Run()
perfsvr
109,560
Just app.Run()
NodeJS
perfsvr
96,558
Scala
perfsvr
204,009
libuv C#
perfsvr
300,507
12 threads, 1024
connections
Table 3: ASP.NET 5 shows that it has massive performance gains over previous versions.
Figure 17: CodeLens provides a great deal of useful information about your code.
58
codemag.com
This new project system and runtime are very, very different from the way Visual Studio has assembled code
for compilation and packaging since Visual Studio .NET
in 2002. Seasoned .NET developers are used to a project producing a .dll file called an Assembly. Although assemblies are still the unit of code at runtime, theyre no
longer the sole unit of packaging at compile time. This
new project system produces Nuget packages from each
project. These Nuget packages are appropriate for deployment because they can contain multiple assembles, which
allows each project to produce assemblies targeted at different environment, all in the same compilation step.
And because ASP.NET 5 is an open source framework being released from GitHub, its set up to come into Visual
Studio 2015 without issue.
60
codemag.com
Figure 19: Universal Windows applications are available when running on Windows 10.
JavaScript, or C++, in a very similar fashion to Windows 8
applications. Universal Windows applications are distributed via the Windows Store, but they can also be installed
directly, called Side-Loading, if developer options are
turned on within Windows.
Creating a Universal Windows application is very simple
and can be done through the New Project dialog, as
shown in Figure 19.
If you have created a Windows 8 application, youll feel
right at home in the code, however, you still must adapt
to the new Visual Studio project system for the new CoreCLR runtime. Figure 20 shows a new Windows 10 application in the Solution Explorer.
DNX Internals
codemag.com
61
For applications needing to move to .NET 4.6, Visual Studio 2015 provides an easy migration path, excluding the
DNX changes. The folks on the Visual Studio team have
been making it increasingly easier to move from version-
62
codemag.com
The application Ill upgrade as an example is an expensereporting application. Its very simple, and it includes
many concepts of much larger applications. First, clone
the source code repository found at https://github.com/
ClearMeasureLabs/ClearMeasureBootcamp. Figure 22
shows the application running.
Our expense report application is a little on the light side
feature-wise. It includes elements like the Onion Architecture layer, and other elements that youll find in your
own applications, such as:
Separate projects for separate concerns
A UI Project that stands with only a single reference
(to Core)
An older version of NHibernate
Unit tests
HTTP Handlers
The Bootstrap CSS/JS library
StructureMap for dependency injection
A database migrations library
A custom workflow engine
Figure 23 shows the structure the application, as established
by the project, references within the Visual Studio solution.
When you open the solution in Visual Studio 2015, it will
be in 2013 mode. In the past, theres been an automatic
conversion step that modified some source code, an event
that caused every developer on the team to have to upgrade to Visual Studio 2015 at the same time. In this new
version, no code is changed, and other members on the
team dont have to synchronize to the version of Visual
Studio used. Youll notice a small change in the repository, as shown in Figure 24.
If you want to mark the solution file for the new Visual
Studio version so that it opens in version 2015 by default,
youll want to update the first few lines of your .sln file
using this version number:
# Visual Studio 14
VisualStudioVersion = 14.0.23107.0
Visual Studio 2015 works very well side-by-side with Visual Studio 2013 and Visual Studio Code. Installing it will
not cause any adverse side effects.
Wrapping Up
Visual Studio 2015 is both a massive IDE release and one
that sets the stage for a big revision in the CLR that were
all familiar with. In this article, Ive covered several key
concepts, including Microsofts change in philosophy and
how it has become more open and componentized with
developer tooling. I looked at how this release of Visual
Studio supports modern development, including DevOps
topics like Continuous Delivery and Infrastructure as Code
with Docker Container support. I explored ASP.NET 5,
CoreCLR, and the DNX execution environment. Finally, I
showed you how easy it is to bring existing Visual Studio
2013 applications into Visual Studio 2015 without forcing
a cumbersome upgrade process. Im excited about Visual
Studio 2015, and you will be too, because this release
contains something for everyone.
Jeffrey Palermo
codemag.com
63
Bilal Haidar
bhaidar@gmail.com
http://blog.bilalhaidar.com
@bhaidar
Bilal Haidar, a PMP holder
and ASP.NET Insider, works
as a senior software developer at CCC, a multinational
construction company located
in Athens, Greece. Bilal has
been a software developer
for over 10 years, developing
Web applications on top of
VBC, an in-house document
management system. Today,
Bilal builds client-centric Web
applications and services with
HTML5 and JavaScript Web
technologies, using AngularJS
on the front-end, and the ASP.
NET stack on the back-end.
Bilal has published over 60
articles in CODE Magazine and
other online magazines. In
2008, Bilal published his first
book, Professional ASP.NET 3.5
Security, Membership, and Role
Management in C# and VB.NET
from Wrox Press (http://goo.
gl/gMu4AK). You can find
Bilals blog at http://blog.
bilalhaidar.com or contact him
directly at bhaidar@gmail.com.
When the user clicks the Edit button, the Grid opens a
modal pop-up box so that they can edit the records details.
In the complicated scenarios required by Web apps, the
aforementioned editing methods are not enough. In
fact, youre limited in designing the layout of the app by
having only these two options. For instance, an app Im
working on requires the user to edit a record and some
other related records all in one screen. The form to edit
the records contains more than 30 placeholder controls!
None of the above Grid editing modes is an option for this
kind of traffic. Using the inline mode, you have to keep
scrolling right and left across all of the columns. Also, the
pop-up editing mode isnt an option, given the fact that
the modal box is large, covering almost the whole screen.
This is the right time for you to think outside the box!
Kendo UI offers a rich set of widgets that will seem like a
necessity in almost every Web app that you develop because they make functionality like this easier. In addition
to those widgets, Telerik offers a rich and extensive JavaScript API to all of its components. You gain the upper
hand in making direct JavaScript calls to communicate
and configure those widgets.
With the API in hand, you arent limited anymore to what
the widgets originally offered. You can extend the use of
such widgets to satisfy complex and real-life scenarios.
You can read more about the API here: http://docs.telerik.com/KENDO-UI/introduction.
Teleriks DataSource is a building block that plays a central role in every Web app built with Kendo UI widgets.
The DataSource serves as an abstraction layer for data
and is used as a data source for several widgets, such
as Grid, DropDownList, ListView, and others. Every widget needs a DataSource to display and render a set of
records. Not only is a DataSource used as a storage medium for widgets, its also used as a read-write source
to add new records, edit existing ones, and even delete
them. For instance, the Grid widget has a tight coupling
with the DataSource. When the user adds a new row on
the Grid, the Grid internally adds the new record onto the
DataSource its configured to work with. Also, when the
user edits or deletes a row, the DataSource is updated to
reflect the changes accordingly. Bottom line: The Grid and
DataSource are in sync!
The DataSource provides:
When the user clicks the Edit button, the Grid puts the
record into edit mode and at the same time, displays two
buttons: Update and Cancel.
The Grid offers a second mode of editing, pop-up editing,
as shown in Figure 2.
64
codemag.com
DataSource is a
major building block
for offline and single
page applications
Getting Started
This article uses the Grid widget DataSource and its API
to develop a Web app screen, and shows how to use the
API to get around the widgets preset functionalities and
extend them.
The Web app youll build uses the Grid widget to display and
list Employee records. If you recall from the sections above,
Armed by the knowledge of how the user uses the Web app,
lets switch gears and take a walk through the source code.
codemag.com
65
66
<link href="assets/css/kendo/
kendo.common-bootstrap.min.css"
rel="stylesheet" />
<link href="assets/css/kendo/
kendo.bootstrap.min.css"
rel="stylesheet" />
<link href="assets/css/kendo/reset.css"
rel="stylesheet" />
<link href="assets/css/main.css"
rel="stylesheet" />
codemag.com
$(function () {
The Index.html page adds a few references to some JavaScript files. (The source code for index.html page can
be found in the downloadable source code package on
the CODE Magazine website). This code snippet shows the
JavaScript files.
<script src="assets/js/kendo/jquery.min.js">
</script>
<script src="assets/js/kendo/kendo.all.min.js">
</script>
<script src="assets/js/app.js"></script>
// code omitted
});
configureDataSources() { }
configureForm() { }
configureGrid() { }
configureEventHandling(e) { }
Figure 4: The Employee Register Form is used to edit and create employee records.
codemag.com
67
Now that the models are defined, you need to define the
DataSource to use in the code. The module uses two such
The Marital Status DropDownList uses the maritalStatusDs DataSource to populate its elements. Whenever
possible, use DropDownLists for fields to make data entry consistent and controlled. On the other hand, the
Grid widget uses the employeesDs DataSource to populate itself with Employee records. The Web app allows
the user to add new employee records and edit existing
ones. Therefore, the code configures the employeesDs
DataSource with the proper settings to use when saving
new employee records or updating existing records on
the server. For this to work, the code configures both
the transport.create and transport.update settings
to custom JavaScript functions. For the sake of brevity,
the code that configures the transport.update setting
is shown in the app.js module (and the source code for
68
defaultValue: 0
},
FirstName: { type: "string" },
LastName: { type: "string" },
MaritalStatus: { defaultValue: {} },
JobTitle: { type: "string" },
HireDate: { type: "date" },
BirthDate: { type: "date" },
VacationDays: { type: "number" },
SickLeaveDays: { type: "number" },
Salary: { type: "number" }
}
});
codemag.com
codemag.com
Title article
69
},
create: function (options) {
$.ajax({
cache: false,
type: "POST",
url: "/api/Employees/Save",
contentType: application/json; charset=utf-8,
dataType: "json",
data: JSON.stringify(options.data),
success: function (result) {
console.log("employees saved successfully");
options.success(result);
},
error: function (result) {
options.error(result);
}
});
}
},
schema: {
model: configMap.EmployeeModel
}
});
Always strive to
optimize the loading of
data from the server.
// ...
70
codemag.com
$container.find("select[id='MaritalStatus']")
.kendoDropDownList({
dataTextField: "Code",
dataValueField: "Id",
dataSource: configMap.maritalStatusDs,
optionLabel: {
Code: "Select Marital Status",
Id: -1
}
});
codemag.com
71
The user clicks on the Add new employee button and the
form appears. The user fills in the Employee information (as
you saw back in Figure 4), and clicks on the Save button. The
user uses the same form to edit an existing record. The user
selects a row on the Grid and the form shows and renders
the selected row information. When the user clicks on the
Save button, the code handles saving the Employee record,
as shown in the next code snippet. Once again, the user edits
an existing record or creates a new record from scratch.
function handleSaveChanges(e) {
// get uid for currently displayed row
var currentUid = getUid();
// update employee record in DataSource
updateEmployee(currentUid);
reset(true);
// save changes to server using DataSource
getKendoGrid().saveChanges();
}
The function reads in the uid field attached onto the Form
.data() attribute. If the user edits an existing record, the
uid field contains the uid field of the currently edited record. The uid fields value is undefined for a newly added
Employee record. The updateEmployee() function is
then called, passing the value of the uid variable to it as
a parameter, as shown in Listing 3.
The function checks the parameter uid for a valid value. If
it exists, it uses the value of the uid parameter to retrieve
the corresponding Employee record from the employeesDs
DataSource. Otherwise, it initializes a new model and adds
it to the employeesDs DataSource. In both cases, the end
result is a valid Model object, either newly initialized or
populated with an existing Employee record. The form now
binds to the aforementioned model. The addEmployeeToDataSource() function uses the DataSource API to manipulate its data, as shown in the next code snippet.
function makeEmployeeModel() {
var model = new configMap.EmployeeModel({
EmployeeId: 0,
MaritalStatus:
new configMap.ReferenceModel({})
});
return model;
}
function addEmployeeToDataSource() {
var model = makeEmployeeModel();
configMap.employeesDs.add(model);
return model;
}
72
Grid Filtering
It would take a lot of pages to go through all the code details in the app.js module, which is why the source code
for the app.js module can be found in the downloadable
source code package.
Conclusion
I introduced some of the most usable and needed widgets offered by Telerik Kendo UI. Also, I showed how the API could
be used together with the widgets to offer some advanced
scenarios that are valuable and much more realistic than what
Telerik demos online. I recommend that you go through their
documentation for a much deeper knowledge and understanding for the power of the API and functionality it offers.
Bilal Haidar
codemag.com
CODE COMPILERS
(Continued from 74)
the cultural differences between Japan and the
US simply made their model impractical. Right or
wrong, by 2000, much of the fascination with the
Japanese model had disappeared.)
Theory X offered a very basic (and emotionally infantile) view of motivating employees, but Theory
Y didnt offer much in the way of guidance. Cross
your fingers and pray was not well-received. As a
new manager with a growing number of employees looking to me for guidance and direction, it
was a little disappointing to find so little in the
way of actionable points.
Whats worse, psychology then began to discover
that some of the traditional tools of motivation
were, in fact, demotivating.
Summary
Theres more to explore hereits a 200 page
book, after allbut even just the core above
helps begin a long-overdue correction around
how we manage software developers. Ill use the
next column to talk about the six different forms
of motivation (three optimal, three sub-optimal),
but for the moment, if youre struggling with the
basic question of How do I motivate my team to
do better? youre asking the wrong question.
Instead, ask: Why are they motivated to perform as
they do? and be prepared to listen to the answer.
Ted Neward
Nov/Dec 2015
Volume 16 Issue 6
Group Publisher
Markus Egger
Associate Publisher
Rick Strahl
Editor-in-Chief
Rod Paddock
Managing Editor
Ellen Whitney
Content Editor
Melanie Spiller
Writers In This Issue
Jason Bender
Bilal Haidar
Ted Neward
John Petersen
Mike Yeager
Kevin S. Goff
Sahil Malik
Jeffrey Palermo
Paul Sheriff
Technical Reviewers
Markus Egger
Rod Paddock
Art & Layout
King Laurin GmbH
info@raffeiner.bz.it
Production
Franz Wimmer
King Laurin GmbH
39057 St. Michael/Eppan, Italy
Printing
Fry Communications, Inc.
800 West Church Rd.
Mechanicsburg, PA 17055
Advertising Sales
Tammy Ferguson
832-717-4445 ext 026
tammy@codemag.com
Circulation & Distribution
General Circulation: EPS Software Corp.
International Bonded Couriers (IBC)
Newsstand: Ingram Periodicals, Inc.
Media Solutions
Subscriptions
Subscription Manager
Colleen Cade
832-717-4445 ext 028
ccade@codemag.com
US subscriptions are US $29.99 for one year. Subscriptions
outside the US are US $44.99. Payments should be made
in US dollars drawn on a US bank. American Express,
MasterCard, Visa, and Discover credit cards accepted.
Bill me option is available only for US subscriptions. Back
issues are available. For subscription information, email
subscriptions@codemag.com
or contact customer service at
832-717-4445 ext 028.
Subscribe online at
www.codemag.com
CODE Developer Magazine
6605 Cypresswood Drive, Ste 300, Spring, Texas 77379
Phone: 832-717-4445
Fax: 832-717-4460
codemag.com
Managed Coder
73
MANAGED CODER
On Motivation
For an industry that prides itself on its analytical ability and abstract mental processing, we often
dont do a great job applying that mental skill to the most important element of the programmers
tool chestthat is, ourselves. A while back, I wrote a column entitled On Passion. In it, I said:
For a few years now, as Ive interviewed at various companies, whether for full-time position or
as a consultant or contractor, one of the common
questions that repeatedly comes at me is What
are you passionate about? Whats your passion?
Its everywhere, it seems, and its the secret
sauce to success in the profession. Its what defines us. Its what motivates us. If you lack it, you
should quit and take up something else.
This is part of the reason why I think companies
are spending so much effort trying to hire people
with passionit means that theyre self-motivating. It means that theyll be willing to work
through whatever obstacles that arise. It means
that theyll learn whatever they need to learn,
explore whatever they need to explore, master
whatever they need to master to get the job done.
And, more importantly, it means that I, their manager, wont have to figure out how to do the most
difficult task in management: motivate them.
74
Theory
Not surprisingly, theories of how to motivate employees run a wide range across the psychological spectrum. Many people start from Abraham
Maslows Pyramid of Needs, which states that
human beings act to fulfill their needs in a very
specific order: physiological (air, water, food,
sleep), safety (both from physical harm, such
as protection from the weather, and sociological
harm, such as protection from poverty), social
(friends, a sense of connectedness or belonging, receiving love), esteem (feeling important
and respected), and then self-actualization (the
instinctive need to fulfill your full potential). Supposedly, as the theory goes, since a job helps fill
several levels on the Maslow pyramidsafety (job
brings money, protecting against poverty), social
(job brings people around you, creating friends
and connectedness), and esteem (a good job
means you receive respect), early theories of motivation centered pretty strongly around Maslows
pyramid.
Managed Coder
codemag.com