Hello...

and welcome to my blog, feel free to leave a comment!

Search My Site:-
Loading
...


Tuesday, 13 October 2009

Multiple monitors & windows 7

Windows 7 has a great new feature called "aero snap" that lets you drag a window to the left or right of the screen and have it resize to that position (see here for a video of this http://lifehacker.com/5077728/snap-any-window-to-half-the-screen-size-in-windows-7).


This is great feature except if you have multiple monitors. Areo Snap won't snap correctly to the part of the screen that goes across your monitors.

You can work round this by holding down the windows key and pressing the arrow key for the direction you would like to snap in (e.g. if your window is on monitor 1 then press the start key and right and will will snap to the right part of monitor 1)

Perfect!

P.S. Also don't forget you can press the start key up to maximize, down to minimize and you can use the number keys to select items from the start bar to maximize them (or bring them to the foreground)

Thursday, 1 October 2009

jQuery and asp.net

There are many ways to get asp.net control values from javascript. Here are a couple of ways with pro’s/cons

Normal Javascript:

document.getElementById('ctl00_ContentPlaceHolder1_TextBox1').value

This is massivly hard coded and bad. If you change the content place holder, or refactor this into a user control this will no longer work. But this is quick.

document.getElementById('<%=TextBox1.ClientID %>').value

This is less hard coded which is good, but the code can be a bit tricky to read.

With jQuery:

$('#ctl00_ContentPlaceHolder1_TextBox1')[0].value

Again, just as bad as the first normal Javascript example

$('#<%=TextBox1.ClientID %>')[0].value

This is ok compared to the javascript version

$('input[id$=TextBox1]')[0].value

This is probably my favorite method. This tells jquery to search for an input where the id ends with TextBox1 – be careful you have no other TextBox1 ids on the page!

Note the array indexer. This is because jquery returns an array of all the items it finds. This means if you have a grid with 12 rows you can access all of the textbox1’s using

$('input[id$=TextBox1]')[0].value -> $('input[id$=TextBox1]')[12].value

Now you are probably asking why would you just use the first javascript example. This is reasonable for a text box but say you are using a drop down list – which looks better:

var CustomerInputbox = document.getElementById('<%=ddlCustomer.ClientID %>');

var CustomerID = CustomerInputbox.options[CustomerInputbox.selectedIndex].value;

or

var CustomerID = $('select[id$=ddlCustomer] option:selected')[0].value

That is all.

Ross

P.S. Learn to love jQuery, resistance is futile.

Wednesday, 20 May 2009

What don't you know?

As part of the review process at Waterstons we have to set objectives to try and achieve throughout the coming year. I want to orientate mine around stuff I didn't know but wanted to know - here is my list:-


Large scale architecture & design: Probably some kind of training course

Cloud Computing: Microsoft have a beta product called Asure which could offer us the ability to produce some very innovative and scalable solutions.

Microsoft enterprise library application blocks: these include code to make the following easier (and best practice): Caching, Cryptography, data access, logging and security. 

Code generation: Learn more about the code generation techniques we are using

Sql: My sql skills are purely self taught and there are loads of advanced techniques I just don’t know (not really sure how I would self learn this, I do know I have very little knowledge in SSIS).

Visual Studio 2010 & .net 4.0: This will be with us soon and I couldn’t really tell you what we will be getting (the beta is out now) 

ADO.Net data services: a colleague sent an email around about these – I think they could be quite a different way for us to consume sql information.

BI tools: I know the theory behind BI but not the tools 

Test Driven Development: The tools could be useful, but I’m really not sold on this

ASP.Net Routing: This technology allows us to create .net web sites which are search engine optimised (SEO) 

ASP.NET MVC: This is a different way of developing web applications that is gaining a lot of momentum – could easily become industry standard and Microsoft are putting a lot of money and resources into it.

ASP.Net data driven websites: Creates the scaffolding for data driven sites – should do things like code generation but this is from Microsoft

FX Cop/StyleCop: These tools perform analysis on source code to identify potential coding issues

It's really interesting to write a list like this - it defiantly helps organise your (lack of!) free time a bit better - what would be on your list?

Thursday, 26 March 2009

Securing Anonymous web services with Certificates

We are currently working with a client who requires two BizTalk web services to talk to each other, however because they are in different locations there is no common account we can use to secure the communication. Below shows an example of the setup:

BizTalk Server 1:

image

This orchestration has an input port (which accepts an xml file) – this message is then passed to a request reply port (which will call a webservice hosted on BizTalk server 2). The response is then passed to the output port (which is saved to an xml file).

BizTalk server 2:

image

This orchestration is a simple webservice which accepts a message, does something with the contents and returns the new message.

This posting assume you have two orchestrations already talking to each other using wcf without any authentication

Ok that’s the scenario defined – lets get onto the more interesting part!

Configuring BizTalk server 1 (The WCF consumer):

Since we are going to be securing the webservice with certificates lets start by generating the client certificate. Run the following code on the server which will be connecting to the webservice (BizTalk server 1 in my case) in a command prompt:

makecert -r -pe -n "CN=ClientCertName" -b 01/01/2005 -e 01/01/2100 -sky exchange -ss my

To view the certificate type mmc into command prompt, then go to file add/remove snap in, and select Certificates. You should be given an option to select select who you will be managing the certificates for – select “My user account”


image


Now if you look in the Personal folder you should see your certificate. We will need to install this same certificate in a few other places so right click on it and select export. Ensure you include the private key (you actually don't need the private key on the BizTalk server hosting the webservice, but for this demo I have included it).


Now we need to install this certificate in two different locations. On BizTalk server 1 we need to install it under the user account running the host instance. To do this open up a command prompt and type:

runas /user:DOMAINNAME\USERNAME mmc

then type the password for the user. In the management console again select the certificate add in. You can then import the certificate by right clicking on personal and selecting import.


Now we can configure this server to use the certificate you have added. Go into the send port you have generated and ensure you used the type wcf-wshttp – then click configure. For the address modify the url to use Https, then go to the security tab. Here you want to change the security mode to Transport with transport client type: certificate. Then in the client certificate panel click browse. Here you should be able to select the certificate you have just generated.


That’s the first server configured.


Configuring Server 2 (The WCF Provider):


On the second server go to the receive location and select your WCF port. Click configure and go to Security. Set the security mode to Transport, and the client credential type to Certificate.


image


Now we need to configure IIS to host the ssl web service.


Firstly we will need to get another certificate to allow ssl to occur – so right click on the web site and go to properties, then Directory Security and click server certificate. Click the “Create a new certificate” and next followed by “Prepare the request now, but send it later” (You may be able to click send the request immediately to an online certification authority depending on your setup) Fill in all the details ensuring the field named “Common Name” is the dns name used to connect to this machine from Server 1. This will generate a text file which you can then give to a certificate authority to get a valid ssl certificate (this will have to be a certificate authority trusted by Server one – so possible a public authority like VeriSign).


Once you have your certificate you should be able to add it by re-running the above wizard.


Now what we need to do is install the client certificate generated on server 1 – ensure this is installed into the Local Computer certificate store so IIS can access it. Remember for security this certificate should not really include the private key.


After you have added your certificate click the edit button shown below


image


Then select the following “Require Secure Channel”, “Require Client Certificates” and “Enable Certificate Trust List”, then click New...


This Wizard will allow you to specify the client certificates which can be used to access the webservice. Click Add from store then select the client certificate installed above. Click next, give it a friendly name, next and Finish. Then select the certificate list:


image


You will probably have to restart IIS now before this works correctly (and I had to restart IIS every time I changed the certificate trust list).


And thats it! Transport security with client certificates DONE.




Here are some error messages you might get and how to fix them:


The adapter failed to transmit message going to send port "SendPort1" with URL "https://ServerName/TestWebserviceCommunication/TestWebserviceCommunication_ProcessMessage_SendAndRecieve.svc". It will be retransmitted after the retry interval specified for this Send Port. Details:"System.InvalidOperationException: Cannot find the X.509 certificate using the following search criteria: StoreName 'My', StoreLocation 'CurrentUser', FindType 'FindByThumbprint', FindValue '23D68B9999C21FC93702D259736DD0CC1C752B61'.
at System.ServiceModel.Security.SecurityUtils.GetCertificateFromStoreCore(StoreName storeName, StoreLocation storeLocation, X509FindType findType, Object findValue, EndpointAddress target, Boolean throwIfMultipleOrNoMatch)
at System.ServiceModel.Security.SecurityUtils.GetCertificateFromStore(StoreName storeName, StoreLocation storeLocation, X509FindType findType, Object findValue, EndpointAddress target)
at System.ServiceModel.Security.X509CertificateInitiatorClientCredential.SetCertificate(StoreLocation storeLocation, StoreName storeName, X509FindType findType, Object findValue)
at Microsoft.BizTalk.Adapter.Wcf.Runtime.WcfClient`2.ApplyClientCertificate(ClientCredentials clientCredentials)
at Microsoft.BizTalk.Adapter.Wcf.Runtime.WcfClient`2.CreateChannelFactory[TChannel](IBaseMessage bizTalkMessage)
at Microsoft.BizTalk.Adapter.Wcf.Runtime.WcfClient`2.InitializeValues(IBaseMessage message)
at Microsoft.BizTalk.Adapter.Wcf.Runtime.WcfClient`2..ctor(IBaseMessage message, WcfTransmitter`2 transmitter)
at Microsoft.BizTalk.Adapter.Wcf.Runtime.WcfTransmitter`2.GetClientFromCache(String spid, IBaseMessage message)
at Microsoft.BizTalk.Adapter.Wcf.Runtime.WcfAsyncBatch`2.BatchWorker(List`1 messages)"
.

For more information, see Help and Support Center at http://go.microsoft.com/fwlink/events.asp.

This error is because your client certificate is stored in your cert store, but not the cert store used by the biztalk host instance. Look at the step above showing how to run mmc as another user to fix this problem.


The adapter failed to transmit message going to send port "SendPort1" with URL "https://ServerName/TestWebserviceCommunication/TestWebserviceCommunication_ProcessMessage_SendAndRecieve.svc". It will be retransmitted after the retry interval specified for this Send Port. Details:"System.ServiceModel.Security.MessageSecurityException: The HTTP request was forbidden with client authentication scheme 'Anonymous'. ---> System.Net.WebException: The remote server returned an error: (403) Forbidden.
at System.Net.HttpWebRequest.EndGetResponse(IAsyncResult asyncResult)
at System.ServiceModel.Channels.HttpChannelFactory.HttpRequestChannel.HttpChannelAsyncRequest.CompleteGetResponse(IAsyncResult result)
--- End of inner exception stack trace ---

Server stack trace:
at System.ServiceModel.AsyncResult.End[TAsyncResult](IAsyncResult result)
at System.ServiceModel.Channels.ServiceChannel.SendAsyncResult.End(SendAsyncResult result)
at System.ServiceModel.Channels.ServiceChannel.EndCall(String action, Object[] outs, IAsyncResult result)
at System.ServiceModel.Channels.ServiceChannel.EndRequest(IAsyncResult result)

Exception rethrown at [0]:
at System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg)
at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
at System.ServiceModel.Channels.IRequestChannel.EndRequest(IAsyncResult result)
at Microsoft.BizTalk.Adapter.Wcf.Runtime.WcfClient`2.RequestCallback(IAsyncResult result)"
.

For more information, see Help and Support Center at http://go.microsoft.com/fwlink/events.asp.

This error is because the service you have used was not trusted on the Server 2, ensure you have the correct client certificate selected in IIS.