Crystal 0.30.0 has been released!
This release comes with some language changes, compiler features, and std-lib improvements. There is some work-in-progress related to multi-threading in other branches, they are moving forward and we are eager to share them as a whole.
There are 139 commits since 0.29.0 by 28 contributors.
Let’s review some highlights in this release. But don’t miss the rest of the release changelog which has a lot of valuable information.
The language now checks that the return type of an abstract method is obeyed. This means that in an implementing type you need to annotate explicitly the return type if the abstract method is also annotated.
The following is now an error
abstract class Foo abstract def foo : String end class Bar < Foo def foo 1 end end
You will need to declare
def foo : String which makes the underlying issue more evident:
Bar#foo was wrongly trying to return an
Int32 instead of a
You don’t need to copy and paste it. A subtype can be used.
class Parent; end class Child < Parent; end abstract class Foo abstract def foo : Parent end class Bar < Foo def foo : Child Child.new end end
Finally, if you forget to implement some abstract method the compiler will let you know. Even on generic types and modules.
class Foo include Enumerable(Int32) end
In src/enumerable.cr:37:16 37 | abstract def each(&block : T -> _) ^--- Error: abstract `def Enumerable(T)#each(&block)` must be implemented by Foo
Since this change is likely to break a good amount of code it is introduced as a warning. Build your project with
--warnings=all to be ready for when this is switched from a warning to a real compile-time error. Read more about this feature in #7956, #7999, and #8010.
A small breaking-change syntax wise is that ranges can not span across lines since #7888.
There are a couple of new macro methods to extract arguments of
Annotations in #7694. For all metaprogramming lovers, this would be good stuff. As usual, metaprogramming is not something to abuse.
The API to work with AST nodes of paths and types had some polishing that will bring some fewer headaches. Read more in #7970.
Support for LLVM 7 was a long debt. We finally paid it together with support for LLVM 8. Read more about it in #7987 and #7986. In case you want to contribute in two months with the LLVM 9 support ;-)
For macOS official packages (ie: the one that you can download from GitHub) we are now using LLVM 6.0.1. Don’t ask what has been used up until today.
For Homebrew, LLVM 8.0.0 is used from now on.
There was a need for a breaking-change in
UUID: the method
UUID#to_slice was removed because it exposed a pointer to the underlying memory representation and doing that in a stack allocated value is error-prone. Use
UUID#bytes instead, that returns a
StaticArray(UInt8, 16). Read more at #7901.
Benchmark.memory is now available to measure just memory usage. Read more at #7835.
Every now and then some sample code in the docs are outdated. There is a tool made and run regularly to keep them in good shape. Luckily #8003 was not as big as other past iteration. Check maiha/crystal-examples to see how this is done!
JSON serialization can handle numeric keys, so
Hash(Int32, String).from_json works. Read more at #7944.
YAML deserialization handles
String as the last option if the expected type is a union. Since anything can be a
String that make sense. Read more at #7938
Finally there is a breaking-change regarding the API on the JSON parser. The usage of symbols for the parser state was replaced by enums in #7966.
URI.unescape are deprecated and you will need to choose between
URI.decode. This allows you to choose how to handle reserved chars. Read more at #7997.
Snapcraft 3.7 has been released and that means that the Crystal plugin can be used out of the box.
Please update your Crystal and report any issues. We will keep moving forward and start the development focusing on 0.31.
Once again, check your code with
--warnings=all. This will help in the migration of your codebase and will probably push some feedback about that tool. Some future language changes were introduced in this release as warnings for a smooth migration. But, unless you use
--warnings=all you will not discover them.
It will also be helpful if your shards are run against Crystal nightly releases. Either Docker or Snap are the current channels to get them easily. This will help to reduce the friction of a release while checking if the ecosystem is in good shape.