
Rust in production at Figma - steveklabnik
https://blog.figma.com/rust-in-production-at-figma-e10a0ec31929
======
kibwen
On the topic of Rust in production, game studio Chucklefish (makers of
Starbound) are developing a cross-platform (including Xbox/PS4/Switch) game in
Rust, and recently released a whitepaper: [https://www.rust-
lang.org/pdfs/Rust-Chucklefish-Whitepaper.p...](https://www.rust-
lang.org/pdfs/Rust-Chucklefish-Whitepaper.pdf) , and last year did an AMA with
more technical details:
[https://www.reddit.com/r/rust/comments/78bowa/hey_this_is_ky...](https://www.reddit.com/r/rust/comments/78bowa/hey_this_is_kyren_from_chucklefish_we_make_and/)

EDIT: Quote from the OP:

 _> One of them is called `error-chain` and another one is called `failure`.
We didn’t realize these existed and we aren’t sure if there’s a standard
approach._

`error-chain` is in maintenance mode these days; `failure` is its spiritual
successor and seems that it's on the path to becoming a community standard
eventually.

~~~
tytytytytytytyt
That looks more like a very short pdf with a white background than a
'whitepaper'.

~~~
chrisseaton
I'm not sure what you mean - this looks like a very conventional whitepaper to
me.

Wikipedia says

> In business, a white paper is closer [than the government meaning of a
> policy document] to a form of marketing presentation, a tool meant to
> persuade customers and partners and promote a product or viewpoint.

~~~
thanatropism
Much of what I've done professionally over the past decade was to produce
white papers in the following sense:

[https://en.wikipedia.org/wiki/Grey_literature](https://en.wikipedia.org/wiki/Grey_literature)

------
ralusek
Tangentially related, but if any of you work with designers or are yourselves
designers, please give Figma a try. It is identical to Sketch in so many ways,
better in some others (particularly editing vectors and dealing with nested
"symbols" or other components), and only falls behind in a few areas. If any
of you have had to deal with the nightmare of keeping your design files in
sync between designers forgetting to push changes to dropbox or InVision, or
multiple designers working together and having their changes fall out of sync,
the ability to edit and view the same document together cannot be overstated.

~~~
Dowwie
Are you related to the company?

~~~
ralusek
No relation, I just really like it.

------
abalone
_> We chose Rust for this rewrite because it combines best-in-class speed with
low resource usage while still offering the safety of standard server
languages. Low resource usage was particularly important to us because some of
the performance issues with the old server were caused by the garbage
collector._

Reading between the lines here, they didn't go with a more mature language
like Java because they were worried GC tuning would be a problem?

Given all the other issues they noted with using a less mature language like
Rust in production, that's a pretty heavy load to take on in exchange for not
having to tune GC. Isn't GC tuning a fairly well understood problem? Is there
something about encoding large documents that makes it a _significantly_
greater obstacle?

Or are there other unstated considerations at play here? For example, I mean
this completely earnestly and not cynically, but there is a lot more PR and
recruitment value in blogging about a hot new cutting-edge language than "how
we rewrote our TypeScript server in Java".

~~~
tazjin
Language maturity is not a one-dimensional problem and it's also not equal to
the age of the language.

To name just two ways in which I consider Rust more mature than Java:

* It has a lot of fundamentals that are based on more academic languages which have explored some specific PLT space for a long time and let it mature. The fruits of that are now in Rust (many aspects of its type system for example).

* Rust's community has an almost absurd ability (contrasted with most other languages) to focus on specific core libraries and tooling. For example serde[1], _the_ Rust serialization library, is well-understood, simple, mature and supported in basically every Rust library out there.

The second point is extremely impressive when contrasted with the state of
things in Java-land, where you often have many different solutions for the
same problems. Sometimes even the well-known and used ones are of _very_
questionable quality[2].

[1]: [https://serde.rs/](https://serde.rs/) [2]:
[https://github.com/FasterXML/jackson-
databind/pull/1423](https://github.com/FasterXML/jackson-databind/pull/1423)

~~~
dkarl
Jackson's status as the de facto Java standard for reading and writing JSON
really reflects poorly on the Java community. Too often the biggest, hairiest
solutions get anointed as the safe "best practices" choice for all new
development when really they should only be used if you know specific reasons
why they will pull their weight relative to simpler solutions. Jackson is an
800lb gorilla with an impressive arsenal of features, but there's no way in
hell it should be the default choice for a simple greenfield CRUD application.

~~~
abalone
Without turning this into a long tangent subthread.. could you point to some
support for this? The comparisons I've seen are more nuanced.[1]

[1] [https://blog.takipi.com/the-ultimate-json-library-json-
simpl...](https://blog.takipi.com/the-ultimate-json-library-json-simple-vs-
gson-vs-jackson-vs-json/)

~~~
dkarl
That's a performance comparison that ignores all other aspects such as
simplicity, readability, and ease of maintenance. It also shows Jackson coming
in last for parsing small files.

------
fulafel
Interesting:

"Instead of going all-in on Rust, we decided to keep the network handling in
node.js for now. The node.js process creates a separate Rust child process per
document and communicates with it using a message-based protocol over stdin
and stdout. All network traffic is passed between processes using these
messages."

~~~
cakoose
Yeah, waiting for Rust's async/await to mature is probably a good idea. But
I'm not sure why they didn't just use threaded I/O instead.

~~~
fulafel
Sounds like they use processes for fault isolation.

------
rationalthug
I’m curious to know if they ever looked at
[https://github.com/Microsoft/napajs](https://github.com/Microsoft/napajs)
from Microsoft or any other in-nodejs solutions to deal with the need for
multithreading vs launching multiple processes...

------
slezyr
That's a really good review of rust. Especially of async side.

------
chocolatkey
I look forward to using rust, but will probably wait a few more years for the
language to mature. Interested in seeing what it will become!

------
pkulak
Man, is that "cons" section ever terrifying.

~~~
staticassertion
Honestly, it's pretty encouraging. All of the problems they listed are things
I see as being very nearly solved.

For example, I ran into the futures issues. Now I use nightly's async/await,
and it's a massive improvement while still being early days.

I also use the Non Lexical Lifetimes feature, and see a lot of ergonomic wins
there.

The other stuff is being worked through as well - Failure is coming along, and
I hear good things. Libraries are always improving.

I would be a lot more terrified if these issues were surprising, or not being
dealt with, or were extremely hard to fix without breaking the language, etc.
Instead, it's a list of things I've run into and can even solve today with a
few features.

------
vkjv
What were the reasons you decided to go with a child_process model instead of
wrapping you Rust in a Node native module?

------
hsaliak
" each document lives exclusively on one specific worker"

Would decoupling the workers and the documents they work on not solve this
problem? Granted this might be non trivial, but it might have solved the
fundamental issue thats arguably more interesting.

~~~
apendleton
Somebody has to be responsible for reconciling multiple workers' changes to a
document and arriving at a consistent state. Sounds like they're probably
doing it in memory within an application worker. You could imagine a solution
where they move this to the storage layer and have multiple workers acquire
locks to mutate it, but I'm not sure how that wouldn't just move the problem.

~~~
hsaliak
The part I did not get is why a worker was holding on to other files when it
was working on a single doc. "Throwing more hardware at the problem wouldn’t
have solved this issue because a single slow operation would still lock up the
worker for all files associated with that worker"

Admittedly, the blog is light on details here and I am unfamiliar with the
product. With the re-write, they also just moved the problem to rust. So I
think that your suggestion to move the problem to the storage layer could have
been another viable solution.

~~~
apendleton
They didn't do this before because the memory overhead of having a separate
worker for each document would have made the infrastructure costs exorbitant,
presumably (since you'd have to pay for whatever fixed overhead costs Node
has). But the lower overhead of using a Rust process per doc instead of a JS
process per doc has allowed them to move to that model.

~~~
hsaliak
There can be an M:N mapping - An update queue can be consumed by a fixed pool
of workers that can lock a file and commit the update. This is crude but wont
explode the number of workers.. if you have a hashing scheme for the worker
pool and implement linear probing, you can achieve some degree of preference
for the same worker. If their system was such that a worker maintains state
for a bunch of docs, and persists them at checkpoints, while also being doing
compute intensive tasks per document on a single threaded node instance, I
would ask why it was designed like that in the first place.

