Practical TypeScript

Eliminate the Barrier Between JavaScript and HTML (or Anything Else)

The JSX tool lets you describe your page as a set of custom elements that you define in TypeScript classes. Those elements then add to the page whatever text or code makes sense to you.

JSX is an XML based language that, combined with TypeScript (or JavaScript) generates JavaScript which, in turn, writes out your page's HTML. For example, this JSX/XML code generates a div element in your page:

<div />

That is, that JSX code will generate the div element eventually. If you're using React to process your JSX code then your TypeScript file actually generates a JavaScript file with React-based code that will write the div element out to your page. That will look something like this:

React.CreateElement("div")

Which raises the question: What's the point? The critical issue is that JSX allows you to tie TypeScript class to your own custom elements which add whatever you want to the page. This JSX element adds to the page whatever is specified by the Customer class the element is tied to:

<Customer update="false" custId="A123" onBlur={ () => validate(this.value)}
                                       onClick={ () => Update() } />

In addition, the React code is sufficiently smart that, as your custom element updates its HTML, the existing HTML isn't blindly deleted and replaced. Instead, React compares the HTML generated from your code with the page's current HTML and updates only where necessary. JSX also has a single event handler that processes all events rather than having a separate handler for each element/event combination which reduces memory consumption.

I'm being narrow-minded, however, to keep referring to HTML. JSX can be converted into anything you want (NetFlix defines its pages in JSX so it can convert those pages into the appropriate output for individual platforms). In this column, I'll walk you everything you need to do to set up Visual Studio to work with the latest version of JSX and get up your first "Hello, World" page.

Getting Visual Studio Ready
Getting Visual Studio ready to work with JSX does require that you add some additional tools because of some recent changes in React (the tool that processes JSX elements). In late 2015, React 0.14 (the latest version as I write this), made some major changes to the React library structure. React is now split into two major libraries called React and ReactDOM. The problem from your point of view is that the files you need to work with JSX and React in TypeScript aren't all available through NuGet.

To deal with this, you'll need to use two package managers: npm (to get the latest versions of React from node) and tsd (to get the latest versions of the DefinitelyTyped files for React). Before attempting to use either of those I also suggest you get Mads Kristensen's Package Installer which provides a simple front end to working with a variety of package installers (NuGet, npm, tsd, and more). Why make your life more complicated than it needs to be?

To install Mads' utility from Visual Studio's Tools menu, select Extensions and Updates. Then, from the Online tab, search for Package Installer and install it.

Your next step is to use Mads' Package Installer to add tsd to Visual Studio (npm is probably already installed with your copy of Visual Studio). Begin this process by right-clicking on your solution in Solution Explorer and selecting the entry for Mad's utility: Quick Install Package. When the Quick Install Package dialog appears, make sure that the dropdown list on the left is set to npm then enter "tsd" in the textbox, click the install button, and wait patiently for tsd to install (you'll see the completion messages in your Output window, provided that the dropdown list at the top of the window is set to Package Installer).

With Quick Install Package and tsd in place, you're ready to start adding the libraries you need. One last note about configuring Visual Studio: I'm using TypeScript 1.8.0, installed from TypeScriptLang.org.

Configuring Your Project and Page
To get the script libraries stay in Quick Install Package. With the dropdown on the left still set to npm, enter "react" in the text-box and click the Install button. Repeat for "react-global". Now, to add the type definition files for those script libraries, set the dropdown list on the left to tsd, enter "react" in the textbox, click the Install button and wait. Repeat for "react-global".

Now you need to configure your project to use JSX. TypeScript offers you two modes for working with JSX: react (which fully compiles your JSX elements and TypeScript code into JavaScript and produces a .js file) or preserve (which compiles your TypeScript code into JavaScript but leaves your JSX elements alone and produces a .jsx file). The preserve mode allows you to feed your JavaScript file to another JSX interpreter for processing. One example of a JSX processor is Babel, which converts the current version of JavaScript (ES6) to earlier versions.

To use JSX, you have to set one of those options, either in your project's properties on the TypeScript Build tab or in your tsconfig.json file. Setting the react mode in the tsconfig file looks like this:

"compilerOptions": 
 {
    "jsx": "react",
    "sourceMap": true,
     ... more options ...

Now you can start using the script libraries and definition files you added earlier. You'll need the ReactWithAddOns script library in your page or View so that you can use the React libraries. To use the library you added with npm, in Solution Explorer, refresh your view, and then turn on Show All Files.

You'll find the library you should use in the node_modules/react/dist folder. Dragging it into your page or View will generate this script tag:

<script src="~/node_modules/react/dist/react-with-addons.js"></script>

In practice, however, I found that I couldn't get that library to work reliably for me. So, instead, I added these script tags to my page to use the two required libraries from the official source:

<script src="https://cdnjs.cloudflare.com/ajax/libs/react/0.14.7/react.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/0.14.7/react-dom.js"></script> 

You'll also need an element to hold the output of your custom tag. I added a div element with an id of divHello before any of my script tags to my page. Altogether my page looked like this:

<body> 
    <div id="divHello"/>        
    
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react/0.14.7/react.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react/0.14.7/react-dom.js"></script>
</body>

Writing JSX
You're ready to start writing some TypeScript with JSX. First, right-click on your Scripts folder and select Add | TypeScript JSX file. Picking this choice adds a file with an extension of .tsx to your project. In your TypeScript file you just need a reference to the react-global.d.ts definitions file which is in the typings/react folder (notice that this isn't under the Scripts folder). Drag the file into your .tsx file to give this reference:

/// <reference path="../typings/react/react-global.d.ts" />

To test that everything's set up and able to work, enter the code in Listing 1 into your .tsx file following the reference.

Listing 1: Hello, World in TypeScript and JSX

interface propsHello {
    salutation: string;
    name: string;
}

class Hello extends React.Component<propsHello, {}> {
    render() {
        return <span>{this.props.salutation} + ", " + {this.props.name}</span>
    }
}

You can now ask React to render a tag for you like this:

<Hello salutation="Hello" name="World"/>

You can't, however, just add your custom tag to the page: You need to call the render method on the ReactDOM object passing your custom tag and a reference to the element where you want the output displayed. That code should follow the previous code in your .tsx file and look like this:

  ReactDOM.render(
        <Hello salutation="Hello" name="World"/>,
        document.getElementById('divHello'));

To test your TypeScript/JSX file, you'll need to add the JavaScript file generated from your .tsx file to your page or View. To do that, find the .js file and drag into your page after the script tags for your React libraries. I called my file HelloWorld.tsx, so my script tag looked like this:

<script src="~/Scripts/HelloWorld.js"></script>

Now, when you press F5 and your browser displays your page you'll be welcomed to the world of JSX with TypeScript. In my next Practical TypeScript column, I'll show you what you can do there.

About the Author

Peter Vogel is a system architect and principal in PH&V Information Services. PH&V provides full-stack consulting from UX design through object modeling to database design. Peter tweets about his VSM columns with the hashtag #vogelarticles. His blog posts on user experience design can be found at http://blog.learningtree.com/tag/ui/.

comments powered by Disqus
Upcoming Events

.NET Insight

Sign up for our newsletter.

I agree to this site's Privacy Policy.