Skip to content

Commit

Permalink
Merge branch 'source' of https://github.com/artsy/artsy.github.io int…
Browse files Browse the repository at this point in the history
…o oma_relay
  • Loading branch information
orta committed Apr 9, 2019
2 parents 78ddd79 + 2ddc815 commit 856a1d0
Show file tree
Hide file tree
Showing 12 changed files with 447 additions and 125 deletions.
2 changes: 2 additions & 0 deletions .vscode/settings.json
Expand Up @@ -66,6 +66,8 @@
"apps",
"art.sy",
"async",
"behaviour",
"behaviours",
"blog",
"cocoadocs",
"cocoapods",
Expand Down
Binary file modified _design/artsy_open_source.sketch
Binary file not shown.
16 changes: 16 additions & 0 deletions _includes/_series_bio/omakase.md
@@ -0,0 +1,16 @@
### The Artsy Omakase

We gave our JavaScript stack for web and iOS the name "Artsy Omakase" and it represents using:

- React
- Relay
- GraphQL
- Styled Components
- TypeScript
- Storybooks
- Jest
- VS Code

To create a coherent open source development environment with great developer tools that makes it really easy to
fall into the pit of success on large projects. You can watch an overview video from @orta
[on Artsy's YouTube](https://www.youtube.com/watch?v=1Z3loALSVQM) from our React Native conference in 2018.
109 changes: 78 additions & 31 deletions _posts/2016-08-15-vscode.markdown
Expand Up @@ -4,92 +4,136 @@ title: "Using VS Code for JavaScript"
date: 2016-08-15 22:17
author: orta
categories: [tooling, danger, node, reactnative]
series: React Native at Artsy
series: Omakase
---

<center>
<img src="/images/vscode/vscode_logo_artsy.svg" style="width:300px;">
</center>

I'm an old school TextMate user, who has also been using Xcode for the last decade. These two sit at a very opposite ends of an "editor" spectrum.
I'm an old school TextMate user, who has also been using Xcode for the last decade. These two sit at a very
opposite ends of an "editor" spectrum.

TextMate is extremely bare bones at the core, but introduced the idea of bundles as plugins. Making it really easy for others to build their own plugins for their own contexts. Xcode on the other-hand includes a 3D scene editor, the best interface builder I've seen, super rich debugging tools and close to zero support for improving it yourself.
TextMate is extremely bare bones at the core, but introduced the idea of bundles as plugins. Making it really easy
for others to build their own plugins for their own contexts. Xcode on the other-hand includes a 3D scene editor,
the best interface builder I've seen, super rich debugging tools and close to zero support for improving it
yourself.

As we agreed on moving to React Native, we needed to decide what the team should use for [working in that environment][emission_vscode_docs]. After experimentation with many editors, we decided on Microsoft's [Visual Studio Code][vs_code].
As we agreed on moving to React Native, we needed to decide what the team should use for [working in that
environment][emission_vscode_docs]. After experimentation with many editors, we decided on Microsoft's [Visual
Studio Code][vs_code].

We wanted to keep a lot of the best features from Xcode, while working in a completely JavaScript environment. For example: debuggers, inline errors, auto-complete, symbol mapping and to ideally have them all inside a single editor.
We wanted to keep a lot of the best features from Xcode, while working in a completely JavaScript environment. For
example: debuggers, inline errors, auto-complete, symbol mapping and to ideally have them all inside a single
editor.

Let's dig into the principals of how Visual Studio Code works, what makes it a better option for us, and what parts of it really shine.
Let's dig into the principals of how Visual Studio Code works, what makes it a better option for us, and what parts
of it really shine.

<!-- more -->

---

### What is Visual Studio Code?

Visual Studio Code (VS Code) is _yet another_, JavaScript-based text editor. It's built atop of GitHub's [Electron][electron]. Electron is a framework for writing native apps as easy as building websites. It started as a web component for some Microsoft web-service, and eventually evolved into a fully-fledged text editor.
Visual Studio Code (VS Code) is _yet another_, JavaScript-based text editor. It's built atop of GitHub's
[Electron][electron]. Electron is a framework for writing native apps as easy as building websites. It started as a
web component for some Microsoft web-service, and eventually evolved into a fully-fledged text editor.

#### IDE - Editor hybrid

Visual Studio Code (VS Code) believes that the sweet-spot between and IDE and a plain Text Editor, is somewhere a little bit closer to the IDE side.
Visual Studio Code (VS Code) believes that the sweet-spot between and IDE and a plain Text Editor, is somewhere a
little bit closer to the IDE side.

{% include epic_img.html url="/images/vscode/editors.png" title="Editors" style="width:100%;" %}

This means instead of the Text-Editor style folder based approach, VS Code expects to set up a project structure per-project to start supporting from of the more useful IDE-like features.
This means instead of the Text-Editor style folder based approach, VS Code expects to set up a project structure
per-project to start supporting from of the more useful IDE-like features.

It supports TextMate style plugins (called Extensions) through a controlled, but expanding [extension API][vs_extensions]. The extension API work takes an [Apple-like][xpc] approach to ensuring stability by having all extensions run outside of the host process. [This approach][extensions_approach] ensures any extension crash does not take down the editor.
It supports TextMate style plugins (called Extensions) through a controlled, but expanding [extension
API][vs_extensions]. The extension API work takes an [Apple-like][xpc] approach to ensuring stability by having all
extensions run outside of the host process. [This approach][extensions_approach] ensures any extension crash does
not take down the editor.

It's also smart about deciding when to load an extension, for example, my [Danger][danger_code] extension will [only load][danger_vscode_load] if there is a `Dangerfile` in the root of the workspace.
It's also smart about deciding when to load an extension, for example, my [Danger][danger_code] extension will
[only load][danger_vscode_load] if there is a `Dangerfile` in the root of the workspace.

These two approaches to extensions are specifically aimed at [addressing issues][atom_slow] seen inside Atom, where any user actions can be / are blocked by extensions, and extensions have full-reign to make any change they want. Even on my Mac Pro, there is a noticable lag. I initially assumed this was the "JavaScript tax" for all Electron apps, but VS Code is fast.
These two approaches to extensions are specifically aimed at [addressing issues][atom_slow] seen inside Atom, where
any user actions can be / are blocked by extensions, and extensions have full-reign to make any change they want.
Even on my Mac Pro, there is a noticable lag. I initially assumed this was the "JavaScript tax" for all Electron
apps, but VS Code is fast.

### Making Intellisense

By default a JavaScript project does not have a way to provide auto-completion, or in VS Code's terminology: Intellisense. Trying to make auto-complete based on a [REPL][repl] can only get you so far, because it has to be wary against functions with side-effects. Other alternatives are to build an [AST][ast] from the code, and then introspect that.
By default a JavaScript project does not have a way to provide auto-completion, or in VS Code's terminology:
Intellisense. Trying to make auto-complete based on a [REPL][repl] can only get you so far, because it has to be
wary against functions with side-effects. Other alternatives are to build an [AST][ast] from the code, and then
introspect that.

In Xcode the auto-complete tools are powered by the type systems of Objective-C and Swift. This means that you can know the structure of an object, without having to dig inside it, potentially breaking it in the process. Vanilla JavaScript does not have a type system. There are a few root classes though: String, Object, Number etc.
In Xcode the auto-complete tools are powered by the type systems of Objective-C and Swift. This means that you can
know the structure of an object, without having to dig inside it, potentially breaking it in the process. Vanilla
JavaScript does not have a type system. There are a few root classes though: String, Object, Number etc.

To work around this problem, VS Code uses [TypeScript][ts] behind the scenes. TypeScript is a language that compiles down to JavaScript which provides a typing structure on top of JavaScript. This is a similar approach to how [Flow works][flow] too, which is the language [we write React Native][flow_pr] in.
To work around this problem, VS Code uses [TypeScript][ts] behind the scenes. TypeScript is a language that
compiles down to JavaScript which provides a typing structure on top of JavaScript. This is a similar approach to
how [Flow works][flow] too, which is the language [we write React Native][flow_pr] in.

This can work out really well for your own classes if you are declaring your types, but the npm ecosystem is _full_ of untyped JavaScript, and a lot of your work is about sitting atop those abstractions. The fix for this is offered via [DefinitelyTyped][dt] which provides type definitions for popular npm modules. For example here is [one for Redux][dt_redux] - these act like [header files in Objective-C][switch_header] - offering inline documentation, and the shape of the object.
This can work out really well for your own classes if you are declaring your types, but the npm ecosystem is _full_
of untyped JavaScript, and a lot of your work is about sitting atop those abstractions. The fix for this is offered
via [DefinitelyTyped][dt] which provides type definitions for popular npm modules. For example here is [one for
Redux][dt_redux] - these act like [header files in Objective-C][switch_header] - offering inline documentation, and
the shape of the object.

I use an extension to keep these up to date and to have them installed in every project I work in: [Types auto installer][types]. Here's an example of auto-complete for [a Redux store][redux_store].
I use an extension to keep these up to date and to have them installed in every project I work in: [Types auto
installer][types]. Here's an example of auto-complete for [a Redux store][redux_store].

{% include epic_img.html url="/images/vscode/redux.png" title="Redux" style="width:100%;" %}

It'll also provide information about the parameters, which is a life-saver for me. Having grown up with [named][swift_params] [parameters][ruby_params].
It'll also provide information about the parameters, which is a life-saver for me. Having grown up with
[named][swift_params] [parameters][ruby_params].

{% include epic_img.html url="/images/vscode/redux-params.png" title="Redux Params" style="width:100%;" %}

### Runtime
### Runtime

Using console logs to debug isn't an acceptable answer when debugging for me anymore. [That's churn][churn] that I'm not willing to lose time to. Luckily for me, VS Code supports debugging across many languages.
Using console logs to debug isn't an acceptable answer when debugging for me anymore. [That's churn][churn] that
I'm not willing to lose time to. Luckily for me, VS Code supports debugging across many languages.

It does this by having a generic VS Code [Debug Protocol][vscode_debug] which lets extensions use their own processes to run the debugger. So the ruby debugger runs on the [`ruby-debug-ide`][ruby_debug] gem, and for node-based projects it uses the debugger built into node.
It does this by having a generic VS Code [Debug Protocol][vscode_debug] which lets extensions use their own
processes to run the debugger. So the ruby debugger runs on the [`ruby-debug-ide`][ruby_debug] gem, and for
node-based projects it uses the debugger built into node.

So, here is a common case. I want to start up my web-server, so I need to run `npm dev`. I can run this from VS Code:
So, here is a common case. I want to start up my web-server, so I need to run `npm dev`. I can run this from VS
Code:

{% include epic_img.html url="/images/vscode/start.png" title="Editors" style="width:100%;" %}

Once that's running - I can attach a debugger. This is listing all of the available node processes on my computer:

{% include epic_img.html url="/images/vscode/attatch.png" title="Editors" style="width:100%;" %}

Then I can add a breakpoint, and when it is triggered, I have a full stack trace and REPL. The REPL is very barebones, for example - there's no auto-complete. However, it's good for quick exploration. I keep [accidentally prefixing][po] my REPL code with `po`.
Then I can add a breakpoint, and when it is triggered, I have a full stack trace and REPL. The REPL is very
barebones, for example - there's no auto-complete. However, it's good for quick exploration. I keep [accidentally
prefixing][po] my REPL code with `po`.

{% include epic_img.html url="/images/vscode/debug.png" title="Editors" style="width:100%;" %}

The breakpoint works through a [source map][source_map], and so the line you expect is the one that you're working in. That stuff is all pretty magic to me. Good on Microsoft, and the node community for pulling that off.
The breakpoint works through a [source map][source_map], and so the line you expect is the one that you're working
in. That stuff is all pretty magic to me. Good on Microsoft, and the node community for pulling that off.

### Wrapup

I still feel a little bit uncomfortable in JavaScript projects, as a long-time native developer. However feel like VS Code is a nice mix of the freeform "just do something" style of Text Editors, which work across a lot of systems and the tight-knit IDEs that are bound to a specific domain. It can be a bridge between worlds.
I still feel a little bit uncomfortable in JavaScript projects, as a long-time native developer. However feel like
VS Code is a nice mix of the freeform "just do something" style of Text Editors, which work across a lot of systems
and the tight-knit IDEs that are bound to a specific domain. It can be a bridge between worlds.

VS Code has become my main editor in Ruby and JavaScript, due to having great support for the projects and being an OSS project which I feel like I can contribute to. No more being [locked out][xcode8] of improving my editor. Awesome!
VS Code has become my main editor in Ruby and JavaScript, due to having great support for the projects and being an
OSS project which I feel like I can contribute to. No more being [locked out][xcode8] of improving my editor.
Awesome!

[danger_tweet]: https://github.com/rubyide/vscode-ruby/pull/41
[vs_code]: https://code.visualstudio.com/
[electron]: http://electron.atom.io
[vs_code]: https://code.visualstudio.com/
[electron]: http://electron.atom.io
[nav]: https://github.com/artsy/team-navigator
[repl]: https://en.wikipedia.org/wiki/Read–eval–print_loop
[ast]: http://jointjs.com/demos/javascript-ast
Expand All @@ -101,14 +145,17 @@ VS Code has become my main editor in Ruby and JavaScript, due to having great su
[switch_header]: https://github.com/artsy/eigen/blob/master/Artsy/App/ARSwitchBoard.h
[types]: https://marketplace.visualstudio.com/items?itemName=jvitor83.types-autoinstaller
[redux_store]: http://redux.js.org/docs/api/Store.html
[swift_params]: https://developer.apple.com/library/ios/documentation/Swift/Conceptual/Swift_Programming_Language/Functions.html
[swift_params]:
https://developer.apple.com/library/ios/documentation/Swift/Conceptual/Swift_Programming_Language/Functions.html
[ruby_params]: https://robots.thoughtbot.com/ruby-2-keyword-arguments
[churn]: http://blog.cleancoder.com/uncle-bob/2016/07/27/TheChurn.html
[vs_extensions]: https://code.visualstudio.com/docs/extensions/overview
[extensions_approach]: https://code.visualstudio.com/docs/extensions/our-approach
[xpc]: https://developer.apple.com/library/mac/documentation/MacOSX/Conceptual/BPSystemStartup/Chapters/CreatingXPCServices.html
[xpc]:
https://developer.apple.com/library/mac/documentation/MacOSX/Conceptual/BPSystemStartup/Chapters/CreatingXPCServices.html
[danger_code]: https://marketplace.visualstudio.com/items?itemName=Orta.vscode-danger
[danger_vscode_load]: https://github.com/orta/vscode-danger/blob/a21ccc101b2b1c1be595b10565bca9c88242fb6f/package.json#L18-L20
[danger_vscode_load]:
https://github.com/orta/vscode-danger/blob/a21ccc101b2b1c1be595b10565bca9c88242fb6f/package.json#L18-L20
[atom_slow]: https://discuss.atom.io/t/why-is-atom-so-slow/11376
[vscode_debug]: https://code.visualstudio.com/docs/extensions/example-debuggers
[ruby_debug]: https://github.com/rubyide/vscode-ruby#debugger
Expand Down

0 comments on commit 856a1d0

Please sign in to comment.