Wednesday, May 15, 2013

10 Things I Learnt Watching A Video About 10 Things Paul Irish Learnt From The jQuery Source

Great, if slightly quirky, video from Paul Irish. Some good points about IIFE’s and jQuery selector performance.

I’ve even added a Cornify button for you to click here:

Cornify

Saturday, May 11, 2013

One or more types required to compile a dynamic expression cannot be found. Are you missing a reference?

Just had an issue trying to use a dynamic object in a .NET test project – at build time I had the compiler error:

One or more types required to compile a dynamic expression cannot be found. Are you missing a reference?

In the end all I had to do was reference “Microsoft.CSharp” from my test project.

Wednesday, May 8, 2013

AntiScrape - IIS ASP.NET Http Module

Download Code

no-scrapeAntiScrape is an IIS ASP.NET Http Module to help in the fight against website scrapers!

How does it work?

AntiScrape hooks into the IIS ASP.NET request/response pipeline.

When your website users request a page, it automatically adds secret hidden links to the page that normal users in web browsers won't see. However, website scrapers that are scanning the HTML of the page will see the link and follow it.

Once the scraper has followed the secret link, they are recorded as being a scraper, and from then on what happens is entirely up to you!

You can either:

  • Return custom content and/or HTTP status code for every other request the scraper makes (even for legitimate content), or
  • Introduce a configurable random delay for all requests that the scraper makes, slowing the scraper down, or
  • Do nothing, other than log the scraping activity.

The settings for AntiScrape are integrated into the web applications web.config.

How are the scraping requests logged?

The module comes with a reference implementation of the data persistence layer for SQL Server, but other implementations can be easily added by implementing the IDataStorage interface in an assembly that resides in the web applications bin folder (remembering to remove the assembly containing the SQL Server reference implementation). AntiScrape uses Microsoft Unity to resolve the IDataStorage interface at run-time.

Development Goals

As part of this project I wanted to ensure that the module could be integrated with an existing web solution as easily as possible. Therefore the sample web project is just a vanilla web forms project created with File, New Web Project in Visual Studio, plus the dlls and some config changes. There are some other minor tweaks to show the results of the scraping requests in a table, but that’s it!

Development Status

This software is currently in active development, and so not recommended for production environments at present.

Stuff I have yet to deal with:

  • Legitimate scrapers – such as search engine crawlers
  • Randomizing the honeypot url

Once I have something reasonable that answers these I shall put together a NuGet package that integrates the module and applies the config transforms.

Live Demo

Live demo is available on Windows Azure here: AntiScrape Demo

Source Code

Source code is available on Github here.

Technology Used

X-POW - Proof Of Work for ASP.NET MVC

Rusty_PadlockX-POW is a proof-of-work implementation for ASP.NET MVC.

View the source code here.


How It Works

The server-side implementation is as an MVC ActionFilterAttribute called RequireXpowAttribute. This does not allow the request through unless the hash problem has been solved.
The client-side implementation is a javascript library that uses Web Workers to perform the hash calculations off the main javascript thread. It raises an event when the hash has been solved, informing the page that it can continue on to the original target.

Configuration

There are two settings that can be tweaked in the web.config:
<appSettings>
  <add key="LeadingBytes" value="2"/>
  <add key="LeadingBytesValue" value="7"/>
</appSettings>
  • LeadingBytes is the number of bytes at the start of the hash to consider when checking the value
  • LeadingBytesValue is the maximum value that the leading bytes of the hash should be to be considered valid
Both of these settings are a single byte, and so are in the range of 0 to 7


Original Technical Details

These details are from the original spec I wrote, and so are slightly out-of-date and need some tidying up. I will update them as soon as I can, but are included here for the extra detail they bring!

Overview
Client requests page. Server sends back page with X-PoWRequest header containing 128bit value. First byte is number of leading zeroes that hash result must have, the other 15 bytes are random. Server also sets cookie value with same name. Client must generate own 128bit value so that when server value and client value are combined into a single 256bit value and hashed using SHA-256 the first N bytes of the hash are zero

Example
Server sends:

              NZ[       random data          ]
X-PoWRequest: 0465A709F1CE40EABEFEF4C94FA0E9A8

Where NZ is number of leading zero bytes the hash of the result must have, in this case 4 Also stores value in a list of request values for the session.

Client responds:

X-PoWRequest: 0465A709F1CE40EABEFEF4C94FA0E9A8
X-PoWResponse: ED807302BF6A403ABE0C0864E271E284

Server checks that X-PoWRequest is present, if not response invalid.
Server checks that X-PoWResponse is present, if not response invalid.
Server checks that X-PoWRequest is in the list of values in the session, if not response invalid.

Server combines values into single 256bit value:

[         server value         ][         client value         ]
0465A709F1CE40EABEFEF4C94FA0E9A8ED807302BF6A403ABE0C0864E271E284

Computes hash:

[                              hash                            ]
00000000891444D0AE14416C4D25E59EACE0404151F44C118F8B1CF868C314A8

Checks first 4 bytes are zero, if so response valid server removes request value from session list

Client
Client is a javascript library that is included in any page that will need to pass x-pow tests. Starts up once document has finished loading (body.onload, or $(document).ready())

Possibly postpone body.onload, and/or $(document).ready() until the script has solved the problem? http://api.jquery.com/jQuery.holdReady/

It will do nothing if the X-PoWRequest cookie/header is not present - raise ready event immediately.

If it is present, then it will start attempting to solve the problem. Maybe each attempt is on a timer in order to keep other scripts responsive - use webworker if available? http://code.google.com/p/ie-web-worker/

Once problem is solved X-PoWRequest and X-PoWResponse cookie/headers are added and javascript event is raised to indicate that the page is ready to communicate with the server again. This event should be used to update the dom to enable interaction with server - GET/POST/PUT/DELETE etc.

Other possible client implementations:

Create Portable Class Library (http://msdn.microsoft.com/en-us/library/gg597391.aspx) that adds support to Silverlight/WP7/.NET applications.

Create a single static method that returns Task and performs the calculations asynchronously in a background thread, something like:

public static Task<byte[]> GenerateResponse(byte[] request)
public static Task<string> GenerateResponse(string request)
public static Task GenerateResponse(HttpContext context)

Other helper methods:

public static bool RequiresResponse(HttpContext context)
public static string GetRequest(HttpContext context)
public static byte[] GetRequest(HttpContext context)
public static void SetResponse(HttpContext context, byte[] request, byte[] response)
public static void SetResponse(HttpContext context, string request, string response)

Server
Server is an ASP.NET MVC Filter Attribute which checks the request value is the one stored for the session, and then calculates the hash of the request and response values, and checks that the leading zeros are the correct number.

Also need an element that adds the X-PoWRequest header to server responses that are required to interact with controller actions that have the filter attribute applied to them. Perhaps an attribute on controller actions that return views that then need to interact with other controller actions that require xpow.

[ActivateXpow] - ActionResult returned has X-PoWRequest header present, and server value added to session xpow value cache.

[RequireXpow] - Checks that the X-PoWRequest and X-PoWResponse headers are present. Checks the request value is the one stored for the session. Calculates the hash of the request and response values. Checks that the leading zeros are the correct number.

Possible other approach:

Single attribute - [RequireXpow] - When an initial request is made to the action with this attribute, the action redirects to a built in action that delivers a defined view and also the xpow request to the browser, which performs the calculation and resubmits the request to the original action with the xpow response included automatically without the need for user intervention. This defined view just needs to be a simple "processing" animation, perhaps with some kind of feedback.

Issues with this approach would be preserving the original HTTP POST data (although this might be trivial).

Saturday, May 4, 2013

Google Chrome on Android,–webkit-overflow-scrolling and Modernizr.overflowscrolling

Google Chrome Logo
This morning I decided to install the latest version of Google Chrome for Android (26.0.1410.58), and test some work I had been doing on converting a website from using iScroll to overflow: scroll and –webkit-overflow-scrolling: touch. Imagine my surprise when I saw that none of my scrolling sections worked any more.
Investigating the issue it seemed that the Modernizr test for this support was now returning false. Digging into that it seemed that the underlying feature detection test was now returning false, which is represented in this javascript snippet:
!!('WebkitOverflowScrolling' in document.documentElement.style)
Which meant that the CSS I was using to enable the scrolling was not being applied by the browser, as it looked like this:
.overflowscrolling .my-scroller {
    overflow: scroll;
    -webkit-overflow-scrolling: touch;
}
This issue has been reported on Stack Overflow here.

More detail about what has changed is revealed in this Chromium issue comment, dated Feb 12:

https://code.google.com/p/chromium/issues/detail?id=175670#c4
No, I think this was indeed triggered by 172481. We removed -webkit-overflow-scrolling with the hopes that it was no longer necessary because we'd automatically opt-in to fast scrolling when we need. The problem is that it isn't happening here.
So it would seem that support for –webkit-overflow-scrolling had been removed from the code at this point.

Here is another issue that discusses the support for overflow scrolling touch:

http://code.google.com/p/chromium/issues/detail?id=128325#c23
Tien-Ren observed while debugging 162363 that -webkit-overflow-touch is an inherited property.  So the behavior of setting zindex: 0 on all non-hidden elements with that property creates a cascade of stacking contexts below it.  (This behavior, behind ENABLE_ACCELERATED_OVERFLOW_SCROLLING, is currently enabled only on Android.)  The obvious fix would be to set zindex: 0 on only "overflow: scroll" elements.
So it would seem that if you are having issues with the scrolling not working as expected then adding zindex: 0 to the element with overflow: scroll then this may help. However this did not work for me, although the scrolling sections worked (with my modified Modernizr test detailed below) the momentum effect of the scrolling was not present.

This comment from Jan 8 seems to suggest that –webkit-overflow-scrolling was still present at this point in time:

http://code.google.com/p/chromium/issues/detail?id=128325#c29
It turns out that iOS Safari also creates stacking contexts for all inherited elements, so let's leave this effect for -webkit-overflow-scrolling on Chrome for Android.  This means that we should never support this property on desktop Chrome.
So the decision to remove it probably occurred between Jan 8 and Feb 12.

No mention of this change was made in the official release notification here:

http://googlechromereleases.blogspot.co.uk/2013/04/chrome-for-android-stable-channel-update.html

For now I have customised the Modernizr test for overflow scrolling so that if it does not detect the feature it checks the user agent of the browser to see if it is the currently affected version and if so returns true. Obviously this is not an ideal scenario.

Thursday, May 2, 2013

Using WebGL + SignalR To Create A Multiplayer HTML5 Space Simulation – Part 1

 

multiplayer_3d_demo_screenshot1

View Demo

Although the name suggest that this is a game, at present it is merely a demo. When you visit the site (in a browser that fulfils the requirements below) then you will be presented with a first-person view from your own personal spaceship, flying through the galaxy.

Other people also viewing the site at the same time as you will be visible to you as spaceships flying through space, their positions updated in real time. Your spaceship will also be visible to them.

Controls

Mouse

  • Moving the mouse pointer away from the centre will turn your ship in that direction
  • Left click moves your ship forward
  • Right click moves your ship backwards

Keyboard

  • W moves your ship forward
  • A moves your ship to the left
  • S moves your ship backwards
  • D moves your ship to the right
  • Q rotates your ship around the forward axis to the left
  • E rotates your ship around the forward axis the the right
  • R moves your ship upwards
  • F moves your ship down

 

HUD

Top left displays your radar, which shows where other ships are in space. Your ship is represented by the large green dot in the centre, other ships are smaller red dots around. If a red dot is on top of the green dot that means that either the other ship is right next to you, or directly in front of you.

Bottom left displays the game info messages, which will tell you about events in the galaxy, such as a new player joining the game.

Requirements

You will need a browser that supports WebGL, running on a reasonably powerful computer with decent graphics hardware.

The currently recommended browser is Google Chrome. The demo works ok on Firefox (but not as fast as Chrome), and not at all on IE 10 or less. Apparently this may be changed in IE 11 (which will possibly support WebGL).

Google Chrome has also been found to work on Android devices, such as Tablets and recent phones. However what does not work at present is the touch interface for these devices. At present this is primarily a desktop-with-mouse driven experience.

Technology

This demo uses WebGL for the graphics rendering. It also uses either WebSockets, Server-Sent Events or AJAX Long Polling for the real-time communications.

It is built with the following technologies:

  • Three.js is a WebGL javascript library
  • SignalR is Real-Time Communications library for the web
  • Windows Azure is Microsofts Cloud Hosting Solution

 

Live Demo

A live demo is available here: http://awesome3dgame.azurewebsites.net/

Source Code

Source code is available on Github here: https://github.com/SneakyBrian/Awesome3DGame

Future Posts

In future posts I will delve into the details of how this was implemented.