03 October 2017

Who knew than JSON.parse() requires double quotes

The other day we were trying to get a small app off the ground. Sometimes even the simplest things which should obviously work, just don’t work.

The code in question was creating a small object:

var s = '{';
s = s + 'width : 17,';
s = s + 'length : 20';
s = s + '}';

var o = JSON.parse(s);

But after executing, o did not contain an object at all.

(As I write this, call to JSON.parse(s) fails with an exception in Chrome. I am fairly certain that during the development there was no exception.)

After unsuccessfully trying out a few things, a search on the internet revealed that property names must be double quoted. This was a bit surprising, since one can easily asume that whatever Javascript code is valid, it will still be valid when passed as a string into JSON.parse()

Turns out JSON has special syntax which prescribes double quotes.

20 October 2016

Supporting client side AngularJS routing in ASP.NET MVC without a controller

For our AngularJS application, we have perused ASP.NET MVC/WebAPI template. It creates a scaffolding with lots of stuff which is really helpful in the beginning. As our app matured we began to realize that the additional stuff is just a hindrance. Whoever uses WebGrease today? Ditto for Bootstrap installed as a NuGet package.

So we went about tidying up: removing NuGet packages, cleaning up web.config etc. At one point, we wanted to remove HomeController since all it does is serve index.html for requested URLs

Recommendations found online concerning AngulerJS client side routing can generally be divided in two categories:

  • use a HomeController and
  • use URL rewriting

URL rewriting, while powerful, somehow also seems out of place. Not to mention that it relies on regular expressions, of which we are no experts.

Further attempts to force routes.MapRoute to route all URLs to index.html failed since ASP.NET MVC is controller oriented and apparently has to have a controller.

But then, while reading a rather thorough overview of ASP.NET routing, a method MapPageRoute popped up. Our index.html is a page, so maybe this is right. On first attempt, server failed complaining

Server Error in '/' Application.

There is no build provider registered for the extension '.html'

A (bit dirty) fix for this was to rename index.html to index.aspx

public static void RegisterRoutes(RouteCollection routes)
{
	routes.MapPageRoute(
        routeName: "CatchAll",
        routeUrl: "{*anything}",
        physicalFile: "~/app/index.aspx");
}

With this in place, we were able to get rid of HomeController.

A better solution would be to separate front end and Web API in two projects. Front end can then be hosted on whichever web server.

18 August 2016

The rabbit hole of AngularJS localization

TL;DR

For date and time formats AngularJS relies on CLDR.

The problem

Few days ago, I was trying to display an instant in time with Angular and its date filter.

After installing angular-i18n and including the appropriate file in the index.html, the string was different, although not in an expected way. It was displayed using a dot (.) instead of a colon (:) as a time separator (instead of 14:37 it would display 14.37)

A quick glance revealed that the referenced file (angular-locale_sr-latn-rs.js) has time formats defined with dot. My first thought was that it’s a bit weird that such a widely used library has a bug. But then, for a long time Windows had almost proper formats for Serbian locale. Until recently, date format was missing the final dot, so instead of 18.08.2016. a date would be formatted as 18.08.2016

As a quick fix I referenced sr-latn-ba which has the proper separator.

Now, a minor thing like this can surely be fixed properly by contributing to Angular repository.

The not-solutions

Without giving it much thought, after quick search, I somehow land on bower-angular-i18n which looks about right. Until I notice that there are pull request months old. Why could that be?

A comment in one of them says:

This repo is for distribution on npm and bower. The source for this module is in the main AngularJS repo. Please file issues and pull requests against that repo.

Ah, no problem. I’ll just go there.

At AngularJS repository, after a search for i18n pull requests:

Localization Issues: Angular.js uses the Google Closure I18N library to generate its own I18N files (the ngLocale module).

Hmmm.. Ok then.

A search in Closure Library yields another closed PR:

See https://github.com/google/closure-library/wiki/Internationalization-(i18n)-changes-in-Closure-Library

A paragraph on that page says the following:

Closure Library’s i18n files that contain locale data (e.g., currency symbols, date time patterns, etc.) are auto-generated based on data from CLDR. If you see an incorrect symbol, please first check CLDR

Will this ever end?

CLDR

Sure enough, CLDR, in an XML file with Serbian locale data, defines time formats which use the dot instead of colon.

If only it was obvious what one needs to do to fix the omission. After taking a wrong turn and trying CLDR Survey Tool, it becomes clear that CLDR : Bug Tracking is the proper way forward.

Finally, here is the submitted ticket. We’ll see how it goes.