Category Archives: JavaScript

Next JsWorld release scheduled for November 2010

JsWorld iconToday I looked up Unicode’s tentative schedule for their next CLDR 1.9 release. It is planned for the 10th of November, which means that I’ll be able to update the JsWorld locale definition files soon thereafter and release in turn a JsWorld update. The next JsWorld version will probably be 2.4.

For those if you who don’t know, JsWorld is a comprehensive JavaScript library for formatting and parsing of numbers, currency and date/time inside the browser, in a user specified locale. The locale data strictly follows Unicode’s sources and I strive to update it as soon as the consortium releases a new snapshot of their database. Currently Unicode keeps track of over 300+ world locales, 200+ languages and 100+ currencies.

First look at JsonSSO

Earlier in August I began work on JsonSSO, a web service that provides single sign-on and session management. It naturally complements Json2Ldap, another product of mine which provides web-friendly JSON-RPC access to LDAP v3 compatible directories such as OpenLDAP, MS AD and Novell eDirectory.

The recent years we saw a proliferation of single sign-on (SSO) solutions. While the underlying concept of SSO is relatively simple, the IT context (participating apps, authentication methods, back-ends, platforms, policy, etc.) can vary significantly, which has prompted the development of so many implementations.

JsonSSO has three defining features:

  1. User authentication is done against a back-end LDAP directory via Json2Ldap.
  2. Once a user session is established, participating web clients may be given an open LDAP connection (by means of Json2Ldap) bound as the currently logged-in user. This connection allows web clients convenient and flexible access to user details such as user ID, name, email, photo, application preferences, etc.
  3. An internal database records the details of all active and expired user sessions. It can be queried for audit and management purposes via a JSON-RPC interface.

For JsonSSO to be easy to understand and work with I intend to stick to these three main features. Diversions, such as adding DB-based authentication, will be avoided. I want to have JsonSSO as web-friendly as possible, keeping all incoming (from clients) and outgoing (to back-end) connections in the form of HTTP.

Here is a preliminary overview of the JsonSSO API and its configuration settings. These may change somewhat by the time JsonSSO is officially released (Q4 2010).

JSON-RPC 2.0 API

  • sso.login Initial login with an authenticating ID (username, email, etc.) and password. Returns a new session identifier (SID) which can be passed between the participating web clients and apps.
  • sso.logout Closes a user session. Can be invoked by any of the participating web clients and apps that holding the corresponding SID.
  • sso.getUserID By passing a valid SID, clients can get the user’s system/org-wide ID.
  • sso.getUserDN By passing a valid SID, clients can get the distinct name (DN) of the user, i.e. their directory record.
  • sso.getJson2LdapURL Returns the URL of the Json2Ldap web service.
  • sso.getAnonymousLdapConnection Returns an anonymous LDAP connection (via Json2Ldap) to the back-end directory (if permitted by config).
  • sso.getBoundLdapConnection Returns an LDAP connection (via Json2Ldap) bound as the currently logged-in user (if permitted by config and the web client/app has authorisation).
  • sso.refresh Allows clients/apps to extend a user session by presenting its SID, otherwise it would eventually expire after a preconfigured idle time.
  • sso.getSessionSettings Returns the max idle time, max duration and other settings for a session represented by a given SID.
  • sso.registerLogoutCallback Allows participating web apps to receive a notification that the user has logged out and the session has ended.
  • sso.unregisterLogoutCallback Allows to cancel a previously registered logout notification.
  • sso.listRegisteredCallbacks Lists all web apps that have requested to receive a logout notification.
  • sso.listSessions Lists the details of current or expired sessions. Regular users can only access their own session history. Administrators have full access.
  • ws.getName Returns the web service name.
  • ws.getVersion Returns the web service version.
  • ws.getTime Returns the local web service time.

JsonSSO configuration parameters

This set of parameters governs web client/app access to the JsonSSO service:

  • jsonsso.clients.requireHttps
  • jsonsso.clients.returnAnonymousLdapConnection
  • jsonsso.clients.returnBoundLdapConnection
  • jsonsso.clients.allowLogoutCallbacks

User session limits:

  • jsonsso.sessions.maxTime
  • jsonsso.sessions.maxIdleTime
  • jsonsso.sessions.quotaPerUser
  • jsonsso.sessions.onQuotaExhaustion

Specifies the Json2Ldap URL through which the back-end LDAP directory will be accessed:

  • jsonsso.json2ldap.url
  • jsonsso.json2ldap.trustSelfSignedCerts

Specifies the server details of the back-end LDAP directory. If the useDefault parameter is true JsonSSO will use the default LDAP server for the configured Json2Ldap gateway/proxy.

  • jsonsso.ldapServer.useDefault
  • jsonsso.ldapServer.host
  • jsonsso.ldapServer.port
  • jsonsso.ldapServer.timeout
  • jsonsso.ldapServer.security
  • jsonsso.ldapServer.trustSelfSignedCerts

The uidAttribute parameter specifies the name of the LDAP attribute that holds the system/org-wide user IDs (typically userid but may be something else). If set, the groupDn parameter governs which users are allowed to login via JsonSSO.

  • jsonsso.users.uidAttribute
  • jsonsso.users.groupDn

This set of parameters determines how to derive the user directory record (DN) from the username or email entered at login:

  • jsonsso.dnResolution.method
  • jsonsso.dnResolution.dnTemplate
  • jsonsso.dnResolution.searchFilter
  • jsonsso.dnResolution.searchBaseDn
  • jsonsso.dnResolution.searchUserDn
  • jsonsso.dnResolution.searchUserPassword

This set of parameters determine which users have admin access to the session logs:

  • jsonsso.admin.dn
  • jsonsso.admin.groupDn

Json2Ldap gets mentioned in Network World

Json2Ldap iconThanks to Dave Kearns for mentioning Json2Ldap in his last week’s IdM newsletter for Network World. I hope that would help towards making the software more popular.

Since its 1.0 release at the end of April 2010 initial sales have been rather disappointing. I suppose this has got to do with Json2Ldap being a truly novel product, so potential clients wouldn’t even suspect that such a solution existed. Directory services are typically regarded as a “deep” back-end function and few people involved with LDAP and IdM probably imagine that they can be exposed as a web service in a simple and elegant way. I guess it would take some time and campaigning to change this mindset.

So currently I’m looking for a partner to step up the marketing of Json2Ldap so I can go back to my real job, the greater Transaction Company software project. The LDAP web gateway/proxy was, after all, just a side-product of this project, but still, why not take advantage and its uniqueness and usefulness and help it grow into a popular product on its own?

JsWorld 2.3.1

JsWorld iconEarlier this week I released a new minor version of the JsWorld library for localised formatting and parsing of numbers, currency and date/times in JavaScript.

So what is different in JsWorld 2.3.1?

Those of you familiar with the library know that apart from providing l10n logic, it also comes with a set of 300+ ready locale definitions which can be applied to configure the various formatting, parsing and helper classes for a particular language + country combination. These definitions I derive from the Unicode Common Locale Data Repository (CLDR) and now have been updated to its latest 1.8.1 release.

There has been a small bug since the 1.8 CLDR release, which affects the t_fmt value of the syr_SY locale (Syriac/Syria). Basically, the format string doesn’t include an AM/PM designation which makes display ambiguous and will also result in an error during parsing. I filed a ticket with Unicode and hopefully this bug will get sorted out by the next CLDR release, planned for 27 Oct. 2010.

The other change to JsWorld 2.3.1 is that I added a minified (or compressed) version of the script. There have been some requests in the past to include a minified version, so now you can have that:

  • JsWorld.js – the original script with comments and pretty formatting.
  • JsWorld.min.js – script minified with the JSMin utility by Douglas Crockford.

Otherwise, everything else is just the same with JsWorld 2.3.1. The main reason people buy the library still seems to be the comprehensive currency formatting that it offers.

Example of formatting Euros and South African Rands in the Finnish (fi_FI) locale:

<script type="text/javascript" src="JsWorld.js"></script>
<script type="text/javascript" src="locales/js/fi_FI.js"></script>

// Create locale object from fi_FI data
var locale = new jsworld.Locale(POSIX_LC.fi_FI);

// Create an Euro formatter for the fi_FI locale
var monFormatter = new jsworld.MonetaryFormatter(locale);
alert(monFormatter.format(10000));

// Create a South African Rand formatter for the fi_FI locale
monFormatter = new jsworld.MonetaryFormatter(locale, "ZAR");
alert(monFormatter.format(10000));

Running the above example produces the following formatting:

10 000,00 €
10 000,00 ZAR

Check the library manual on currency formatting if you wish to find out more.

The JsWorld website is at http://software.dzhuvinov.com/jsworld.html

Give your LDAP server a JSON front-end!

LDAP gateway

After several months of on-and-off development, this week finally saw the release Json2Ldap, a new product for LDAP directory integration into web applications through a simple JSON + HTTP protocol.

The software has good potentials to become a success, I believe.

Json2Ldap was conceived last summer during the MyTransactionCenter project. The web application had to connect to an LDAP directory to authenticate users, retrieve employee attributes and query organisational settings such as group memberships and policies. The typical approach in such situations is to program the web server application to handle the necessary LDAP requests and then pass the processed results to the browser for display. This is the established method for working with back-end directories, but I didn’t like it, for it was out of place with the MyTransactionCenter architectural principle — to serve as a flexible aggregator of web content and web services provided by the Transaction Company ecosystem. That’s the essence of modern Ajax/Web 2.0 apps — combining various content and services to produce useful and original mashups.

The intuitive solution? I needed LDAP to “become” a web service, accessible from any JavaScript application running in a browser. This is how the idea of a JSON-to-LDAP gateway was born.

Json2Ldap accepts requests for LDAP operations which are JSON messages received via HTTP POST. JSON + XMLHttpRequest, after all, is the lingua franca in the Ajax/Web 2.0 universe. But instead of devising my own ad-hoc JSON schema, as most people do, I decided to use the JSON-RPC 2.0 protocol, which by that time had stabilised towards becoming a standard and I already had a base Java implementation for it. JSON RPC is a simple protocol for remote procedure calls (RPC), with some XML-RPC heritage, but otherwise is a lot more natural to work with from within JavaScript.

Version 1.0 of Json2Ldap provides about 35 JSON remote procedure calls, which map closely to the standard LDAP operations. It also provides several extensions.

  • Directory connection calls: ldap.connect, ldap.isConnected, ldap.close
  • Directory authentication calls: ldap.bind, ldap.anonymousBind, ldap.simpleBind
  • Directory read operation calls: ldap.getEntry, ldap.compare, ldap.search, ldap.getRootDSE
  • Directory write operation calls: ldap.add, ldap.delete, ldap.modify, ldap.modifyDN
  • Extended directory operation calls: ldap.ext.passwordModify, ldap.ext.whoAmI
  • Directory schema information calls: ldap.schema.getObjectClass, ldap.schema.getAttributeType, etc.
  • Web service information: ws.getName, ws.getVersion, ws.getTime

Json2Ldap is not just about mapping JSON RPC calls to LDAP requests. That was actually the easier bit. Considerable thought was spent to ensure that the gateway provides a well managed and securable web access to the back-end directory servers. The Json2Ldap configuration allows admins to place a number of useful access restrictions and policies, such as:

  • Define whitelists of LDAP servers that gateway clients may connect to
  • Define LDAP connection limits per client and idle timeouts
  • Require TLS/SSL for client-gateway or for gateway-directory connections
  • Require all clients to authenticate at connection time using LDAP bind
  • Refuse directory write requests
  • Predefine “canned” ldap.presetConnect and ldap.presetBind requests.

Json2Ldap was implemented as a lightweight Java web service and is packaged as a WAR file ready for deployment into any servlet container, such as Apache Tomcat. Moreover, you can deploy one gateway instance to serve all your web applications and back-end LDAP directories at the same time. This can save you tonnes of development, maintenance and admin time.

You can find out more about Json2Ldap on its product page. It comes with a rich reference describing configuration and available RPC requests in detail. In the next few weeks I plan to write a few specific usage examples and maybe a small demo application.

Contact me if you have any questions or wish to test the software at your company.

JsWorld – now with number, currency and date/time parsing

Yesterday I released a major update to the JS World library which now adds classes to parse localised number, currency and date/time strings. This feature came about thanks to a client that had purchased a JS World license and later paid for the development of reverse parsing.

The library, now under version 2.3, underwent significant refactoring in order to accommodate the parsing classes: logic that was common to the formatters and the parsers was factored out, which now made it necessary (finally) to introduce a namespace. All JS World code is now packed into a namespace object called “jsworld”. Also, a new class jsworld.Locale was introduced to take care of the validation and encapsulation of the locale properties after loading them from the external datafile.

Here is an example showing how formatting works now:

<!-- Load the JS World classes -->
<script type="text/javascript" src="JSWorld.js"></script>

<!-- Load the en_US locale properties object "POSIX_LC.en_US" -->
<script type="text/javascript" src="locales/js/en_US.js"></script>

<script type="text/javascript">
	try {
		// Create en_US locale object using the loaded locale properties
		var lc = new jsworld.Locale(POSIX_LC.en_US);

		// Create currency formatter configured for the above locale spec
		var formatter = new jsworld.MonetaryFormatter(lc);
		
		// Format a few amounts
		var amount1 = formatter.format(1500);
		var amount2 = formatter.format(-1500);
		var amount3 = formatter.format(7500000.00);
	} catch (error) {
		alert(error);
	}
</script>

And this is a JS World parse example. The steps required to initialise a parser for a particular locale are the same as for formatters.

<!-- Load the JS World classes -->
<script type="text/javascript" src="JSWorld.js"></script>

<!-- Load the de_DE locale properties object "POSIX_LC.de_DE" -->
<script type="text/javascript" src="locales/js/de_DE.js"></script>

<script type="text/javascript">

	var formattedAmount = "-1.234.567,89 €";

	// Create monetary parser for de_DE locale
	var lc = new jsworld.Locale(POSIX_LC.de_DE);
	var parser = new jsworld.MonetaryParser(lc);

	try {
		var parsedAmount = parser.parse(formattedAmount);
		document.writeln("Parsed original amount: " + parsedAmount);
	} catch (error) {
		alert(error);
	}
</script>

You can read more about parsing in the parsing manual.

Finally, JS World 2.3 also introduces a set of functions for working with ISO 8601 date/times:

JS World 2.3 is immediately available for download. The license price remains unchanged at € 495.-

JsWorld 1.4

I’ve just updated the JSWorld library to the latest world locale data derived from Unicode‘s CLDR 1.7.2 (released December 2009). The current JSWorld version is now 1.4.

You can purchase a license and download JSWorld 1.4 from here.

A newer JSWorld version is already planned and work should soon begin on it if all goes well. It will add methods to parse formatted currency amounts, numeric amounts and data/time strings.

Finally, huge thanks to the many people who contribute to the Unicode’s ongoing CLDR process of keeping an up-to-date database of the world’s various locales!