Wednesday, October 31, 2012

Santanna Halloween

Share photos on twitter with Twitpic Share photos on twitter with Twitpic
Share photos on twitter with Twitpic Share photos on twitter with Twitpic

A file deleted but not committed can cause a file lock in Team Foundation Server.

TFS is so much fun.

Subtracting days from a date in JavaScript and getting the day of the week in JavaScript isn't too tough.

The "BeginDate" conditional logic below shows how to roll a date backwards by 30 days.

function setPopupDate(targetID) {
   var dateInput = document.getElementById(targetID);
   var clockDate = new Date();
   if (targetID == FormFields.BeginDate) {
      clockDate.setDate(clockDate.getDate() - 30);
   }
   if (targetID == FormFields.EndDate) {
      var day = clockDate.getDay();
      clockDate.setDate(clockDate.getDate() - day);
   }
   var clockMonth = clockDate.getMonth() + 1;
   var clockDay = clockDate.getDate();
   var clockYear = clockDate.getFullYear();
   if (clockMonth < 10) {
      dateInput.innerHTML = "0" + clockMonth;
   } else {
      dateInput.innerHTML = clockMonth;
   }
   if (clockDay < 10) {
      dateInput.innerHTML = dateInput.innerHTML + "/0" + clockDay + "/" + clockYear;
   } else {
      dateInput.innerHTML = dateInput.innerHTML + "/" + clockDay + "/" + clockYear;
   }
}

 
 

The "EndDate" conditional logic above may be confusing. What am I attempting here?

var day = clockDate.getDay();
clockDate.setDate(clockDate.getDate() - day);

 
 

Well, per this, .getDay() will return a number which can be translated to a day of the week like so:

  1. Sunday
  2. Monday
  3. Tuesday
  4. Wednesday
  5. Thursday
  6. Friday
  7. Saturday

 
 

I want to roll the "EndDate" date back to the most recent Sunday, so subtracting a number of days equal to the encoding for the day of the week at hand should do the trick! On the JavaScript side, the controls I am handing this stuff too are ignorant of the time of day and the DateTime values that C# ultimately makes from strings all thus end up with midnight for the time of day. 12AM is the earliest possible moment in a day, but really I want the "EndDate" value to be at the other end of the time range within the Sunday specified. I thus do the following on the C# side. Here "endDate" is a string holding something like "10/31/2012" which can be translated into a DateTime value with a specific date but not a specific time of day. Midnight will be used as a default for the time of day.

DateTime end = Convert.ToDateTime(endDate);
end = end.AddDays(1);
end = end.AddSeconds(-1);

 
 

Bonus: In typing this up I learned how to change the inital digit of an ordered list to something other than the number one.

<ol start="0">
   <li>Sunday</li>
   <li>Monday</li>
   <li>Tuesday</li>
   <li>Wednesday</li>
   <li>Thursday</li>
   <li>Friday</li>
   <li>Saturday</li>
</ol>

date versus datetime in MSSQL

Per this a date type in MSSQL does not hold the time while datetime type does.

midnight is the default time of day for a DateTime in C#

DateTime halloween = Convert.ToDateTime("10/31/2012");

...will convert to a DateTime of: 10/31/2012 12:00:00 AM

Monday, October 29, 2012

VB script methods running as Macros in Excel

Evan Cortinas showed me today that one may right-click on a tab in Excel and select "View Code" from the menu that appears to see the VB script methods running as Macros in the Excel sheet. You may also write/redact code in the same locale.

Sunday, October 28, 2012

query Mongo using multiple criteria from C#

public List<UserAccounts> GetUserAccount(string email, string password)
{
   var server = MongoServer.Create("foo");
   var database = server.GetDatabase("bar");
   var allRecords = database.GetCollection<UserAccountDataTransferObject>("baz");
   var query = from user in allRecords.AsQueryable<UserAccountDataTransferObject>()
            where user.Email == email && user.Password == password
            select user;
   List<UserAccount> userAccounts = new List<UserAccount>() { };
   foreach (UserAccountDataTransferObject userAccount in query)
   {
      userAccounts.Add(new UserAccount(userAccount.Email, userAccount.Password,
            userAccount.Status));
   }
   return userAccounts;
}

Saturday, October 27, 2012

getting the current url, replacing every dash with a slash, and jQuery animations

$(function () {
   $("#successbar").animate({ width: "302px" }, 0).animate({ width: "302px" }, 900, function
         () {
      $("#successbar").animate({ width: "302px" }, 0).animate({ width: "22px" }, 900,
            function () {
         var reroute = (document.URL).split("/")[5];
         var rerouteParts = reroute.split("-");
         reroute = '/';
         jQuery.each(rerouteParts, function () {
            reroute = reroute + this + "/";
         });
         window.location = reroute;
      });
   });
});

BundleConfig

BundleConfig.cs in the App_Start folder of a MVC4 project looks like so by default:

using System.Web;
using System.Web.Optimization;
   
namespace MongoLogin
{
   public class BundleConfig
   {
      public static void RegisterBundles(BundleCollection bundles)
      {
         bundles.Add(new ScriptBundle("~/bundles/jquery").Include(
                  "~/Scripts/jquery-1.*"));
   
         bundles.Add(new ScriptBundle("~/bundles/jqueryui").Include(
                  "~/Scripts/jquery-ui*"));
   
         bundles.Add(new ScriptBundle("~/bundles/jqueryval").Include(
                  "~/Scripts/jquery.unobtrusive*",
                  "~/Scripts/jquery.validate*"));
   
         bundles.Add(new ScriptBundle("~/bundles/modernizr").Include(
                  "~/Scripts/modernizr-*"));
   
         bundles.Add(new StyleBundle("~/Content/css").Include("~/Content/site.css"));
   
         bundles.Add(new StyleBundle("~/Content/themes/base/css").Include(
                  "~/Content/themes/base/jquery.ui.core.css",
                  "~/Content/themes/base/jquery.ui.resizable.css",
                  "~/Content/themes/base/jquery.ui.selectable.css",
                  "~/Content/themes/base/jquery.ui.accordion.css",
                  "~/Content/themes/base/jquery.ui.autocomplete.css",
                  "~/Content/themes/base/jquery.ui.button.css",
                  "~/Content/themes/base/jquery.ui.dialog.css",
                  "~/Content/themes/base/jquery.ui.slider.css",
                  "~/Content/themes/base/jquery.ui.tabs.css",
                  "~/Content/themes/base/jquery.ui.datepicker.css",
                  "~/Content/themes/base/jquery.ui.progressbar.css",
                  "~/Content/themes/base/jquery.ui.theme.css"));
      }
   }
}

 
 

This will allow you to use this in a view:

@Scripts.Render("~/bundles/jqueryui")

 
 

...in order to render out this HTML:

<script src="/Scripts/jquery-ui-1.8.11.js" type="text/javascript"></script>

 
 

I do not immediately see how the asterisks are getting replaced. I assume the asterisks exist so that one could configure the bundles to use the minified versions of the .js libraries.

must keep reading/burnt out on reading

In remoting, two ASP.NET applications are able to share objects. An object will get serialized by one app and then picked up by another. This is the most interesting thing I read about in the Serialization chapter of C# 4.0 in a Nutshell. The chapter is largely on XML-driven ways to serialize objects that I will never use. I remember being excited in seeing a serialization chapter in the book when I first picked it up in Barnes and Nobles (window shopping in advance of an Amazon buy/that's what Barnes and Nobles is good for) but now I've actually read the chapter and it never mentioned JSON. The chapter was probably written for C# 3.0 in a Nutshell and ported into the book I'm reading now. I'm twenty pages shy of being two-thirds through the thousand page tomb (at page 666), and I'm really, really burnt out on reading it. I guess I will keep reading and finish the book however. I have learned a lot about delegates. This book helped delegates make more sense than anything I had read previously. Well, at least now I'm on the other side of the serialization chapter. At the three-pages-a-day rate I am undertaking, I am going I will be done around the end of February 2013. I lug the book around with me everywhere I go in hopes of being able to read some when waiting at restaurants for food or tech events for the show to start. In recent weeks both Kassandra Perch and Sukant Hajra have given me grief about trying to read an O'Reilly book cover to cover. They both scoffed at the prospect and suggested that O'Reilly books were not something they read "anymore" as if to suggest I was trapped in the past. Ha! Perhaps they are right. I'm going to tough it out however as I'm already hip deep into the book I bought.

Perhaps one can mock classes and not just interfaces.

That kind of means that some of what I suggest here is bogus. I've done some Googling, in fear of bad blogging, that suggests one can mock classes. I'm used to seeing interfaces mocked as I'm used to seeing interfaces carrying the external dependencies which bled into other bit of code in the name of loose coupling.

Friday, October 26, 2012

Testing C# and JavaScript isn't too tough!

Click here to get a project on how-to-test that I made for my coworkers! It includes this introduction note which shows off how upcasting to interfaces comes into play in testing!

 
 

This ASP.NET web application is designed to give a very simple example of how tests may be used. The application itself is very elementary. It does three things:

  1. It offers a means for a user to translate a single digit into a French word. All French translations are facilitated exclusively in JavaScript.
  2. It offers a means for a user to translate a single digit into a German word. All German translations are facilitated exclusively in C#.
  3. It writes all German-translated single digit numbers to a text file.

There are 29 tests wrapped around the logic of the three items above. I'd encourage you to try to change them around and to see what happens when they fail upon your alterations. These 29 tests are found in five locations. They are:

  1. In the WebApplication project at \Scripts\widgets\FrenchTranslator\ there is an .html file titled "SpecRunner.html" which may be opened in or independent of Visual Studio to run the tests defined in "FrenchTranslator.spec.js" (which tests the code in "FrenchTranslator.js" using the HTML in "fixture.html"). There are thirteen tests here which test the French translations. A framework called Jasmine was used to write a JavaScript widget for the French translations as Jasmine's logic may be tested with Jasmine's tests. Unfortunately, this does mean doing things the Jasmine way and that can be a sizable departure from other JavaScript/jQuery implementations. I was recently told that Mocha.js is a better, less awkward tool for this sort of testing. Perhaps it is. The Jasmine way of doing things involves making a folder with four files in it with the latter three serving to test the first:
    1. a JavaScript widget
    2. an HTML fixture in the shape of the HTML the widget expects to manipulate and interact with
    3. a JavaScript specification for testing the widget
    4. an HTML test runner for running the specification for testing the widget
  2. The next four places where tests are found are all in files in the WebApplication.Tests project. The project itself is a test project and thus its tests may be run from within Visual Studio 2010 at: Tests > Run > All Tests in Solution …In particular, BasicUnitTests.cs tests the logic in GermanTranslator.cs back in the WebApplication project. GermanTranslator.cs in turn drives the German translations as you might guess from the name. There are thirteen tests here on the C# side which parallel those in the JavaScript side mentioned previously.
  3. FullSystemTest.cs should spawn a WatiN test. You should see Internet Explorer open and then see fields populated and buttons clicked as though the browser were being manipulated by a user. Selenium is another popular framework for this sort of thing and I've recently heard of another yet called phantomjs. I put three second delays in the one test here so that you may observe what it does in a browser in lieu of merely having a browser open, flicker quickly, and then close.
  4. In order to write tests you have to write code that is testable, and by that I mean code that is somewhat isolated without external dependencies bleeding into it. This can be a challenge. Code that has many tentacles out to many things cannot be tested without much pain and probably will have to be refactored, before any testing really begins, to isolate that which should be tested. For example, in this application, the calls to GermanTranslator.cs are done by GermanTranslatorWrapper.cs which also attempts the file writing. You would not want to test GermanTranslatorWrapper.cs as the app uses it because if you did so you would end up writing to the text file inappropriately as you tested, contaminating user-driven contents there with your own test-driven content. The File I/O stuff here is an example of an external dependency, and MockTest.cs expositions a way to test GermanTranslatorWrapper.cs while sidestepping the external dependency. Again, the nature of the code to be tested must be accommodating to testing, and to be accommodating I isolated the File I/O piece into FileWriting.cs in the Infrastructure folder of WebApplication and then handed it into GermanTranslatorWrapper.cs at a constructor. The constructor takes an IFileWriting interface at its signature and we are able to hand a FileWriting object in nonetheless as FileWriting inherits from IFileWriting allowing for an implicit upcasting. What do I mean by implicit upcasting? Imagine an Animal:
       public class Animal
       {
       }

     
    Then imagine a Parrot that inherited from Animal:
       public class Parrot : Animal
       {
       }

     
    You could explicitly cast a Parrot to its parent type like so:
       Parrot parrot = new Parrot();
       Animal animal = (Animal) parrot;

     
    You could also implicitly cast a Parrot to an Animal by handing it into a constructor signature that expected an Animal such as this one:
       public class AnimalHandler
       {
          public AnimalHandler(Animal animal)
          {
             Animal handledAnimal = animal;
          }
       }

     
    In this case, providing a child type of the type specified in the constructor signature will not cause an error. Instead, C# allows for the child to be implicitly upcast to a parent. That makes this legitimate:
       Parrot parrot = new Parrot();
       AnimalHandler animalHandler = new AnimalHandler(parrot);

     
    Moving forward, we may also make a class inherit from an interface instead of a parent class. (We have to use interfaces with a mocking framework. That is how the magic work.) What if we had an interface called IParrot?
       public interface IParrot
       {
       }

     
    What if Parrot inherited from IParrot instead of Animal?
       public class Parrot : IParrot
       {
       }

     
    Well, then we could have an explicit upcasting like so:
       Parrot parrot = new Parrot();
       IParrot iParrot = (IParrot) parrot;

     
    We could also hand a Parrot into a constructor signature of this nature:
       public class AnimalHandler
       {
          public AnimalHandler(IParrot iParrot)
          {
             IParrot handledAnimal = iParrot;
          }
       }

     
    And, have implicit upcasting like so:
       Parrot parrot = new Parrot();
       AnimalHandler animalHandler = new AnimalHandler(parrot);

     
    The MOQ (pronounced "Mock You") framework allows us to fabricate a different implementation for IFileWriting when testing GermanTranslatorWrapper.cs. Instead of facilitating File I/O stuff, our IFileWriting will just be a dummy object that does nothing. MOQ allows us to specify what the one method inside of the interface will do. I have it just returning true without attempting any file stuff. The one test in MockTest.cs shows off mocking, the making of an on-the-fly interface that is a stand-in for an interface that would otherwise be procured through an upcasting from a class. Again, we can only sidestep the external dependency in GermanTranslatorWrapper.cs in testing by way of the manner GermanTranslatorWrapper.cs was written to begin with.
  5. Another way to do what is done in MockTest.cs is shown in StubTest.cs. Here we do not use a mocking framework, but instead we just hand in a preexisting object (MockWithMe.cs) to be upcast to IFileWriting. In the mocking approach we have to use interfaces, but not so with stub objects. Stubs can be more flexible in this manner while mocks can be quicker to craft and easier to craft in variations.

icons for showing all files are project specific

The icon for this is not going to show up if you are clicking on the solution in lieu of a particular project in the Solution Explorer. duh.

Thursday, October 25, 2012

Santanna is cool!

Share photos on twitter with Twitpic

I've worked at Santanna Energy for a month and a day now. I am enjoying it. They do gas and electric in markets in Illinois, Indiana, Michigan, and Ohio, yet are headquartered in Austin, Texas funny enough. They are sort of a frontend for sales, using different vendors in different markets.

Share photos on twitter with Twitpic

Today was the first day I got my hands in the real code in lieu of the scratch-the-surface stuff. Today we also had a quarterly meeting, my first.

Share photos on twitter with Twitpic

doctoring line breaks in and out of a .csv

I have found a ways to remove all line breaks in a .csv file and then add my own back in. This is really helpful if the .csv was made from other data just copied into Notepad (say from XML). First step: copy to Word. To remove all line breaks in word:

  1. do a find and replace replacing ^p^p with ^l (lowercase L)
  2. do a find and replace replacing ^p with nothing

 
 

To add line breaks back in to define the rows in a .csv. Do this find and replace in Word and then copy back to Notepad:

  1. do a find and replace replacing what you will with ^p

you have to pay $99 a year to submit apps to Apple's App Store

See: https://developer.apple.com/programs/ (and also:)

Wednesday, October 24, 2012

rickroll a keyCode???

<body
   onkeydown="javascript:if(window.event.keyCode == 13) window.event.keyCode = 9;">

nvarchar(max)

I had a back-and-forth with Chad Myers of Dovetail last night over Twitter over using varchar(max) instead of ever using varchar(50) or something less. It doesn't seem like one is going to lose a lot with varchar(max). I wondered if nvarchar(max) could come with problems but this suggested that nvarchar(max) uses nvarchar up to 255 characters and then falls over to something else behind the scenes. (no way to index an nvarchar(max))

Polyfill

a Polyfill is a way to fake support an HTML5 feature where it cannot be had in an older browser

Tuesday, October 23, 2012

an example of a culprit for an extra blank page in an SSRS report

...is this:

<TablixRowHierarchy>
   <TablixMembers>
      <TablixMember>
         <Group Name="list1_Name">
            <GroupExpressions>
               <GroupExpression>=Fields!Name.Value</GroupExpression>
            </GroupExpressions>
            <PageBreak>
               <BreakLocation>Between</BreakLocation>
            </PageBreak>
         </Group>
         <SortExpressions>
            <SortExpression>
               <Value>=Fields!Name.Value</Value>
            </SortExpression>
         </SortExpressions>
         <DataElementOutput>Output</DataElementOutput>
         <KeepTogether>true</KeepTogether>
      </TablixMember>
   </TablixMembers>
</TablixRowHierarchy>
<DataSetName>Whatever</DataSetName>
<PageBreak>
   <BreakLocation>End</BreakLocation>
</PageBreak>

 
 

Note the discrepancy between Between and End! The solution: Use Between in both places. The extra blank page can cause heartache when attempting to export from SSRS into Excel (where the individual pages in the pagination will manifest as independent tabs). This is one of the errors in our logs caused by an extra blank page:

ERROR: Throwing Microsoft.ReportingServices.Diagnostics.Utilities.InternalCatalogException: The row item structure object corresponding to a line cannot be null, Microsoft.ReportingServices.Diagnostics.Utilities.InternalCatalogException: An internal error occurred on the report server. See the error log for more details.;

can't export to Excel from SSRS but can export to CSV???

What could the problem be:

table locking in a transaction

If starting a transaction with table x and then touching table y later, you are likely shipshape, but if starting a transaction with table x and then touching table x again before ending the transaction you may encounter a lock. I had this happen to me yesterday. I experienced an inexplicable timeout which was, in fact, a lock.

Monday, October 22, 2012

1st Titanium App!

At C:\Users\tjaeschk\My Documents\Titanium_Studio_Workspace I created my first Titanium app. The Android and BlackBerry options are initally greyed-out. They seem to require configuration. My app is named "Jaeschke" with an application id of com.tom.jaeschke.

Share photos on twitter with Twitpic

I am making a "Tabbed Application" and I am warned "Requires Titanium Mobile SDK 1.8.0+." Do I already have the SDK?

Share photos on twitter with Twitpic

The app comes with an "Open New Window" button and I decide that enough work for a first app is to just make the button say "Tom Jaeschke was here!" I change about \i18n\en\strings.xml and \i18n\ja\strings.xml

Share photos on twitter with Twitpic

I change up \Resources\ui\handheld\ApplicationWindow.js to reference the XML changes I just made at the "strings" files.

Share photos on twitter with Twitpic

I preview my app!

Share photos on twitter with Twitpic

Next challenge: How do I get the app out to the iPhone App Store?

SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;

...should come before that SELECT statement that is getting blocked due to locking. (credit to Nathan Carroll)

How big can JSON content get in an ASP.NET app?

We have our Web.config file in one app ending like so...

   <system.web.extensions>
      <scripting>
         <webServices>
            <jsonSerialization maxJsonLength="500000">
            </jsonSerialization>
         </webServices>
      </scripting>
   </system.web.extensions>
</configuration>

 
 

...and this is to make sure that JSON which is long enough for our needs may be passed in AJAX. I suppose there is a need to define this in the name of preventing denial of service attacks.

Sunday, October 21, 2012

I installed Titanium Studio today.

I created an account at http://www.appcelerator.com/ today and downloaded Titanium. I have the IDE set up, but I have done nothing with it. I did find this omission of XML in the install process funny:

Share photos on twitter with Twitpic

Some helpful links I was given during the setup process:

  1. https://my.appcelerator.com/resources
  2. http://docs.appcelerator.com/titanium/2.1/index.html
  3. http://developer.appcelerator.com/questions/newest

IList

This points out that IList has a IsFixedSize property on it. I suppose one could use this to see if an IList was made from an upcast from an array or from a list. I get the impression that both a list and an array may be upcast to an IList.

Saturday, October 20, 2012

get the file path to the root of the current web application you are running in Cassini and Visual Studio

string foo = Path.GetDirectoryName(Assembly.GetExecutingAssembly().GetName().
   CodeBase);
foo = foo.Replace(@"file:\", "").Replace(@"bin", "");

 
 

Namespaces: System.IO and System.Reflection

I wrote a WatiN test for the first time in a forever today.

using System;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using WatiN.Core;
using WebApplication.Infrastructure;
namespace WebApplication.Tests
{
   [TestClass]
   public class FullSystemTest
   {
      [TestMethod]
      public void may_convert_a_single_digit_to_German_or_to_French()
      {
         using (var browser = new IE("http://localhost:65535/"))
         {
            TimeKeeping timeKeeping = new TimeKeeping();
            DateTime startOfTest = timeKeeping.GiveTime();
            while (startOfTest.AddSeconds(3) > timeKeeping.GiveTime()) { }
//wait 3 sec
            
            browser.TextField(Find.ByName("TextBox1")).TypeText("7");
            while (startOfTest.AddSeconds(6) > timeKeeping.GiveTime()) { }
//wait 3 sec
            
            browser.Button(Find.ByName("Button1")).Click();
            while (startOfTest.AddSeconds(9) > timeKeeping.GiveTime()) { }
//wait 3 sec
            
            var german = browser.Div(Find.ById("germanout")).Text.Trim();
            Assert.AreEqual(german, "sieben");
            while (startOfTest.AddSeconds(12) > timeKeeping.GiveTime()) { }
//wait 3 sec
            
            browser.TextField(Find.ById("forfrench")).TypeText("7");
            while (startOfTest.AddSeconds(15) > timeKeeping.GiveTime()) { }
//wait 3 sec
            
            browser.Div(Find.ById("frenchbutton")).Elements[0].Click();
            while (startOfTest.AddSeconds(18) > timeKeeping.GiveTime()) { }
//wait 3 sec
            
            var french = browser.Div(Find.ById("frenchout")).Text.Trim();
            Assert.AreEqual(french, "sept");
            while (startOfTest.AddSeconds(21) > timeKeeping.GiveTime()) { }
//wait 3 sec
         }
      }
   }
}

 
 

DateTime.Now is being abstracted away like so:

using System;
namespace WebApplication.Infrastructure
{
   public class TimeKeeping
   {
      public TimeKeeping()
      {
      }
      
      public DateTime GiveTime()
      {
         return DateTime.UtcNow;
      }
   }
}

two random things of JavaScript and jQuery

  1. Get or set the HTML inside of a div in JavaScript:
    var whatitwas = document.getElementById('whatever').innerHTML;
    document.getElementById('whatever').innerHTML = whatitisnow;

     
  2. bind/live/delegate in jQuery:
    $('#foo').bind('click', function() {
       alert($(this).text());
    });
    $('#bar').live('click', function() {
       alert($(this).text());
    });
    $("table").delegate("td", "hover", function(){
       $(this).toggleClass("hover");
    });
    1. bind effects immediate entities
    2. live effects those that may appear later too
    3. I've never used delegate, but, per Justin Pope:
      1. delegate takes three parameters
      2. delegate is a marginally more performant version of live
      3. delegate must be declared before the thing it effects comes into memory

 
 

Note: After I wrote the above today, Steve Flitcroft told me over Twitter that I should use .on instead of .live or .delegate.

 
 

Another Note: (writing this a day after I wrote this blog posting) Mr. Flitcroft also gave me a link to: http://www.ultimatewebtips.com/why-jquery-live-is-a-bad-option-to-use/

How will I know what port Cassini will run on for Watin testing?

Well, you can set this for a project. Right-click on the project in the Solution Explorer in Visual Studio 2010 and select Properties from the menu that appears. In the project's properties, navigate to the "Web" tab (for a web project, duh) and click the "Specific port" radio button. You may need to run your web app once to get it to disassociate with the port it was using beforehand before the WatiN stuff will work.

prep Interop.SHDocVw for WatiN

The cure for this error which you might get when you try to run a WatiN test...

Could not load file or assembly 'Interop.SHDocVw, Version=1.1.0.0, Culture=neutral, PublicKeyToken=db7cfd3acb5ad44e' or one of its dependencies. The system cannot find the file specified.

 
 

...is to click on your Interop.SHDocVw reference in the Solution Explorer and set Embed Interop Types to False at the Properties pane.

History API

Share photos on twitter with Twitpic

Something more from Kyle Simpson's HTML5 talk at IEEE on Wednesday: There is now a History API!

Share photos on twitter with Twitpic

see if a string contains a substring in JavaScript

if (billiards.toLowerCase().indexOf(liar) >= 0) {

a try/catch block, a case statement, and a string to number conversion, all within a chunk of a Jasmine widget

castStringToInteger: function (string) {
   var self = this;
   self.options.Translation = "Sacrebleu!";
   try {
      var integer = parseInt(string);
      if (integer > -9999999) {
         self.options.Number = integer;
         self.castIntegerToString();
      } else {
         throw "conversion is bad";
      }
   }
   catch (err) {
   }
},
castIntegerToString: function () {
   var self = this;
   switch (self.options.Number) {
      case 0:
         self.options.Translation = "zéro";
         break;
      case 1:
         self.options.Translation = "un";
         break;
      case 2:
         self.options.Translation = "deux";
         break;
      case 3:
         self.options.Translation = "trois";
         break;
      case 4:
         self.options.Translation = "quatre";
         break;
      case 5:
         self.options.Translation = "cinq";
         break;
      case 6:
         self.options.Translation = "six";
         break;
      case 7:
         self.options.Translation = "sept";
         break;
      case 8:
         self.options.Translation = "huit";
         break;
      case 9:
         self.options.Translation = "neuf";
         break;
   }
},
options: {
   Number: null,
   Translation: null
}

 
 

Note

  1. alert(err); inside the catch block would bubble our exception up to the user, but I have left this out instead opting to swallow the exception and just say "Sacrebleu!" when things don't go as planned.
  2. var float = parseFloat(string); is the way to handle a number with a decimal in it.

Friday, October 19, 2012

sessionStorage and localStorage

I saw Kyle Simpson speak on HTML5 two days ago at IEEE. sessionStorage is used like localStorage in terms of syntax, but sessionStorage lasts until you close the browser tab while localStorage will be around forever if you don't clean it up.

Share photos on twitter with Twitpic

It makes sense to use both sessionStorage and localStorage in lieu of cookies where we used to use cookies in applications. Kyle's slides are at https://speakerdeck.com/u/getify/p/html5-javascript-on-crack-v4

Share photos on twitter with Twitpic

Threading doesn't really exist in JavaScript. If you need a separate, independent process, you need to load another script somehow. An iFrame out to another page does this trick for example. These sort of hacks are called Web Workers.

sticky icky

Control Panel>Ease of Access>Change how your keyboard works>Set up Sticky Keys ...in Windows 7 allows one to uncheck the checkbox for "Turn on Sticky Keys when SHIFT is pressed five times" to keep the Sticky Keys feature from happening. I really hate it. I'll try to type regular copy and I'll end up firing off some hot key behavior. Boo. Hiss.

You must explicitly create a test project as a test project if you wish to use MSTest with it.

If you make a console app and then stick some tests in it, you will be told "no tests were run because no tests are loaded or the selected tests are disabled" when you attempt to run the tests in MSTest as suggested here.

Thursday, October 18, 2012

margin: 0 auto;

...is the magic for centering a div of a fixed width horizontally in whatever it sits within.

Using JavaScript in Windows 8 intrigues me.

Share photos on twitter with Twitpic

I saw Johnathan Hebert speak at the last AustinJS of 2012 on JavaScript within Windows 8's Metro interface.

Share photos on twitter with Twitpic

In Visual Studio Express 2012 one may create a new project of the type "JavaScript Template" for Metro development. The Windows Store template has a pages folder. One navigates to and from pages in a Metro app, but one never leaves a greater scope that surrounds the "pages." You never go "out of scope." When previewing, one may preview in the Simulator, at the Local Machine, or at a Remote Machine. In the simulator there is a weird tool panel at the right with tools that let you simulate, for instance, the touch or drag of a finger. Windows API objects called WinRT (RT for runtime) objects are accessible from JavaScript and they may be used to access all the stuff you might expect that you can do in the operating system. A page is an example of a context. Any one context will be either a web context or a local context. You must make the tough call of picking one. Only the local context has access to the WinRT goodies while only the web context has access to the ability to inject JavaScript through other script tags by referencing URLs out in the wild. When changing a page the contents of the div that starts out like this...

<div class="pagecontrol" ...

 
 

...gets appended with new information as does the head tag for the app. However, this information does not get replaced when you go to new pages. Leaving a page and coming back to it does not jog this stuff into loading a second time (it hangs out in DOM at length as you navigate) so a script that is triggered upon the loading of a page's contents is only going to fire off once. You can hack around this with the script injection stuff in web contexts. In local contexts the script tags are seen as unsafe and are blocked. (You can use tags to local scripts, and... yes... there is also an unsafe way to hack your way to the web-based scripts that may inject unsafe HTML if you're stubborn.) Pages load from ms_appx paths like so...

ms_appx///default.html

 
 

...with three slashes as shown above. Metro apps live at...

C:/Users/YOUR USERNAME HERE/AppData/Local/Packages/

 
 

...and, the Package.appxmanifest in your project may be inspected for a GUID that will correspond to a filename here. The package will contain folders for LocalState, RoamingState, and TempState. Many functions run asynchronously using a "pattern of promises" in which you call a method and pass in a callback to eventually occur. The callbacks are promise objects. Most of the WinRT methods which are asynchronous end in "Async" for clarity but writeText is an example of one of the exceptions...

local.writeText(fileName, text).done(SOME MORE CODE HERE);

 
 

...in the code above .done is a promise object.

Share photos on twitter with Twitpic

There are also promise objects for error and failure scenarios. .then may be used for chaining a sequence...

Share photos on twitter with Twitpic

...and one may set Visual Studio breakpoints inside of a .then sequence!

Share photos on twitter with Twitpic

I chatted up Lon Ingram (of Waterfall Mobile) at this event and he recommended Mocha.js in lieu of Jasmine and PhantomJS in lieu of Selenium! PhantomJS scripts can be run from a shell and can run jQuery inside of the pages of content they manhandle! Mocha will run inside of Node.js.

Wednesday, October 17, 2012

change your password in Windows 7

  • at: Control Panel > User Accounts > User Accounts > Change User Account Control settings
  • or perhaps via: Ctrl-Alt-Delete

Conway's Law

...named for a Melvin Conway suggests that software will be designed in a structure that is akin to the management structure of the company designing it.

Tuesday, October 16, 2012

Oversight for your Oversight

Last night at Lean Software Austin, I posed the question "Do managers have to be good programmers?" and the usual soft affirmations, serving more to make a position obtainable than to prop one up*, were absent. Instead I was met with a resounding "Yes" and I got the impression that I was the only individual in the room would have made the "mistake" of wondering as much aloud. Scott Bellware asserted most managers are failed programmers and are disconnected. He spoke of an aristocracy in which the upper tier of an organization pads its pockets in lieu of building a slush fund of cash padding for research and rainy days. This leads to playing the short game (short term) instead of the long game. How does one keep this from happening? What will make a manager a better manager when you can't expect his manager to do so in the aristocracy model? Some insights, serving as a light in the dark in the name of preventing bad management:

  • Program or be programmed. Everyone has to be a programmer. So what we are really talking about is how to hire in general. The programmers become/are the managers.
  • Tristan Slominski suggested there should be no hiring bonus and no artificial incentives in hiring. People should join a team for the RIGHT reasons. This drew the most applause of the evening. It is alright to start a team with the good people you know, but when you ask good people if they know good people in hopes of baiting other good people, you are sliding into bad.
  • Marissa Mayer of Yahoo apparently has a practice of screening everyone herself. I heard about this for the first time last night. This could be a good thing if the person on top is good. Another example of when this doesn't work was given too, an example of a Vice President inheriting a team full of bad hires and then setting ridiculous hiring practices that only PhDs navigate well as an overreaction. The hiring hero has to be wise.
  • Greg Symons of DrillingInfo suggested that one does not need to play the short term game of trying to find the right people quickly. He simply suggested that if you cannot find the right people in a short enough amount of time that you will lose anyway in spite of your efforts to the contrary, so you might as well take the pressure off of yourself that leads to panic and bad hiring decisions.
  • Matthew McCullen was hired at GitHub after they were well-established, successfully, and hard to break into. He did it by being a renowned blogging expert at Git. Try to hire people who are smarter than you. This is tricky, but here Matthew MuCullen is an example of finding someone smart.
  • Don't play to the stockholder. That is courting the short game. It is vital to have someone protecting the company from the stockholders.
  • Think about who you want to go into combat with.

 
 

*Debate picks apart would-be solutions at Lean Software Austin. Once and again, I've been to this group and come away without any new solutions. Instead, challenges are discussed in such a manner that one is left with the belief that software development is just really, really hard and that there are no easy answers. Do not read this as criticism, as indeed we are talking about the hard problems people haven't solved and not the easy stuff. This session was different from the others I've been to in that there were some insights that everyone agreed upon as listed above. That said, we also struggled with:

  • Kenneth Olsen's Deck was brought up as a potential company to envy, although it is long gone. They had a very flat structure and there was some debate over whether the way Deck did things was wise. Supposedly no one ever got fired there and open debate and bickering was rampant. Jay Paulson spoke of his own experience in a no-one-gets-fired-ever environment and didn't make it sound like an environment to envy.
  • GitHub and Valve were brought up as companies that were doing everything right too, but Tristan Slominski counter argued that the people working at these companies have themselves as clients (as geeks need source control and geeks play games) and thus both enterprises had an advantage that other enterprises would likely not, skewing how miraculous their accomplishments really were.

 
 

Thanks to Sukant Hajra for moderating the event. This was his event. Thanks to Compass Learning for hosting and Olivier Champet of Compass Learning for keeping the doors open.

Monday, October 15, 2012

throw an exception in C#

System.ApplicationException ex = new System.ApplicationException("Ouch!");
throw ex;

 
 

throw new Exception(); is more plain-jane but it works too.

Friday, October 12, 2012

JavaScript slice

This suggests that Orange and Lemon may be collected alone in an array together with this JavaScript:

var fruits = ["Banana", "Orange", "Lemon", "Apple", "Mango"];
var citrus = fruits.slice(1,3);

 
 

Anthony Dominguez mentioned yesterday that if you want to make a new array from an array that you should port from one to the other with an all encompassing slice. If you do not do so, then the two arrays will reference the same information!

Addendum 7/4/2015: .slice may be called with just one parameter in which case everything before the point specified gets dropped. For example:

var citrus = fruits.slice(1);

 
 

...will give us the Orange, the Lemon, the Apple, and the Mango too dropping only the Banana. If .slice is called with more than two parameters the extra values seem to be ignored and if it is called with zero parameters it will just return everything unsliced.

transactions through SQLConnection with the ability to rollback upon failure

We (Santanna Energy) are doing some lightweight SOA (service-oriented architecture) stuff in the name of making sure that we rollback writes via stored procedures if a subsequent push to Microsoft Dynamics GP (Great Plains) fails. Nathan Carroll has implemented something of this approach:

using (var Conn = new SqlConnection(_ConnectionString))
{
   SqlTransaction trans = null;
   try
   {
      Conn.Open();
      trans = Conn.BeginTransaction();
      
      using (SqlCommand Com = new SqlCommand(ComText, Conn, trans))
      {
         
/* DB work */
      }
      trans.Commit();
   }
   catch (Exception Ex)
   {
      if (trans != null) trans.Rollback();
      return -1;
   }
}

DevExpress

While I am thinking about it DevExpress is/has a suite of fun stuff for ASP.NET. I have only been exposed to it minimally. One thing that is really neat about it, that I've seen, is that one may write their own ASP.NET MVC controls. One may craft what HTML gets put out by the controls, etc. There are also canned MVC controls. I have heard that there is a pagniated list that allows one to get pages one-page-at-a-time from a database in lieu of loading all records upfront and them binding them to a control that hides some of the records (this is how some JavaScript-driven paginated lists work). Other notes:

  1. http://tom-jaeschke.blogspot.com/2012/05/devexpress-grid-will-paginate-on-server.html
  2. http://tom-jaeschke.blogspot.com/2012/03/devexpress-coderush-is-apparently-tool.html

Thursday, October 11, 2012

CAST a varchar to an int in MSSQL

I made the following stored procedure in the name of making a stored procedure which I could get to fail based upon what I passed in.

USE [IT]
GO
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE PROCEDURE [dbo].[sp_tblUsers_GetByUserID]
   @UserIDAsString varchar(50)
AS
BEGIN
SELECT * FROM tblUsers WHERE UserID = CAST(@UserIDAsString AS INT)
END
GO

 
 

I need this for testing. CAST and CONVERT are detailed here: http://blog.sqlauthority.com/2007/07/07/sql-server-convert-text-to-numbers-integer-cast-and-convert/.

get back the auto-incrementing id from a sproc

USE [IT]
GO
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE PROCEDURE [dbo].[sp_tblUsers_Insert]
   @UserID int = null OUTPUT,
   @FirstName varchar(50),
   @LastName varchar(50)
AS
BEGIN
INSERT INTO tblUsers (FirstName, LastName) VALUES (@FirstName, @LastName)
SELECT @UserID = IDENT_CURRENT('tblUsers')
END
GO

Dreamweaver font-family settings!

  1. font-family: Arial, Helvetica, sans-serif;
  2. font-family: "Times New Roman", Times serif;
  3. font-family: "Courier New", Courier, monospace;
  4. font-family: Georgia, "Times New Roman", Times serif;
  5. font-family: Verdana, Arial, Helvetica, sans-serif;
  6. font-family: Geneva, Arial, Helvetica, sans-serif;

Wednesday, October 10, 2012

use regular expressions in JavaScript

function validateEmail(email) {
   var pattern = /^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,6}$/;
   if (!email.match(pattern)) {
      alert('oh no!');
      return false;
   }
   return true;
}

subtract one array from another in JavaScript

In this example, Bar contains a subset of the items in Foo. Baz will end up with all of the items in Foo not in Bar. The lines in black are helpful, not required.

function DefineBaz() {
   
var DiagnosticsHelper = "";
   Variables.Baz = new Array();
   for (var x = 0; x < Variables.Foo.length; x++) {
      var isMatch = false;
      for (var y = 0; y < Variables.Bar.length; y++) {
         if (Variables.Foo[x].UserID == Variables.Bar[y].UserID) {
            isMatch = true;
         }
      }
      if (!isMatch) {
         Variables.Baz.push(Variables.Foo[x]);
      }
   }
   
for (var z = 0; z < Variables.Baz.length; z++) {
      DiagnosticsHelper = DiagnosticsHelper + Variables.Baz[z].UserID + " ";
   }
   document.getElementById("whatever").innerHTML = DiagnosticsHelper;

}

 
 

You can probably see how the DiagnosticsHelper could be moved about in code to collect values from Foo and Bar also.

Tuesday, October 9, 2012

Transpilation

CoffeeScript, TypeScript, and Google's Dart are languages which compile to JavaScript. How this works is not something I'd speculated on before, but Headspring's Patrick Lioi illuminated the process and made it seem less like magic in a talk I saw yesterday at the Austin .NET User's Group. Patrick's example was a language he wrote himself called Rook which compiles to C#. I had assumed this sort of thing outside of my grasp. As it turns out, this is something I could do myself with a whole lot of work and patience, although I can't imagine I have the tenacity Mr. Lioi exhibited for the plumbing required.

Your own invented syntax typed into notepad can serve as actual syntax, providing instructions to a compiler for how it should craft code in another language, in lieu of merely being a string of meaningless, seemingly random characters. There are four things a compiler must do:

  1. Lexing:
    The lexer arm of a compiler takes in a string and breaks it into a collection of the smallest possible string pieces in which every chuck has meaning. Regular expressions are going to do the heavy lifting here to find and make sense of things. An example line of Rook code is Print(evens.First()) and the lexer is going to have to be smart enough to separate this into Print(), evens, and .First(). One just has to slog through writing the rules. Naturally, the order one tries to make matches in code matters. One must try to find != before either ! or = or it will never be found. Things to remember about regular expressions, straight from one of Patrick's slides, are:
    • a* signifies zero or more matches for a
    • a+ signifies one or more matches for a
    • a|b|c allows for either one a, one b, or one c
    • abc signifies a followed by b followed by c
    • (a|b|c)*def is thus any number of the first three lowercase letters of the alphabet
                                        ...followed by d followed by e followed by f
     
  2. Parsing:
    The lexed content is then placed into a tree by a parser. Irony and ANTLR are examples of tools that do this. Naturally, you can write your own too and Patrick has written one called Parsley which he uses to parse Rook syntax. Everything gets separated into functions (operations are a type of function with a funny name) and keywords. Prioritizations will determine where in a tree a given function sits as a node and which might come before something else. For Rook, for example, the multiplication of two and three in 1 + 2 * 3 + 4 will be given priority (if no parenthesis are used to break up the numbers and suggest priority) because Parsley slates such as a rule. What lines of code comes first, second, and last obviously also biases where lexed items end up in the tree the parser makes.

     
  3. Type Checking:
    Here one assigns a type to each node of a language-to-be-compiled of the language-to-be-compiled-to. Patrick suggested looking into Hindley-Milner Type Inference (Google it!) for more on this. The compilation should fail in this step if the code handed in is just bad. The compiler safety stuff gets baked in here. Half the talk was on this stuff and some of the tricky challenges. Does the + operator concatenate two strings or add two integers together? You cannot tell from the operator itself. You have to look to its nodes.
     
  4. Transpilation:
    This is the act of walking an annotated tree and writing copy in the target programming language based upon what is found. In this step, a compiler would walk an annotated tree of Rook syntax (for example) and write C# (for example) elsewhere as it went. For this to work, we have to be able to ask every node "What is your type?" and get back an answer that makes sense in C#. That said, we should be there on the other side of the prior three steps.
     

At this event Zackary Geers mentioned that Austin's Microsoft Office should host the Austin .NET Users Group from this event going forward.

keep a form from posting in jQuery, even within Chrome

This fails in Chrome as it turns out. This offers this hack to make it work in Chrome:

$("#signup_form").validate({
   submitHandler: function(form) {
      alert("Test");
      form.submit();
   }
});

UNION two SELECTs instead of providing a table name inside of a JOIN in MSSQL

This...

INNER JOIN Foo F ON F.BarId = B.BarId

 
 

...could be replaced with...

INNER JOIN (SELECT * FROM Foo UNION SELECT * FROM FooStagingGrounds) F ON F.BarId = B.BarId

 
 

...assuming Foo and FooStagingGrounds have the same columns. In such a scenario, all of the calls to F littered throughout the stored procedure should work against the union of the two tables without needing any further doctoring.

smalldatetime

This tells us that the smalldatetime parameters on a stored procedure should be filled with something like so:

'2010-10-08 12:43:00'

Monday, October 8, 2012

the mouse!

Thad Williams showed me today that typing "mouse" at the start menu in Windows 7 brings up a dialog box for configuring one's mouse.

Share photos on twitter with Twitpic

app uno

What I hope to offer in this blog posting is an exposition on how to make a very simple application using the tools that web monkeys who professionally wrangle line-of-business applications use. Some of the code that follows could be a lot better, but it is kept simple in the name of being easy to understand. This blog post is intended to just show off a bare bones app, devoid of the hand-washing professionals tend to do to tidy things up and make them as maintainable as possible. We will not cut corners on the tooling however. You should use the tools detailed here, namely Microsoft Visual Studio 2012 and Microsoft SQL Server 2012 which may be downloaded online. Both are modern (writing this in 2012), industry standard tools for working with the Microsoft stack where there is a lot of work being done on line-of-business applications currently (again, in 2012). Visual Studio will stop working after a month without an expensive license. I do not know the best way to hack around this problem. Perhaps setting up VMs as detailed here and then reinstalling the software fresh on VMs may do the trick. I am not sure if one can get away with that or not. But, without further ado, assume that you would like to keep a contact list of your friends, Brad, Janet, and Vladimir Putin, on your laptop (which runs Microsoft Windows 7) which is viewable as a web page like so:

Share photos on twitter with Twitpic

To make a file like this, you can make a .txt file on your desktop and rename the file so that it instead has an .html extension. You can then right-click on the file to open it in Notepad and paste in this copy which is of a language called HTML (HyperText Markup Language):

<html>
   <body>
      <h1>My Rolodesk:</h1>
      <table>
         <tr>
            <th>Name</th>
            <th>Phone</th>
            <th>Email</th>
         </tr>
         <tr>
            <td>Brad</td>
            <td>(512) 335-9517</td>
            <td>brad@x.com</td>
         </tr>
         <tr>
            <td>Janet</td>
            <td>(512) 219-1316</td>
            <td>janet@damnit.com</td>
         </tr>
         <tr>
            <td>Vladimir Putin</td>
            <td>(512) 657-0229</td>
            <td>vlad.poo@example.com</td>
         </tr>
      </table>
   </body>
</html>

 
 

If you will save the file and then open it just by double-clicking upon it, you should see the content shown off in the topmost image in this blog posting. This sort of simple content was what Marc Andreessen's World Wide Web was all about in its infancy in the mid 1990s. This sort of content could be hosted as a web page that others could find online, or, in our case, could just sit standalone on someone's laptop. HTML is just one of four varieties of code that I would like to show off however. The others are SQL, ASP.NET with C# and JavaScript. These other three are needed because it turns out there are some things that HTML cannot do on its own that would be really useful. What if you wanted to be able to add a record to your list of contacts without editing in the HTML language that you have recently learned? What if you want your Mom to add to your contacts for you at the same time she is doing your laundry? (I'm just kidding.) Well, your Mom is going to have a tough time wrangling HTML right? Maybe things need to be made more user friendly so that anyone could add a contact through a form. You cannot do this with HTML alone. The first step towards this is to spin up a new database in Microsoft SQL Server 2012. We will make a table to represent our data like so:

Share photos on twitter with Twitpic

We have made a table that represents the data for Brad, Janet, and Vladimir Putin. We have four columns instead of three however. One of the columns, Id, contains a Guid for each row in the database and serves as a unique identifier. This is good policy in database design. The table can be created with SQL (Structured Query Language) which is a language for making database tables like this and manipulating them. The code to make our table is:

/* To prevent any potential data loss issues, you should review this script in detail before
      running it outside the context of the database designer.*/
BEGIN TRANSACTION
SET QUOTED_IDENTIFIER ON
SET ARITHABORT ON
SET NUMERIC_ROUNDABORT OFF
SET CONCAT_NULL_YIELDS_NULL ON
SET ANSI_NULLS ON
SET ANSI_PADDING ON
SET ANSI_WARNINGS ON
COMMIT
BEGIN TRANSACTION
GO
CREATE TABLE dbo.MyDatabaseTable
   (
   Id uniqueidentifier NULL,
   Name varchar(50) NOT NULL,
   Phone varchar(50) NOT NULL,
   Email varchar(50) NOT NULL
   ) ON [PRIMARY]
GO
ALTER TABLE dbo.MyDatabaseTable SET (LOCK_ESCALATION = TABLE)
GO
COMMIT
select Has_Perms_By_Name(N'dbo.MyDatabaseTable', 'Object', 'ALTER') as ALT_Per,
      Has_Perms_By_Name(N'dbo.MyDatabaseTable', 'Object', 'VIEW DEFINITION') as
      View_def_Per, Has_Perms_By_Name(N'dbo.MyDatabaseTable', 'Object', 'CONTROL')
      as Contr_Per

 
 

One could just use the database to keep contacts, but your Mom might have trouble using this too. Instead, I think we should make the database data bled into our web page, replacing the static data typed in there. Strictly speaking, we will need to forgo our web page and instead spin up an ASP.NET Web Forms Application in Visual Studio as this will allow us to do a few things we will need.

Share photos on twitter with Twitpic

Once we make an application we can preview it in Visual Studio. The home page of the application will appear in a web browser and will look like so.

Share photos on twitter with Twitpic

The code for the page will appear as such. The tags with percent symbols and colons in them are special tags not of HTML but instead of ASP.NET. They will render to HTML tags when we preview them in a browser (so to speak).

<%@ Page Title="Home Page" Language="C#" MasterPageFile="~/Site.Master"
      AutoEventWireup="true" CodeBehind="Default.aspx.cs"
      Inherits="MyApplication._Default" %>
   
<asp:Content runat="server" ID="FeaturedContent"
      ContentPlaceHolderID="FeaturedContent">
   <section class="featured">
      <div class="content-wrapper">
         <hgroup class="title">
            <h1><%: Title %>.</h1>
            <h2>Modify this template to jump-start your ASP.NET application.</h2>
         </hgroup>
         <p>
            To learn more about ASP.NET, visit <a href="http://asp.net" title="ASP.NET
                  Website">http://asp.net</a>.
            The page features <mark>videos, tutorials, and samples</mark> to help you get
                  the most from ASP.NET.
            If you have any questions about ASP.NET visit
            <a href="http://forums.asp.net/18.aspx" title="ASP.NET Forum">our forums</a>.
         </p>
      </div>
   </section>
</asp:Content>
<asp:Content runat="server" ID="BodyContent" ContentPlaceHolderID="MainContent">
   <h3>We suggest the following:</h3>
   <ol class="round">
      <li class="one">
         <h5>Getting Started</h5>
         ASP.NET Web Forms lets you build dynamic websites using a familiar drag-and-
               drop, event-driven model.
         A design surface and hundreds of controls and components let you rapidly build
               sophisticated, powerful UI-driven sites with data access.
         <a href="http://go.microsoft.com/fwlink/?LinkId=245146">Learn more…</a>
      </li>
      <li class="two">
         <h5>Add NuGet packages and jump-start your coding</h5>
         NuGet makes it easy to install and update free libraries and tools.
         <a href="http://go.microsoft.com/fwlink/?LinkId=245147">Learn more…</a>
      </li>
      <li class="three">
         <h5>Find Web Hosting</h5>
         You can easily find a web hosting company that offers the right mix of features and
               price for your applications.
         <a href="http://go.microsoft.com/fwlink/?LinkId=245143">Learn more…</a>
      </li>
   </ol>
</asp:Content>

 
 

We will now bring in our prior HTML content. Some of it will be recreated, but we can just copy this tag from our original document.

<h1>My Rolodesk:</h1>

 
 

We will splice it into the code between the second set of asp:Content tags, dropping all of the prior content there first. We will also drag a GridView control from the Toolbox to below our H1 tag.

Share photos on twitter with Twitpic

The code now looks like this:

<%@ Page Title="Home Page" Language="C#" MasterPageFile="~/Site.Master"
      AutoEventWireup="true" CodeBehind="Default.aspx.cs"
      Inherits="MyApplication._Default" %>
   
<asp:Content runat="server" ID="FeaturedContent"
      ContentPlaceHolderID="FeaturedContent">
   <section class="featured">
      <div class="content-wrapper">
         <hgroup class="title">
            <h1><%: Title %>.</h1>
            <h2>Modify this template to jump-start your ASP.NET application.</h2>
         </hgroup>
         <p>
            To learn more about ASP.NET, visit <a href="http://asp.net" title="ASP.NET
                  Website">http://asp.net</a>.
            The page features <mark>videos, tutorials, and samples</mark> to help you get
                  the most from ASP.NET.
            If you have any questions about ASP.NET visit
            <a href="http://forums.asp.net/18.aspx" title="ASP.NET Forum">our forums</a>.
         </p>
      </div>
   </section>
</asp:Content>
<asp:Content runat="server" ID="BodyContent" ContentPlaceHolderID="MainContent">
   <h1>My Rolodesk:</h1>
   <asp:GridView ID="GridView1" runat="server"></asp:GridView>
</asp:Content>

 
 

In order to let ASP.NET bind database data to our GridView control we will need to alter the code behind file for our web form. The code behind file is written in C# and starts out looking like so:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
   
namespace MyApplication
{
   public partial class _Default : Page
   {
      protected void Page_Load(object sender, EventArgs e)
      {
         
      }
   }
}

 
 

We alter it to this:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Data.SqlClient;
using System.Data;
   
namespace MyApplication
{
   public partial class _Default : Page
   {
      protected void Page_Load(object sender, EventArgs e)
      {
         SqlConnection connection = new
               SqlConnection(@"server=.\TWENTYTWELVE;database=MyDatabase;
               Integrated Security=true;");
         SqlCommand command = new SqlCommand();
         SqlDataAdapter adapter = new SqlDataAdapter();
         DataSet dataSet = new DataSet();
         string query = "SELECT * FROM MyDatabaseTable";
         command.CommandText = query;
         command.CommandType = CommandType.Text;
         command.Connection = connection;
         adapter.SelectCommand = command;
         adapter.Fill(dataSet);
         GridView1.DataSource = dataSet;
         GridView1.DataBind();
      }
   }
}

 
 

When we preview our project we see this:

Share photos on twitter with Twitpic

Note that this piece of code in the code behind is a SQL statement that is run against our database to get all of the data in our table.

SELECT * FROM MyDatabaseTable

 
 

If we view the HTML the browser is receiving we will see that our GridView is becoming HTML that looks not unlike the other HTML we originally wrote. This is a good example of how ASP.NET tags behave differently yet similar too regular HTML tags.

Share photos on twitter with Twitpic

The HTML made by our H1 tag and GridView is:

   <h1>My Rolodesk:</h1>
   <div>
   <table cellspacing="0" rules="all" border="1" id="MainContent_GridView1"
         style="border-collapse:collapse;">
      <tr>
         <th scope="col">Id</th><th scope="col">Name</th><th scope="col">Phone</th>
               <th scope="col">Email</th>
      </tr><tr>
         <td>71352ec1-63a8-4f7f-a30c-8d4a042ee301</td><td>Brad</td><td>(512) 335-
               9517</td><td>brad@x.com</td>
      </tr><tr>
         <td>3be815ae-83ce-4892-881c-86d85d2ff316</td><td>Janet</td><td>(512) 219-
               1316</td><td>janet@damnit.com</td>
      </tr><tr>
         <td>519f3334-4fbc-4fd6-91e0-265e7ea2c7db</td><td>Vladimir Putin</td><td>(512)
               657-0229</td><td>vlad.poo@example.com</td>
      </tr>
   </table>
</div>

 
 

Now we will make a form to shove data into our database table as a new row. If we made the form in our original HTML it might look like so:

Share photos on twitter with Twitpic

The code would be revised as such:

<html>
   <body>
      <h1>My Rolodesk:</h1>
      <table>
         <tr>
            <th>Name</th>
            <th>Phone</th>
            <th>Email</th>
         </tr>
         <tr>
            <td>Brad</td>
            <td>(512) 335-9517</td>
            <td>brad@x.com</td>
         </tr>
         <tr>
            <td>Janet</td>
            <td>(512) 219-1316</td>
            <td>janet@damnit.com</td>
         </tr>
         <tr>
            <td>Vladimir Putin</td>
            <td>(512) 657-0229</td>
            <td>vlad.poo@example.com</td>
         </tr>
      </table>
      <h1>Add an entry:</h1>
      Name: <input name="Name" />
      <br />
      Phone: <input name="Phone" />
      <br />
      Email: <input name="Email" />
      <br />
      <button type="submit">Submit</button>
   </body>
</html>

 
 

But, there is no way to make our form speak to our database table with HTML alone so we should instead have our form inside our ASP.NET web form in our ASP.NET project. We will copy and paste it there:

<%@ Page Title="Home Page" Language="C#" MasterPageFile="~/Site.Master"
      AutoEventWireup="true" CodeBehind="Default.aspx.cs"
      Inherits="MyApplication._Default" %>
   
<asp:Content runat="server" ID="FeaturedContent"
      ContentPlaceHolderID="FeaturedContent">
   <section class="featured">
      <div class="content-wrapper">
         <hgroup class="title">
            <h1><%: Title %>.</h1>
            <h2>Modify this template to jump-start your ASP.NET application.</h2>
         </hgroup>
         <p>
            To learn more about ASP.NET, visit <a href="http://asp.net" title="ASP.NET
                  Website">http://asp.net</a>.
            The page features <mark>videos, tutorials, and samples</mark> to help you get
                  the most from ASP.NET.
            If you have any questions about ASP.NET visit
            <a href="http://forums.asp.net/18.aspx" title="ASP.NET Forum">our forums</a>.
         </p>
      </div>
   </section>
</asp:Content>
<asp:Content runat="server" ID="BodyContent" ContentPlaceHolderID="MainContent">
   <h1>My Rolodesk:</h1>
   <asp:GridView ID="GridView1" runat="server"></asp:GridView>
      <h1>Add an entry:</h1>
      Name: <input name="Name" />
      <br />
      Phone: <input name="Phone" />
      <br />
      Email: <input name="Email" />
      <br />
      <button type="submit">Submit</button>
</asp:Content>

 
 

What we create looks like so:

Share photos on twitter with Twitpic

Now our code behind must change to be able to push a record into our table:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Data.SqlClient;
using System.Data;
   
namespace MyApplication
{
   public partial class _Default : Page
   {
      protected void Page_Load(object sender, EventArgs e)
      {
         SqlConnection connection = new
               SqlConnection(@"server=.\TWENTYTWELVE;database=MyDatabase;
               Integrated Security=true;");
         if (Page.IsPostBack)
         {
            connection.Open();
            SqlCommand insert = new SqlCommand("INSERT INTO MyDatabaseTable (Id,
                  Name, Phone, Email) VALUES ('" + Guid.NewGuid() + "','" +
                  Request.Form["Name"] + "','" + Request.Form["Phone"] + "','" +
                  Request.Form["Email"] + "')", connection);
            insert.ExecuteNonQuery();
            connection.Close();
         }
         SqlCommand command = new SqlCommand();
         SqlDataAdapter adapter = new SqlDataAdapter();
         DataSet dataSet = new DataSet();
         string query = "SELECT * FROM MyDatabaseTable";
         command.CommandText = query;
         command.CommandType = CommandType.Text;
         command.Connection = connection;
         adapter.SelectCommand = command;
         adapter.Fill(dataSet);
         GridView1.DataSource = dataSet;
         GridView1.DataBind();
      }
   }
}

 
 

Our code behind empowers us to add a record for Karen. To add a record for Karen we will ultimately run this line of SQL:

INSERT INTO MyDatabaseTable (Id, Name, Phone, Email) VALUES ('0d9d4a70-64bb-42ff-a19c-707134c54827','Karen','(512) 419-8788','karen@something.com')

 
 

Karen will show up like so when we preview our app:

Share photos on twitter with Twitpic

Karen will show up like so when we look at our database table:

Share photos on twitter with Twitpic

We are there. We have a way to add records to our web page that holds our contacts. Brad, Janet, Vladimir Putin, and Karen are now all collected together and we may give them other playmates easily whenever we please. As you can see, we are just getting started. There is a lot not to like about this set up. For example, what if we have a typo in a record? It would be good to create a way to edit records, maybe even delete records. All that is a little bit more than the scope of this example however. One enhancement I will offer is to use JavaScript to ensure that one cannot submit the form without filling out all of the form fields. That will keep a user from entering a partial record accidentally. This trick will work in most browsers. We will need to reference the jQuery library that is part of our Visual Studio project. Here is our revised web form. The stuff in the second script tag is a type of code known as JavaScript.

<%@ Page Title="Home Page" Language="C#" MasterPageFile="~/Site.Master"
      AutoEventWireup="true" CodeBehind="Default.aspx.cs"
      Inherits="MyApplication._Default" %>
   
<asp:Content runat="server" ID="FeaturedContent"
      ContentPlaceHolderID="FeaturedContent">
   <section class="featured">
      <div class="content-wrapper">
         <hgroup class="title">
            <h1><%: Title %>.</h1>
            <h2>Modify this template to jump-start your ASP.NET application.</h2>
         </hgroup>
         <p>
            To learn more about ASP.NET, visit <a href="http://asp.net" title="ASP.NET
                  Website">http://asp.net</a>.
            The page features <mark>videos, tutorials, and samples</mark> to help you get
                  the most from ASP.NET.
            If you have any questions about ASP.NET visit
            <a href="http://forums.asp.net/18.aspx" title="ASP.NET Forum">our forums</a>.
         </p>
      </div>
   </section>
</asp:Content>
<asp:Content runat="server" ID="BodyContent" ContentPlaceHolderID="MainContent">
   <h1>My Rolodesk:</h1>
   <asp:GridView ID="GridView1" runat="server"></asp:GridView>
      <h1>Add an entry:</h1>
      Name: <input name="Name" />
      <br />
      Phone: <input name="Phone" />
      <br />
      Email: <input name="Email" />
      <br />
      <button type="submit">Submit</button>
   <script src="/Scripts/jquery-1.7.1.js" type="text/javascript"></script>
   <script type="text/javascript">
      jQuery(document).ready(function () {
         $("form").submit(function () {
            var emptyField = false;
            var inputs = document.getElementsByTagName("input");
            if (inputs["Name"].value == "") emptyField = true;
            if (inputs["Phone"].value == "") emptyField = true;
            if (inputs["Email"].value == "") emptyField = true;
            if (emptyField) {
               alert('Be careful! You have yet not filled out all of the form fields!');
               return false;
            } else {
               return true;
            }
         });
      });
   </script>
</asp:Content>

 
 

We get this error if we try to submit our form with an empty field. The submission will be blocked. We will not write a partial record to our database table.

Share photos on twitter with Twitpic

Again, and in conclusion, we have a my-first-app sort of app here. Does this make sense?