---
title: Crystal 0.18.0 released!
version: 0.18.0
summary: :-)
thumbnail: +
author: asterite
---

[Crystal 0.18.0](https://github.com/crystal-lang/crystal/releases/tag/0.18.0) has been released!

This is a **huge** release with many new language and standard library features, and
a few breaking changes as well.

Let's review them.

## Union as a first class citizen

Union types exist in the language since day one. However, they were types without a name. Sure,
you could write `Int32 | String` in type expressions, but you couldn't write `Union(Int32, String)`
the same way you can write `Tuple(Int32, String)` to denote a tuple of two types.

Now you can. And you can also add class methods to the `Union` type. This seemingly small change
adds a lot of power to the language.

For example, we can define a method to parse a JSON string into a `Union`. To do this we try
to parse the string for each type in the union, as can be seen [here](https://github.com/crystal-lang/crystal/blob/25b79258913d0d3f2859fa6db4f302f47b025e95/src/json/from_json.cr#L191-L228)
(the code could be just [these 9 lines](https://github.com/crystal-lang/crystal/blob/25b79258913d0d3f2859fa6db4f302f47b025e95/src/json/from_json.cr#L219-L227), but
it's more complex because it has fast paths for primitive types)

With that, we can now write:

```ruby
require "json"

array = Array(Int32 | String).from_json(%([1, "hello", 2]))
array # => [1, "hello", 2]
```

We can also use unions in mappings, even unions of complex objects:

```ruby
require "json"

struct Point
  JSON.mapping x: Int32, y: Int32
end

struct Circle
  JSON.mapping center: Int32, radius: Int32
end

class Result
  JSON.mapping shape: Point | Circle
end

result = Result.from_json(%({"shape": {"x": 1, "y": 2}}))
result # => Result(@shape=Point(@x=1, @y=2))

result = Result.from_json(%({"shape": {"radius": 1, "center": 2}}))
result # => Result(@shape=Circle(@center=2, @radius=1))

shapes = Array(Point | Circle).from_json(%([{"x": 1, "y": 2},
  {"radius": 1, "center": 2}]))
shapes # => [Point(@x=1, @y=2), Circle(@center=2, @radius=1)]
```

In short, more expressive power and type safety.

## Hash, Enumerable and block auto-unpacking

We won't deny it, Crystal has a lot of inspiration in Ruby, be it in some of its syntax
and a huge part of its standard library.

In Ruby there's the [Enumerable](http://ruby-doc.org/core-2.3.1/Enumerable.html) module. You just
need to define an `each` method that yields some values, `include Enumerable`, and you get
a lot of collection methods like [map](http://ruby-doc.org/core-2.3.1/Enumerable.html#method-i-map)
and [select](http://ruby-doc.org/core-2.3.1/Enumerable.html#method-i-select). For example:

```ruby
class Foo
  include Enumerable

  def each
    yield 1
    yield 2
    yield 3
  end
end

foo = Foo.new
foo.map { |x| x + 1 }      # => [2, 3, 4]
foo.select { |x| x.even? } # => [2]
```

Ruby's [Hash](http://ruby-doc.org/core-2.3.1/Hash.html), a mapping from keys to values,
is also `Enumerable`. But there's something a bit magical happening in `Hash`. Take a look:

```ruby
hash = {1 => "a", 2 => "b"}
hash.each do |key, value|
  # Prints "1: a", then "2: b"
  puts "#{key}: #{value}"
end

hash.map { |key, value| "#{key}: #{value}" } # => ["1: a", "2: b"]
```

So, we can iterate a `Hash` and get its keys and values, and we can also use `map` on it,
and transform the keys and values. But how does it work?

One would think that `Hash` implements `each` like this:

```ruby
class Hash
  def each
    # for each key and value
        yield key, value
    # end
  end
end
```

Then maybe Enumerable's `map` is implemented like this:

```ruby
module Enumerable
  def map
    array = []
    # We need a splat because Hash yields multiple values
    each do |*elem|
      array.push(yield *elem)
    end
    array
  end
end
```

However, that doesn't seem to be the case, because if we define our own `map`
method that doesn't use a splat, it works as expected:

```ruby
module Enumerable
  def map2
    array = []
    # We don't use a splat
    each do |elem|
      array.push(yield elem)
    end
    array
  end
end

hash = {1 => "a", 2 => "b"}
hash.map2 { |key, value| "#{key}: #{value}" } # => ["1: a", "2: b"]
```

What's going on?

The answer is that if a method yields an array, and the block specifies more than
one argument, the array is unpacked. For example:

```ruby
def foo
  yield [1, 2]
end

foo do |x, y|
  x # => 1
  y # => 2
end
```

So `Hash` is actually [yielding](https://github.com/ruby/ruby/blob/06975d613a3ae8e926a34e4ebbc25be86b8a7aee/hash.c#L1779-L1788)
a [two-element array](https://github.com/ruby/ruby/blob/06975d613a3ae8e926a34e4ebbc25be86b8a7aee/hash.c#L1743-L1755), not two elements, and when
using `each`, `map` and `select`, if we specify more than one block argument,
Ruby unpacks it for us.

Ruby's solution is very convenient and powerful: it lets us iterate a hash
as if it were a sequence of keys and values, without us having to care if
it's internally implemented as such; and when we want to add methods to
Enumerable we don't need to use splats to "get it right", we can just
treat each yielded element as a single object.

In Crystal we decided to do the same, although for tuples, because their size
is known at compile-time. This means that the first Hash snippet now works
exactly the same as in Ruby, and `Enumerable`'s code remained the same, and
extensions to it will continue to work well.

## Splats in yield and block arguments

Splats now work in yield and block arguments. This makes it trivial to forward
block arguments to another method:

```ruby
def foo
  yield 1, 2
end

def bar
  foo do |*args|
    yield *args
  end
end

bar do |x, y|
  x # => 1
  y # => 2
end
```

## Named tuples and arguments can be created with string literals

Named tuples were introduced in the [previous release](http://crystal-lang.org/2016/05/17/crystal-0.17.0-released.html)
but only allowed identifiers as keys.

```ruby
{foo: 1, bar: 2}
```

Starting from this release, we can use a string literal too. This makes it possible to
have named tuples with spaces and other symbols:

```ruby
{"hello world": 1}
```

This is a breaking change, as that syntax used to mean a Hash with string keys. Now, only
`=>` means Hash, and `:` always means a named-something.

Why is this useful? Consider a library like [html_builder](https://github.com/crystal-lang/html_builder),
that provides an efficient DSL for generating HTML:

```ruby
require "html_builder"

html = HTML.build do
  a(href: "http://crystal-lang.org") do
    text "crystal is awesome"
  end
end

puts html # => %(<a href="http://crystal-lang.org">crystal is awesome</a>)
```

We say it's efficient because `HTML.builds` creates a string builder, and methods
append to it. For example the `a` method appends `"<a ...></a>"`, and so on. And,
in this case, the argument to `a` is a named argument (`href`), which on the method
side gets captured as a named tuple, iterated and appended to the string builder,
so no memory allocations other than that for the string builder exist.

The problem is, if we wanted to have a `"data-foo"` attribute we couldn't do it:
we'd had to use a `Hash`, which is much slower. Well, now we can:

```ruby
require "html_builder"

html = HTML.build do
  a(href: "http://crystal-lang.org", "data-foo": "yes") do
    text "crystal is awesome"
  end
end

puts html # => %(<a href="http://crystal-lang.org" data-foo="yes">crystal is awesome</a>)
```

This is just one use case, but one can imagine many more uses cases. For example, generating
JSON objects with keys that have spaces:

```ruby
require "json"

{"hello world": 1}.to_json # => "{\"hello world\":1}"
```

## Class variables are now inherited

Class variables now work more like Ruby's class instance variables: they are available
in subclasses, with the same type, but each subclass has a different value for it.

For example:

```ruby
class Foo
  @@value = 1

  def self.value
    @@value
  end

  def self.value=(@@value)
  end
end

class Bar < Foo
end

p Foo.value # => 1
p Bar.value # => 1

Foo.value = 2

p Foo.value # => 2
p Bar.value # => 1

Bar.value = 3

p Foo.value # => 2
p Bar.value # => 3
```

## OpenSSL and TLS improvements

[@jhass](https://github.com/jhass) and [@ysbaddaden](https://github.com/ysbaddaden) took the
lead on improving and stabilizing OpenSSL and TLS-related functionality in the standard library.
Be sure to read the [changelog](https://github.com/crystal-lang/crystal/releases/tag/0.18.0)
to see all the additions and changes. Huge thanks to them!

## For Functional Languages fans...

User defined classes can now be generics with a variable number of type arguments. The built-in
Tuple, Union and Proc use this. For example, `Proc` is `Proc(*T, R)`, with `T` being the arguments
types and `R` the return type.

With that, and because `T` and `R` can be queried at compile time, we added a
[partial](https://github.com/crystal-lang/crystal/blob/25b79258913d0d3f2859fa6db4f302f47b025e95/src/proc.cr#L99-L130) method:

```ruby
add = ->(x : Int32, y : Int32) { x + y }
add.call(1, 2) # => 3

add_one = add.partial(1)
add_one.call(2)  # => 3
add_one.call(10) # => 11

add_one_and_two = add_one.partial(2)
add_one_and_two.call # => 3
```

One could even define a `curry` method if we wanted too. But we leave that as an exercise
to the reader (hint: use a different struct to represent a curried method).

## And more...

There are more little features, like being able to use macros in more places, better error
message when an `as` cast fails, and several enhancement to the standard library.

> **THANKS:**
> Thank you everyone who contributed to this release! <3
