Bright and Dark sides of Darklang

Set up an API, datastore, or background worker in 10 seconds

Grzegorz Gajos
7 min readMay 19, 2020

Some time ago I stumbled upon a Darklang. A completely new approach to cloud-native apps.

- The quickest way to code a backend
- Set up an API, datastore, or background worker, in 10 seconds
- Build an entire backend in hours
- Tooling you expect

Sounds promising right? I wanted to test out how much of those promises are actually true. The entire IT industry is rather focusing around small incremental change. One element to improve. Small but right. Darklang approach is very different. They are trying to invent everything once again. Claiming that it is more straightforward and faster. Rather than combining all the levels of abstraction, they are trying to build all the pieces together upfront.

In the standard approach, we have git branches, code changes, unit & integration testing, PR, commits, pushes, code review, CI, CD, deployments, keys, artifacts, instances configs.

In the Dark approach, we just change the code and it’s alive!

Please note that at the moment of writing Darklang is still in the BETA phase and issues presented in this article might no longer be valid.

I tried to find some simple use-case and proceed with the implementation. I’ve got access to the BETA version of Darklang (since it’s not yet live). Ready? Let’s start.

Website monitoring tool

Project: The app is loading a list of websites from google spreadsheet. Producing summary with rows like: “Domain ggajos.com returned 200", “Domain unknowndomain.com returned 500”.

Now. Let’s paint it.

Forget about projects, files, and directories

Darklang is using “Canvas” instead of “Projects”. It emphasizes the freedom of creation. We don’t have to worry about the location of elements. We are looking at the element that we are building and the things around it. We can see the canvas name in the address bar. The link will open our canvas in the place where we left it. We also don’t need to save anything, it just works. Every change is immediately available in production. While it might sound scary, there is a bunch of mechanisms to avoid unwanted surprises.

Dark Canvas

Let’s start with the creation of a simple endpoint.

First deployment on Production

Try to imagine what would be the fastest way to do that? Try to recall what steps you need to perform in the framework you are using right now? How much boilerplate and redundant actions you need to perform?

Creating a new HTTP endpoint is one of the most trivial cases:

  • 1. Click somewhere on the canvas.
  • 2. Select “New HTTP Handler” option.
  • 3. Select the name of the endpoint.
  • 4. Select the verb.
  • 5. Type the sample response.
  • 6. Open the browser with the newly created endpoint by a single click.
  • DONE
Creating simple endpoint, faster

Wow, that was fast. Can we speed this up even more? Well, yes. On the first menu, we don’t have to pick anything. We can immediately start typing REST endpoint name (uri):

Creating simple endpoint, even faster

It’s insane how well hidden is the complexity of possible options. The UX here is outstanding. The change is available immediately online.

Providing a list of URLs to monitor

Now let’s prepare a list of our websites to check. I’m going to type a few webpages in spreadsheet.

Creation of spreadsheet

We are going to access the spreadsheet via Google Sheet API. The required request is self-explanatory.

GET https://sheets.googleapis.com/v4/spreadsheets/ {spreadsheetId}/values/{range}

Let’s try to implement that call.

Loading data from a spreadsheet

Darklang provides class HttpClient with a few methods to perform the HTTP calls. We are interested in HttpClient::get method which is performing (suprise) a GET call.

Loading data from a spreadsheet

Ooops, we have PERMISSION_DENIED reply from the API. It looks like we need to provide an API key. The second parameter of the HttpClient::get is a query part. We can provide query args by passing a map like{ key: … }:

Adding missing Google API Key

What is again a really nice feature, is that we are able to see the response immediately. There is no need to execute any run button, compile anything, or wait for some action. It is really crazy fast way of prototyping! But the really neat feature is about to come.

Mind-blowing-friendly feature of dark: Autocomplete for dynamic JSON

This has to be scam right? How we can get the autocomplete for the JSON file if there is no definition or schema of the structure? How this can work if the structure of the JSON is completely dynamic? Well, it can:

Static typing for JSON!

Since code is executed immediately, the content of the JSON is parsed from the real response. Analyzed and fetched into autocomplete. It’s so simple, yet one of the most mind-blowing features. That’s not all. We can see the preview of the selected element while typing.

Ok, now let’s try to export a list of websites from the reply.

Functional programming

Dark is heavily functional, however, the syntax sometimes is a bit odd. Rather than mapping object like list.map(... we need to reach out for static reference and pass the object as the first argument List::map list lambda. I can understand some rationale behind it but even returning some element from the list is not just likelist[0] but another static method List::getAt list 0. When we add up everything together it is getting little less readable than expected (as in Java for example). The response from the google spreadsheet is a two-dimensional array (array of arrays). We need to extract the array. Below it’s a code that is extracting a single array from an array of arrays.

Extracting specific uris

Now when we are able to list out websites, let’s try to actually fire the request and see the response code (that website is working fine).

Monitoring websites

We are going to use HttpClient::get again and get the response.code out of it. Our endpoint is returning now a list of response codes rather than websites:

Test HTTP call to check the response

Trivial String join

Let’s try to do some very basic operation. Concat the website along with the status code. Very simple, right?

Dark side of language, some things are really not intuitive

Well, here things are getting clunky. The response code is Intand the text is String:

  • There is an operator + which is able to concat Int types, but cannot be used since types are different.
  • There is an operator ++ which is able to concat String types but cannot be used as well, types are different.
  • There are no methods like Int::toStringor String::valueOf

There is a simple method toString that is coming from nowhere, just a public static method available for the operation. Can be used like toString number and returns String type. While it’s doing the job well, it feels like a little inconsistency (why it’s not part of some Commons::?).

Concatenation of text

The text is finally concatenated. Changes are available immediately and we can see the responses of the websites.

Status codes

Now let’s try to add a new website and see the result.

Adding a new website to check

Great! The happy path is done. Now let’s add some not existing domain to see the result.

Adding some broken website

Ooops. There is an error.

Error rail

How does the error handling look like? Darklang introduce mechanism called Error Rail

The error rail allows you to keep writing code along the “happy path,” without stopping to handle errors. This is based on Railway Oriented Programming and the UI elements are unique to Dark.

In short, instead of try/catch blocks, errors are returned from functions and handled via pattern matching or if/else blocks. I wanted to present it here as well but there was little surprise. This feature is a little buggy now, so it’s not possible to catch the error.

Bright Side of Darklang

It’s the biggest paradigm shift that I’ve seen for quite some time. Darklang is finally something that is not built as abstraction layer over all other layers of abstraction. Autocomplete or live preview feels like the application is running while typing. Working with requests and payloads is just insanely easy.

Dark Side of Darklang

The code editing is really awkward sometimes. The idea is that it should be hard to make a mistake or write down a code that is incorrect, but actually sometimes it’s hard to write it at all. Even removing part of the text (code) is difficult. I had to copy the code out from the browser to notepad, edit outside and paste it back. The structure of the code is very flat, therefore I cannot see how to write something bigger than a couple of methods/functions.

I’m judging now something which is still in BETA phase, so I will stop :). The work done by Darklang team is really outstanding. Fingers crossed how the project is going to develop over time.

--

--

Grzegorz Gajos

Software Engineer, Co-founder of opentangerine.com. Owner of real, brutal, hands-on experience in diverse IT fields since 2009.