Versioning Language Features in JScript


With Internet Explorer 8 we introduced several new JScript language features including native JSON support and accessor methods for Mutable DOM prototypes. Of course, any new language feature introduces compatibility risk and one of the main pieces of feedback we received was that we needed to provide a smart way for developers to opt in or out of these new language features.


 


So in the JScript engine shipped as a part of Internet Explorer 8, we introduced a versioning switch which enables developers to choose the JScript language set they want to support. Web developers can opt-in/opt-out of select JScript language features by using IE8’s Document Compatibility, which depends upon the layout (or document) mode in which web content is loaded.


 


Potential Issue: Example


As an example, let’s look at IE8’s native JSON support. We added this support to the engine by adding a global JSON object with built-in parse() and stringify() methods, as per the draft ES3.1 specification, now called the ECMAScript Fifth Edition. Now, for the sake of example, let us pretend that the JScript engine did not allow language versioning and a site implemented a JSON call like this:


 



   1: if(!this.JSON) // check for non-existence of JSON object/functions


   2: {


   3:     //<define a JSON object>


   4:     //<define a non-standard compliant encoder function – JSON.encode>


   5:     //<define a non-standard compliant parser function – JSON.parse>


   6: }


   7: 


   8: //somewhere in the code


   9: JSON.encode(myObj);                         


 


For IE7, since no JSON object existed by default, the if check would evaluate to true and the user defined JSON object and encoder/decoder methods would be defined. The call to JSON.encode() would work as wanted.


 


However, for IE8, the existence of the native JSON object would cause the if check to evaluate to false and no user defined method would be available. The call to JSON.encode() would now fail, which would produce unexpected application behavior, since no such method was defined.


 


JScript Versioning in Internet Explorer 8 (for Web Developers)


Web developers can now avoid such issues by choosing an appropriate layout (or document) mode for their content. Choosing the layout mode as “Internet Explorer 8 Standards Mode” opts in to the JScript language features supported by version 5.8 JScript engine. Choosing the layout mode to be any mode other than the “Internet Explorer 8 Standards” mode, would imply an opt-in to support JScript language feature set equivalent to the one shipped in version 5.7 of the JScript engine (equivalent to the one shipped in IE7). Going back to the example above, the site owner can either update the code to start taking advantage of native JSON support and use the “Internet Explorer 8 Standards” mode, or can choose any other layout mode to use the existing code as is, thus maintaining  compatibility with IE7.


 


While a dependency on the document mode implies that developers will need to make a switch to both IE and JScript level features and can’t single out/opt-in only to the JScript changes, we did not want to introduce a new version vector specifically for the JScript engine. We wanted to support the same system used by IE8 overall for standards support.


 


You could read more about IE8’s Compatibility View feature in Scott Dicken’s blog Just The Facts: Recap of Compatibility View and the MSDN documentation for Defining Document Compatibility.


 


JScript Versioning in other JScript Hosts (for JScript Host Developers)


Apart from Internet Explorer, there are various other hosts such as Windows Script Host, CScript etc. which host the JScript engine, To avoid similar compatibility issues and enable hosts to choose a particular JScript language feature set, the JScript engine now exposes an IActiveScriptProperty::SCRIPTPROP_INVOKEVERSIONING property.


 


To opt in to a set of language features that should be supported by the JScript script engine, the host needs to invoke the IActiveScriptProperty::SetProperty and set SCRIPTPROP_INVOKEVERSIONING to one of the values below during the engine initialization:



  • 1 (or SCRIPTLANGUAGEVERSION_5_7):  To use the language features equivalent to those shipped in Version 5.7 (or IE7) of the JScript engine

  • 2 (or SCRIPTLANGUAGEVERSION_5_8):  To use the language features available in Version 5.8 (or IE8) of the JScript script engine. This includes features available in version 5.7 and the language changes introduced in version 5.8.

 


By default, the set of language features supported by the JScript script engine is set to 0 (or SCRIPTLANGUAGEVERSION_DEFAULT), equivalent to the language feature set shipped in version 5.7 of the JScript engine, unless the host chooses to support a different default behavior.                                                                                                                                                  


 


List of features versioned


Right now, only nine JScript features are versioned like this:



  • Native JSON support – This would introduce a new built-in JSON object, and the following built-in methods – JSON.parse(), JSON.stringify(), Date.toJSON(), Number.toJSON(), Boolean.toJSON() and String.toJSON()

  • Support for accessor methods for enabling Document Object Model prototypes

  • Default the separator to “,” if the separator value is ‘undefined’ in Array.prototype.join

  • Return the length of the resultant array instead of ‘undefined’ for Array.prototype.unshift

  • Call toString() if precision is ‘undefined’ instead of throwing a “RangeError” for Number.prototype.toPrecision

  • Support for array subclassing

  • Support for trailing commas in object literals

  • Implemented Error.prototype.toString to provide better error messages

  • Support for index operator [] on string values

 


I hope JScript versioning will help ensure that the IE8 end user experience is compatible with IE7 and will give developers some time to update their code to take advantage of these new language enhancements.


 


Gaurav Seth


Program Manager, JScript

Comments (26)

  1. Thank you for submitting this cool story – Trackback from DotNetShoutout

  2. Stoyan says:

    I find this.JSON is not very robust change too easy to fail if I forget var anywhere in the code

    mby something more verbose?

    if (typeof JSON === "object" && typeof JSON.encode === "function"){

       //

    }

  3. OMFG says:

    Are you seriously out to lunch?! or did you fail to clarify that this DOES NOT apply to normal IE web browser development?

    if in IE8 I need to check/set variables:

    SCRIPTLANGUAGEVERSION_5_7

    or

    SCRIPTLANGUAGEVERSION_5_8

    In order to get/not get method availability in ===> JAVASCRIPT <===

    Then this plan is seriously mega-flawed.

    the language attribute on script tags is already deprecated because IE !@#$ed it up in earlier versions so we no longer do stuff like:

    <script language="JavaScript1.2">…

    Please clarify that developers DO NOT NEED TO SET ANYTHING to get the MAXIMUM JavaScript implementation that IE8 supports.

    If you can’t, please jump on the IE Blog and disclose this disaster to the developers that will be affected by this and start ducking when they start throwing the furniture.

    OMFG!

  4. Smith says:

    OMFG,

    I think you are mistaken. The usage of IActiveScriptProperty::SetProperty is in my opinion for other JSCript hosts like WScript, CScript etc. For IE8, the feature is aligned with whether you are running your sire in standards mode or not which makes sense to me at least. IE8 standards mode is to enable IE run as a browser which is more compatible with standards. So running the new JScript compliant feature in a different/default would break this.

    However I would like to hear what happens if I call IActiveScriptProperty::SetProperty from JScript running within the browser (IE).

    Thanks,

    Smith

  5. GauravS says:

    @OMFG: Smith’s reasoning is correct. The JScript language features are tied to the document mode chosen by a web page. If the document mode is “IE8 Standards”, all the nine features mentioned above are switched on. For all other document modes, these features are not available (equates to language support as it existed in IE7).

    One of the ways in which a web developer can choose to use the IE8 Standards mode (and get the most of the JScript language changes) is by using the X-UA-Compatible meta tag <meta http-equiv="X-UA-Compatible" content="IE=IE8"> as described in  http://msdn.microsoft.com/en-us/library/cc288325(VS.85).aspx.

    The SCRIPTLANGUAGEVERSION flags are not for use by web developers. They are meant for developers creating new JScript hosts by using the IActiveScript interfaces (like developers creating a browser, WScript host etc.)

    @Smith: From versioning perspective, calling IActiveScriptProperty::SetProperty from JScript running within the browser (IE) is not a supported scenario. It will not impact the language support chosen by the page (which is based on the document mode) and cannot be used to switch between the different support levels.

  6. AndyE says:

    So there’s no way of activating the new JScript features without enabling IE8 standards mode for the DOM?

    That seems pretty poor if you’re a Windows Desktop Gadget developer – using the new JScript features is impossible without risking backwards compatibility with IE7 users.

    It seems like Gadget design is going the way of the web design – we can’t adopt new standards until years after they appear when IE7 market share drops to below 5%/10%

  7. Mitch 74 says:

    @AndyE: you can still use the software-only implementation of the JSON object – which would allow your gadget to work with "native" IE6 and IE7 too.

  8. CB says:

    Why won’t you support the latest scripting and html features in your releases ? You are always behind competitors for absolutely no good reason.

    Where is for example the HTML5 support for things like <CANVAS> currently supported (for a long time) by Firefox and Chrome.

    Is it because you fear nobody would use Silverlight if there was an easy browser independent way to do animations and video without plugins ??

    SVG support is aboslutely not the same thing since it isn’t even fully scriptable.

    And why did we need to wait until IE8 to get standards support ?? Amazing.

    You need to lead the development, not lagg behind competitors all the time !!!

  9. warrens says:

    CB, I realise it’s "cool" to complain anonymously on the Internet.  But, try and be reasonable.  

    Yes, CSS3, HTML5 and SVG are important, but Microsoft has taken the right path so far with fixing the much more widely-used CSS 2.1 standard first, before moving on to the emerging standards.

    It’s what they told us they were going to do, and it’s what they’ve delivered: IE8 actually has a more complete implementation of CSS 2.1 than Firefox and Opera.  One of the big standards-testing web sites measures IE8’s CSS 2.1 compatibility at 99%… the other browsers are in the low-90s, mainly due to broken / incomplete implementations of CSS 2.1 pseudo-elements and at-elements.

    http://www.webdevout.net/browser-support-summary?IE7=on&IE8=on&FX2=on&FX3=on&OP9=on&SF2=on&uas=CUSTOM

    You might as well be asking why we’re still waiting for Firefox to get "standards support", especially considering they’ve been saying they’ve had it for years.

  10. -TNO- says:

    Maybe I’m just ignorant, but is there a better example on how to enable the new JScript version in WSH/ASP? A registry setting perhaps? The example given doesn’t quite lend itself to web developers and system administrators seeking to use these new features.

  11. GauravS says:

    @TNO: These new language features are currently not supported/versioned by hosts other than Internet Explorer. Hosts other than IE such as WSH/ASP will automatically use the latest vesrion of JScript installed on the machine. However, the language feature support is equivalent to that of JScript v5.7.

  12. Neiyuki says:

    Is there any way to enable the 5.8 features in WSH?

    Or will you going to change the WSH executables?

  13. @Neiyuki: The WSH currently does not support the 5.8 features. However, you can use script based work-arounds for some of the 5.8 features like JSON.

  14. John says:

    @GauravS: There is a growing demand for being able to use these new features in hosts other than IE, such as WSH/ASP. Is there any reason why there is no option to select the 5.8 feature set for these hosts?

    Could a method for selecting a version be provided? Possibly a Registry setting, or better still:

    ScriptEngine.set(‘5.8’);

  15. GauravS says:

    @John: Due to the possible side-effects, there is no simple mechanism which can enable these features unless the host makes a change to enable the new feature-set.

    If the feature you are looking at is JSON support, you can use the JSON imlementation from http://www.JSON.org as a workaround.

  16. John says:

    @GauravS: What sort of side-effects are you referring to? Things could work in exactly the same manner as IE8, the developer opts-in. As far as I am aware the whole point of the IE8 "opt-in" was to avoid side-effects.

    Surely the JScript feature set could provide a script based opt-in such as:

    ScriptEngine.set(‘5.8’);

    What would be the problem in implementing such a feature in a future revision?

    Server-side JavaScript is gaining momentum and Microsoft has an excellent platform for this in ASP 3.0. It seems wrong using script based JSON implementations when the native feature is there, just no way to access it.

    Thanks,

    John

  17. GauravS says:

    @John: I was referring to the use of registry keys to switch versions. No such support is available.

    Thanks for your feedback! Will consider the approach you suggest for the future versions.

  18. Sergei says:

    Are you saying the side effect is registry keys? I was thinking side effect meant something in functionality. And why only registry key to switch version? You can as well do it at runtime. Can you tell us why other hosts apart from IE cannot do this switch at runtime. I understand the IActive* way of integrating with JavaScript, but I cannot understand why one host can do it from native code while others can’t and need registry settings to do the same? Can you explain please.

    Thanks.

  19. John says:

    @Sergei: I was under the same impression, that the side-effects were to do with the functionality being exposed to other hosts, however, this doesn’t seem to be the case. There aren’t any registry keys to enable the hidden functionality, I had just suggested it. Obviously a registry setting would be a less than ideal solution.

    @GauravS: If there aren’t any side-effects related to exposing the hidden functionality, then I really can’t understand why a script based method isn’t provided to switch between engines? This would provide much more flexibility to the developer whilst also making it host independent. I would imagine that it would be a trivial thing to implement?

    I appreciate your comment on considering this for a future release, if this type of thing isn’t implemented, then any new features that are added will again be inaccessible which would be a real shame.

    Hopefully you could push this through sooner rather than later, and we could all enjoy the hard work the JScript team has done in bringing us these new features.

    Thanks,

    John

  20. Nigel says:

    So, how do you actually set IActiveScriptProperty::SetProperty for WSF script?

  21. I think you are mistaken. The usage of IActiveScriptProperty::SetProperty is in my opinion for other JSCript hosts like WScript, CScript etc. For IE8, the feature is aligned with whether you are running your sire in standards mode or not which makes sense to me at least. IE8 standards mode is to enable IE run as a browser which is more compatible with standards. So running the new JScript compliant feature in a different/default would break this.

    However I would like to hear what happens if I call IActiveScriptProperty::SetProperty from JScript running within the browser (IE).

    Thanks,

  22. Dolmen says:

    I hope we will get ES5 features in an upgraded WSH and more generally in JScript as a generic scripting engine.

  23. STF says:

    And how are we supposed to "the host needs to invoke the IActiveScriptProperty::SetProperty and set SCRIPTPROP_INVOKEVERSIONING to one of the values below during the engine initialization"?  Some example please?

  24. Byron says:

    The undocumented "feature" of the SetProperty with SCRIPTPTOP_INVOKEVERSIONING is that the value must be a VT_I4 or VT_I2 – any other integer type will be rejected as invalid.

    Here's the code scrap where I create my language engine.

    HRESULT result = CoCreateInstance(m_LanguageId, 0, CLSCTX_ALL, IID_IActiveScriptProperty, (LPVOID*) &m_pScriptProperty);

    if (result == S_OK && m_LanguageId == CLSID_JScript)

    {

    VARIANT set;

    set.vt = VT_I4;

    set.intVal = SCRIPTLANGUAGEVERSION_5_8;

    if (m_pScriptProperty->SetProperty(SCRIPTPROP_INVOKEVERSIONING, NULL, &set) != S_OK)

    m_bLoadJSONLibrary = true;

    }

  25. Chris says:

    @STF, yeah me too. I'm using IIS 7 and ASP. An example please.

Skip to main content