Distinguished Engineer VSPlatform ToolsMonaco Surviving Application Scale JavaScript TypeScript in the Trenches 3583 Web based development tools platform and cloud services What do we do ID: 428435
Download Presentation The PPT/PDF document "Erich Gamma" is the property of its rightful owner. Permission is granted to download and print the materials on this web site for personal, non-commercial use only, and to display it on your personal computer provided you do not modify the materials and that you retain all copyright notices contained in the materials. By downloading content from our website, you accept the terms of this agreement.
Slide1Slide2
Erich GammaDistinguished EngineerVSPlatform Tools/Monaco
Surviving Application Scale JavaScript - TypeScript in the Trenches
3-583Slide3
Web based development tools, platform, and cloud services
What do we do?Slide4
Team Foundation ServerSlide5
IE F12 Source Code ViewerSlide6
TypeScript PlaygroundSlide7
WinJS PlaygroundSlide8
OneDriveSlide9
Visual Studio Online MonacoSlide10
The Road to Monaco
Small
50 kLOC
Modules
Classes
Promises
10% Typescript
Medium
100 kLOC
“AMD”
Lazy Loaded Contributions
50% Typescript
Larger
200 kLOC
Components
API
Dependency Injection
100% Typescript
patterns
TypeScript
2011
2013
2012
sizeSlide11
We enjoy programming
in JavaScript, but…Slide12
Organizing a large and growing code baseNeed to come up with
“compensating” patterns
for classes and modules/namespaces
Refactoring JavaScript code is difficult
“JavaScript
code ‘
rots
’ over time”
“Writing JavaScript code in a large project is like
carving code in stone
”
Describing APIs
Keep the description in synch with the implementation
Concerns with JavaScriptSlide13
Optional and structural typing Fewer type annotations are necessary than you think
Classes, modulesFormalization of common JavaScript patterns
Interfaces
Interfaces named object types for describing the shape of JavaScript objects
TypeScript to the Rescue…Slide14
TypeScript at Work: Interfaces
interface
IModelChangeAccessor
{
insertText
(
position:IPosition
,
text:string
):
IEditorPosition
;
deleteText
(
range:IRange
):
IDeleteTextResult
;
}
interface IEditableTextModel { change(callback: (changeAccessor:IModelChangeAccessor)=>any): …}Interfaces to be implemented Slide15
TypeScript at Work: Interfaces
export interface
IValidationFilter
{
(
resource:IEventEmitter
):
boolean
;
}
public constructor(
filter:
IValidationFilter
)
{
}
new Validator(
(resource)=>
this.includeModel
(resource)
);CallbacksSlide16
TypeScript at Work: Interfaces
interface
ICommonEditorOptions
{
selectOnLineNumbers
?:
boolean
;
glyphMargin
?:
boolean
;
roundedSelection
?:
boolean
;
theme?:string;
readOnly?:boolean; //…}Option bagsSlide17
TypeScript at Work: Interfaces
var
options:IBuildData
=
JSON.parse
(
req.responseText
);
export
interface
IBuildData
{
requestId:string
;
logOutput
?:string;
buildOutput
?:BuildOutput; killOutput?:KillOutput;}JSON structuresSlide18
TypeScript at Work: Interfaces
declare
module
WinJS {
module
Binding {
//...
}
}
class Promise<T> {
//...
}
}
E
xternal types from other librariesSlide19
Promises Pattern
promise.then(
onFulfilled
,
onRejected
);
An object representing a value which may not yet have been computed
onFulFilled
called after a promise is fulfilled, with the promise’s value as its first argument
onRejected
called after a promise is rejected, with the promise’s reason as its first argument
http://promises-aplus.github.io/promises-spec
/
https://github.com/promises-aplus/promises-spec/blob/master/implementations.md
promise.then((result) => {...}, (err) => {...});Slide20
class
Promise<T> {
then<U>(success?: (value: T) => Promise<U>,
error?: (error: any) => Promise<U>,
progress?: (progress: any) => void): Promise<U>;
//…
}
export
interface
ITypeDeclarationSupport {
findTypeDeclaration(position:Editor.IPosition):
Promise<IReference>
;
}
TypeScript at Work:
GenericsSlide21
https://github.com/borisyankov/DefinitelyTypedTypeScript Type Definitions
TSD:
a package manager to search and install
TypeScript
definition files directly from the
DefinitelyTyped
repository.Slide22
TypeScript at Work: Modules
We started with internal modulesSlide23
The Road to Monaco
Small
50 kLOC
Modules
Classes
Interfaces
Promises
10% Typescript
Medium
100 kLOC
“AMD”
Lazy Loaded Contributions
50% Typescript
Larger
200 kLOC
Components
API
Dependency Injection
100% Typescript
patterns
TypeScript
2011
2013
2012
sizeSlide24
Modules are openundisciplined name space contributions…Y
ou can have cyclic dependencies without noticing…
Name spaces have no relationship to the code organization on disk
Renaming files/name spaces is no fun…
Code organization started to rot
Code Organization PainsSlide25
Growing Pains: Order Matters…Slide26
Growing Pains: Dependencies…
“… our
dependency graph was such a mess that each area had a dependency on just about every other area.”Slide27
Growing Pains: Eager loadingSlide28
Separately loaded code
referenced using external module names Implemented in separate source files
Entities are private unless exported
TypeScript: External Modules
File main.ts:
import
adder= require("./adder");
adder.add(3,4);
File adder.ts:
export function
add(op1: number, op2: number):number {
return op1+op2;
}Slide29
CommonJS used by node.js
Asynchronous
Module Definition
(AMD)
requires an AMD compliant module loader, e.g. requireJS
TypeScript: Module Patterns
define
(‘
main
’, [
‘adder'
],
function
(
adder
)
{
// code goes
here adder.add()
});var adder = require(“adder”);adder.add()tsc --module amd main.tstsc --module commonjs main.tsSlide30
AMD in TypeScript vs. JavaScript
AMD in JavaScript
define([‘…./
winjs.base
‘, ‘…./
zoneWidget
’],
function
(WinJS
,
ZoneWidget
) { … }
);
AMD in TypeScript
import
WinJS=
require
('vs/base/lib/winjs
');import ZoneWidget = require('vs/editor/zoneWidget'); Slide31
Server uses node.jsMigrated server to TypeScript once a node.d.ts
file became availableClient migrated to AMD and converted to TypeScript
Common module syntax enables code sharing between client and server
MonacoSlide32
“It feels like fresh showered.
Self contained modules, no more cycles, no more globals, clean file system structure”
After the AMD Migration ImpressionsSlide33
AMD Applied – Lazy Loading
csharp.ts
export class
CSMode
extends
AbstractMode
{
constructor() {
super('
vs.languages.csharp
');
}
// lots of code ….
}
csharp.contribution.ts
modeRegistry.registerMode( [‘text/x-csharp'], new Platform.Descriptor( 'vs/languages/csharp/
csharp', ‘CSMode'));Registered on start-upLoaded on demandSlide34
Pain: “global” CSS filesWant to package CSS files with the JS files into modulesWant to express CSS file dependencies in code
AMD loader pluginsRequired module path can refer to a plugin “plugin!/”
We implemented a
css
loader plugin, that allows to define:
define
(["require", "
vs/
css
!
./
actionbar
",
...], …)
CSS dependencies expressed in a pragma
AMD Applied – CSS DependenciesSlide35
The Road to Monaco
Small
50 kLOC
Modules
Classes
Interfaces
Promises
10% Typescript
Medium
100 kLOC
“AMD”
Lazy Loaded Contributions
50% Typescript
Larger
200 kLOC
Components
API
Dependency Injection
100% Typescript
patterns
TypeScript
2011
2013
2012
sizeSlide36
Migration is code clean-up but real work…Velocity around 300 LOCs per hour
No implicit ‘anys’No missing return types
Towards 100% TypeScript
“As I did conversions, I began
typing various object literals
I was passing around as interfaces. Soon enough
,
I realized how inconsistent I was, the same data was flowing around in at least 3 different formats
.
This is because of the easiness through which you can create literals in JavaScript …. Need some placeholder for data?... Just create a new literal object.” Slide37
Reuse TypeScript code as ‘binary’ JS components with a declarations fileExample using TypeScript language services as a component
Compiler and language services > 30kLOC of TypeScript
Generates a
typescriptservices.d.ts
Componentization
tsc
–declarations
–out typescriptservices.js typescript.tsSlide38
We were on the bleeding edge……but we expected it and had plenty of band aid
We would do it again, the benefits outweigh the painsConfidence, refactoring agility, tooling, fun
We would start with TypeScript (and
CommonJS
/AMD) from the beginning
TS RetrospectiveSlide39
Friday 2:00-3:00pm Building Websites using VSOnline Monaco Chris Dias
Related TalksSlide40
TypeScriptwww.typescriptlang.org
AMDhttp://requirejs.org/docs/whyamd.html
TFS use of TypeScript
http://
blogs.msdn.com/b/bharry/archive/2012/10/24/typescript-a-real-world-story-of-adoption-in-tfs.aspx
Monaco VS Online
Get
started with the
Monaco Channel9 Series
Keep
informed on the
Monaco
Blog
Resources Slide41
for MSDN Ultimate subscribers
Go to
http://msdn.Microsoft.com/specialoffers
SPECIAL OFFERS
Partner ProgramSlide42
Your Feedback is Important
Fill out an evaluation of this session
and help shape future events.
Scan the QR code
to evaluate
this session on your mobile device.
You’ll also be entered into
a daily prize drawing!Slide43
©
2014
Microsoft Corporation. All rights reserved. Microsoft, Windows, Windows Vista and other product names are or may be registered trademarks and/or trademarks in the U.S. and/or other countries.
The information herein is for informational purposes only and represents the current view of Microsoft Corporation as of the date of this presentation. Because Microsoft must respond to changing market conditions, it should not be interpreted to be a commitment on the part of Microsoft, and Microsoft cannot guarantee the accuracy of any information provided after the date of this presentation. MICROSOFT MAKES NO WARRANTIES, EXPRESS, IMPLIED OR STATUTORY, AS TO THE INFORMATION IN THIS PRESENTATION.