February 2008 - Posts

I just finished writing my first production WCF application, which worked very well until I deployed it to our production environment.  All of a sudden none of the WCF calls would work, and I would get a JavaScript "TestService is not defined" error.  When I look inside the JS service reference (in debug mode), I got the following error:

Could not find a base address that matches scheme http for the endpoint with binding WebHttpBinding. Registered base address schemes are [https]

So apparently my WCF service registered itself as HTTPS (since it is over SSL), but my binding was only configured for HTTP.  The solution is to define a custom binding inside your Web.Config file and set the security mode to "Transport".  Then you just need to use the bindingConfiguration property inside your endpoint definition to point to your custom binding.  The entire HTTPS-enabled system.serviceModel section is below:

<system.serviceModel>
<behaviors>    
 <endpointBehaviors>
  <behavior name="TestServiceAspNetAjaxBehavior">
   <enableWebScript />
  </behavior>
 </endpointBehaviors>
</behaviors>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true" />
<services>
 <service name="TestService">
  <endpoint address="" behaviorConfiguration="TestServiceAspNetAjaxBehavior"
   binding="webHttpBinding" bindingConfiguration="webBinding" contract="TestService" />
 </service>
</services>
 <bindings>
   <webHttpBinding>
     <binding name="webBinding">
       <security mode="Transport">
       </security>
     </binding>
   </webHttpBinding>
 </bindings>
</system.serviceModel>

Hopefully this will help someone who has the same problem.

I recently ran into a scenario where I needed to have a submit button exclusively run some client code, which is pretty common and usually handled by having some DOM element call an onclick method that does the work.  However, there was quite a bit of validation that needed to be done and I did not want to have to rewrite the logic that the built in ASP.NET Validators provide.  My solution was to make the form as if I was going to do a full postback, including adding validation to many different controls.  Then I intercepted the postback by calling my custom JavaScript validation/action method and then returning false inside the OnClientClick property of the submitting button (which suppresses the postback, and also the validation).  With the use of Firebug (an essential web development tool for Firefox) I was able to drill into the WebForm__DoPostBackWithOptions() method (included in the WebResource.axd JavaScript include) that ASP.NET uses.  The first few lines are as follows:

var validationResult = true;
 if (options.validation) {
 if (typeof(Page_ClientValidate) == 'function') {
 validationResult = Page_ClientValidate(options.validationGroup);
 }
 }

From there you can see that all of the work is done inside the Page_ClientValidate("ValGroup") function, which you can call from your own code to get the best validation without the postback.  What follows is a quick example of how you would use this in practice:

ASP.NET

<asp:TextBox runat="server" ID="tbHours" Width="50px"></asp:TextBox>
<asp:RequiredFieldValidator ID="rvalAddHours" runat="server" ControlToValidate="tbHours" ValidationGroup="AddEntry" ErrorMessage="* Hours Required" Display="Dynamic"></asp:RequiredFieldValidator>
<asp:RangeValidator ID="rgValAddHours" runat="server" ControlToValidate="tbHours" ValidationGroup="AddEntry" ErrorMessage="* Hours Must Be 0-24" Display="Dynamic" Type="Double" MinimumValue="0" MaximumValue="24"></asp:RangeValidator>
<asp:Button ID="btnAddEntry" runat="server" OnClientClick="ValidateAndAddNewEntry(); return false;" CausesValidation="true" ValidationGroup="AddEntry" Text="Create" />

JavaScript

function ValidateAndAddNewEntry()
{
    var res = Page_ClientValidate("AddEntry");
    
    if ( res == true )
    {
        //Do work
    }
}

Happy Coding!

More Posts