Demystifying The Code

Watch the Windows 7 / Windows Server 2008 R2 Launch Virtually

Experience The New Efficiency Microsoft Launch Event Live from San Diego October 26th Virtually!
www.thenewefficiency.com/live

I, along with my teammates, will be delivering the Windows 7 / Windows Server 2008 R2 launch live from San Diego starting at 9am PDT October 26th. Now, you can view and download these 18 IT Professional and Developer focused sessions without ever leaving the house.  Focusing on Windows 7, Windows Server 2008 R2, and Exchange Server 2010, you can listen to Microsoft experts, download valuable resources and explore the live launch event "virtually".

Mark your calendars

Visual Studio 2010 and .NET 4 Beta 2 – Available Today

Today is a big day for developers.  We released Visual Studio 2010 and .NET 4 Beta 2 to MSDN Subscribers (it will be available generally on Microsoft.com later in the week). 

image

Please visit the Visual Studio 2010 Beta 2 landing page here to download.

image

Happy coding…

AJAX Q & A Question 6: Question regarding Page Methods

Question:  In your presentation, you recommended not having web methods inside of ASPX pages in favor of having a centralized asmx web service. Doesn’t that mean every page would have a larger ovehead by having the client code to generate proxies for all methods?

Answer:

Before I begin answering the question, let me set some context around the discussion.  In a code camp presentation, I was discussing accessing services using the AJAX client libraries.  I discussed calling services exposed in *.asmx pages, as well as WCF services using the new webHttpBinding.  A question arose regarding calling static page methods via client script, or at least that is how I interpreted the question.  Before I move on, I’ll provide an example of how to call page methods. 

Here is the code to create the static PageMethod in the code behind:

PageMethod

Here is the same page method defined inline:

PageMethodInline

Here is the client code that calls the method:

CallPageMethod

Back to the answer…  There are really 2 questions to answer here: 1) Why did I suggest that you should not use page methods and 2) the question regarding whether or not there is more page overhead with the use of asmx services because of the proxy generation:  With regards to the first question, it is really a matter of opinion.  When designing service tiers, I buy into the separation of the actual service and how the service is exposed.  Essentially, if you look at one of the major design goals of WCF was to separate the service development from the decision of how the service is exposed.  This allows one to expose the service over multiple transports (http, wse, tcp, etc).  In support of this in AJAX is the new webHttpBinding, which allows you to access WCF services easily from ASP.NET AJAX.  The binding supports the generation of a client proxy class that greatly simplifies the ability to call these services.

I tend to develop my services in a manner that supports this methodology.  Secondly, PageMethods are only accessible by the page containing them.  They are not reusable across multiple pages.  Lastly, I believe it makes for a more maintainable application if the services are separated from the page / UI logic.  The code in my pages is always UI centric, while I have my business logic and service tiers separated.

In answering the second question: Doesn’t that mean every page would have a larger ovehead by having the client code to generate proxies for all methods?  The answer is, probably not (and it depends upon how you architect it).  First of all, there is proxy code that is generated for PageMethods.  Take a look at the ‘View Source’ for the previous PageMethod:

InlineCode

So, in the case where the asmx has the same number of methods as pagemethods, it should be roughly equal.  The next issue may be that there are a large number of methods in the asmx page and only a percentage are being used on a single page.  If this is an issue, a simple solution is copy the proxy code into a *.js file and add a script reference to it.  This file will then be cached by the browser and you will find that this is quite a bit more performant than the PageMethods on a per page basis (on the second page and thereafter).  This is quite simple to do.  Assume your asmx page is named Test.asmx and the url is http://www.robbagby.com/Test.asmx you could type http://www.robbagby.com/Test.asmx/js in the browser, click save and save the proxy code to a location accessible by your project.  Then add a ScriptReference to this code in the ScriptManager and remove the ServiceReference to the asmx.  (BTW, the same holds true for .svc WCF Service files).

Have a question?  Email rob.bagby@microsoft.com and I’ll add it to the list.

 

Regards

AJAX Q & A Question 5: How do you add a script reference in an extender control as an embedded resource?

Download the ASP.NET AJAX Extender Sample Code here.

This question is referring to a Webcast on creating behaviors and extenders i did in may.  In that webcast, I created an client behavior by creating an AJAX class that implemented Sys.UI.Behavior.  This simple behavior did an image swap when the mouseover event was fired.  I will leave the technical details of creating a client behavior in the ASP.NET AJAX Client Libraries to my webcast or separate blog post (if someone asks me a question that would warrant that post.

The second half of the demo was taking the client behavior and making it a bit more user friendly to consume by wrapping it with an AJAX extender control.  By doing this, developers that want to consume the image swap behavior can do this:

ConsumeExtender

instead of this:

ConsumeBehavior

It is clearly much easier to consume the behavior using the extender.  The developer does not need to wire up a load event handler and call Sys.Component.Create ($create is a shortcut) on the client behavior.  The $create signature is a bit tricky, as well.  Interestingly, when you wrap this client behavior with an extender, the end result when the page is rendered is roughly the same.  The extender control wires up the event handler for load and calls $create for you. 

Notice that in the Extender entender example (the first), that the developer does not (seem to) need to know where the client JavaScript is physically located.  This seems to make it easier to distribute and consume this functionality.  However, depending upon how the extender was implemented this may not be as easy as it seems.  The following figure is the overridden GetScriptReferences method from the example I used in the webcast.  GetScriptReferences simply returns a collection of ScriptReference objects that define script resources that the control requires.

GetScriptReferences

You will notice that we are using a physical path to the HighlightImageBehavior.js client behavior.  What this results in is a dependence that the HighlightImageBehavior.js JavaScript file be distributed to the appropriate directory for every site that intends to consume this extender.  This is not a very good solution.  The better way to implement this is to store the JavaScript file as an embedded resource within the assembly.  Obviously the assembly will always be distributed, and when it is, the required script files will be distributed along with it.

The solution:

Well enough background on the question.  Let’s get on with the solution… This process is quite simple (once you know the steps).  The steps are as follows:

  1. Configure the script file to be embedded in the assembly as an embedded resource
    1. a. Right-click on the *.js file
    2. Choose ‘Properties’
    3. Set ‘Build Action’ to ‘Embedded Resource’
  2. Add an assembly attribute in the AssemblyInfo file that references the script library.  The assembly attribute enables a specified embedded resource in an assembly for use as a Web resource
  3. Use the overload to the ScriptReference constructor that accepts the name of the embedded resource and the name of the assembly

Take a look… 

Embedded

The only tricky part here is the naming of the the script reference.  This is the assembly file name + "." + the resource name.  If you have any questions to how this is named, you can simply configure the script file as an embedded resource, compile the project and use ILDasm (IL Disassembler) to see the name of the resource.  Take a look:

ILDasm

You can see here that the name of the resource is HighlightImage.HighlightImageBehavior.js.  Download the ASP.NET AJAX Extender Sample Code here.

AJAX Q & A Question 4 – In methods, how do I validate types of passed parameters?

ASP.NET AJAX has extended Function with a "private" static method called _validateParams for this purpose.  The _validateParams method is used throughout the ASP.NET AJAX client library to validate arguments/parameters.  You are free to use this in your code to validate parameters.  The following is a copy of the documentation for the private method.:

// <summary>
//     Validates the parameters to a method.
// </summary>
// <example>
//     function foo(anyParam, stringParam, anyArrayParam, stringArrayParam,
//                  interfaceParam, optionalStringParam) {
//         #if DEBUG
//         var e = Function._validateParams(arguments, [
//             { name: "anyParam" },
//             { name: "mayBeNullParam", mayBeNull: true },
//             { name: "stringParam", type: String },
//             { name: "floatParam", type: Number },
//             { name: "intParam", type: Number, integer: true },
//             { name: "domParam", domElement: true },
//             { name: "anyArrayParam", type: Array },
//             { name: "mayBeNullArrayParam", type: Array, elementMayBeNull: true },
//             { name: "stringArrayParam", type: Array, elementType: String },
//             { name: "intArrayParam", type: Array, elementType: Number, elementInteger: true },
//             { name: "domElementArrayParam", type: Array, elementDomElement: true },
//             { name: "interfaceParam", type: Sys.IFoo }
//             { name: "optionalStringParam", type: String, optional: true }
//             { name: "stringParamArray", type: String, parameterArray: true }
//             { name: "mayBeNullParamArray", parameterArray: true, mayBeNull: true }
//         ]);
//         if (e) throw e;
//         #endif
//     }
// </example>
// <param name="params" type="Array">Array of parameter values passed to the method.</param>
// <param name="expectedParams" type="Array" optional="true">Array of JSON objects describing the expected parameters.</param>

Here is an example.  In the setter for LastName, we are validating to make sure that a string is passed:

 ValidateParam

Here you can see we try to set a string, which is successful, then we try to pass a bool, which will fail validation.

CallingParam

Here you can see the message of the error that was thrown:

Error

Notice that you can also validate that the param implements a certain interface.  here are some screenshots illustrating that:

INterfaceValidate

Calling code:

InterfaceCall

Error:

InterFaceError

Want to add a question to the list?  Email me at rob.bagby@microsoft.com.

Regards

ASP.NET AJAX Client Library Question And Answer Series – Question 3 (How do you create static members and methods on an object in asp.net ajax?)

Question: How do you create static members and methods on an object in asp.net ajax?

Answer:

Members can be defined as attributes (fields) and methods in the context of oo programming.  So, in order to effectively answer the question, I need to illustrate how to create a public static field and method.  Take a look at the following Person (ASP.NET AJAX) class:

PersonStatic

Notice the species static field and the showSpecies static method.  In the code below, you can see where we are calling the static method and accessing the static field. 

CallStatic

You will also notice above that we are calling a static alert method on the JavaScript String Object.  Take a look at the following code, where I extended the String signature with an alert static method. 

StringExt 

So, not only can we create static members for our own objects, we can extend any object.

Have a question to add to the list?  Email me at rob.bagby@microsoft.com.

ASP.NET AJAX Client Library Question And Answer Series – Question 2

Question: How does Register Class and initializeBase copy child methods into place?

Answer:

This question is probably referring to a warning I give in most discussions regarding calling initializeBase in the constructor function in an implementing class.  In the following screenshot, CallIt.Components.Employee inherits from CallIt.Components.Person.  The important thing to note from this example is the call to initializeBase in the constructor.

ImplClass

The reason I stress the importance to this call has to do with how the ASP.NET AJAX Client Libraries implements inheritance.  For those of you that are familiar with inheritance in JavaScript, you understand that it is quite involved.  There are essentially 3 steps to inherit the functionality of another function:

  1. Call the call function of the base
  2. Set the prototype of the implementing class to the base
  3. Set the constructor of the newly set prototype back to the implementing class (it will be pointing to the base)

In the following example, Employee inherits the functionality of Person, using the JavaScript inheritance steps outlined above:

JSInheritance

ASP.NET AJAX Client Libraries do not follow this pattern, however.  Essentially, our libraries copy the implementations from base classes to implementing classes.  In my WebCasts, I mention how the call to initializeBase is instrumental in this implementation.  Let’s examine…  The first thing to look at is the Type.prototype.resolveInheritance function in the Client Libraries below.  It is clear that this is the code where the members are copied from base to implementing class.

resolveInheritance

Now, if you look at the Type.prototype.resolveInheritance implementation, you will note that it calls resolveInheritance.  If you fail to make this call, under most circumstances, the base members will not be copied to the implementing class.

resolveInheritance

If you have a question you would like to add to the list, please email me at rob.bagby@microsoft.com.

Demystifying The Code