00:00:16.440
my name is Kirk Haynes my day job is as a developer relations engineer for
00:00:22.320
parity Technologies but I've been doing Ruby for
00:00:27.599
a long time more than 20 years and today we're going
00:00:33.840
to talk a little bit about Crystal and specifically Crystal for
00:00:39.420
rubius what that means is what does crystal look like what is it
00:00:45.140
and how can you leverage your existing Ruby knowledge in order to make you
00:00:50.399
productive more quickly with Crystal and this the first part of this will be kind
00:00:56.219
of like a talk because I kind of want to go over you know like an overview of a bunch of things but
00:01:03.019
it isn't going to be like a talk in the sense that I'm going to hold your questions till the end if you have
00:01:08.340
anything to ask you want to you know talk about anything that you see up on the screen or I think anything that I
00:01:13.380
say interrupt me and let's talk about it and let's just sort of see where this
00:01:18.659
goes um the whole slide deck as well as some
00:01:24.720
code that was used in some of the slides some code examples and a few little
00:01:32.220
I guess you call them exercises are all on GitHub and you can access it through
00:01:38.460
that QR code if that QR code is too little
00:01:43.740
for your camera to read it you know you can grab it from here and that's the URL to go to so if you want to grab it and
00:01:50.460
pull it down to your your laptop to you know follow along on your laptop directly you're welcome to do so
00:01:58.439
um I'll give you just a few seconds there to to grab that and then we'll move on so
00:02:06.000
while we're waiting let me ask this who in here knows what crystal is
00:02:13.140
quite a few of you cool now who in here is actually written the line of Crystal before
00:02:18.720
okay cool it's sometimes yeah yeah it's actually
00:02:25.200
kind of surprising to me how much um how much Ruby code will simply compile with the crystal compiler
00:02:31.379
because the syntax is so similar and there are a
00:02:36.480
lot of things that are quite similar um all right so if you need me to go back to that QR
00:02:41.760
code let me know but otherwise I'm going to roll forwards and let's just talk about a little bit about y Crystal you know we're all here
00:02:48.720
because we like Ruby and I know some of us like
00:02:54.120
you know Keith here you know we've been around a long time we've been using Ruby a long time and there are a
00:03:01.620
lot of benefits to Ruby and you know you can go and you can make a pretty exhaustive list to them this is just a
00:03:06.959
few quick little ones that I think a lot of people agree on you know the blocks the user-friendly syntax the fact that
00:03:13.019
Ruby is a very versatile language you can use it for a lot of different things and it's got some interesting sprinkles
00:03:20.159
a functional programming in it that make it just just enable that usability and that
00:03:26.040
versatility the dynamic typing is one of the things that honestly
00:03:31.319
um really drew me to it initially and I think is one of the things that a lot of
00:03:37.739
people look at as as a benefit the fact that most of the time you don't really have to worry about what the type of
00:03:45.420
your thing is you let Ruby figure it out and you let Ruby tell you if you made a mistake
00:03:51.480
um and Ruby has a really strong set of tools built around it and a
00:03:58.080
really strong testing ecosystem there's a lot of stuff to help you as a developer structure your projects and
00:04:04.200
make your projects easier to work with so
00:04:10.140
there are some drawbacks to Ruby and I know we can argue about some of these drawbacks but generally you know if
00:04:17.579
you're trying to distribute a ruby program a ruby binary it's really difficult to do there are some projects
00:04:24.360
that have existed actually for a very long time to try to tackle this problem and there isn't any one of them that has
00:04:33.120
ever really taken off and dominated this space because it's really a pretty difficult problem to solve because
00:04:38.699
there's so many dependencies wrapped up in a piece of Ruby Ruby code of any
00:04:44.280
significance now you can write something and say m Ruby M Ruby is a ruby-like
00:04:49.740
language itself it's not really Ruby because there's some some significant differences but it's ruby-like and it
00:04:55.979
will compile to be an executable but you can't go take your rails app and turn it into an M Ruby executable
00:05:02.840
now Ruby's performance has always been a topic of discussion and with Ruby 3
00:05:10.020
um that that has been a significant focus and it has gotten a lot faster but
00:05:15.300
nobody writes Ruby because Ruby is going to to be a Lightning Fast 3D rendering
00:05:21.000
engine that's not why we use it um it's it's performance is fairly
00:05:26.039
mediocre concurrency with Ruby is also kind of interesting because
00:05:32.580
there's a lot of different ways to do concurrency with Ruby and that's part of the the tricks with it you've got fibers
00:05:39.479
you've got threads you've got Rafters you've got evented systems and that
00:05:45.000
makes concurrency handling kind of um an adventure sometimes and then
00:05:51.000
the static type checking in Ruby it was added in Ruby 3
00:05:56.780
actually arguably a little bit before that because of the sorbet project but Ruby 3 also has something called RBS so
00:06:04.740
if you want to have static type checking on on your software so that you can
00:06:09.780
really be more certain that you aren't making type
00:06:14.820
related errors you can use it but it is a bolt-on and it has some limitations
00:06:20.160
it's not really when when you're writing code it's it's
00:06:25.259
not fluid to use RBS now these are some of the drawbacks
00:06:30.539
and Crystal has some answers to some of these things um it is syntactically extremely similar
00:06:35.880
to Ruby you know if you look at this code that first little snippet it's the
00:06:41.520
same crystal or Ruby and the next two Snippets are almost the same
00:06:48.000
the one on top is Ruby and the one on the bottom is Crystal the only difference between the two is
00:06:55.080
that in Crystal if you're declaring an array you have to tell it what it's
00:07:00.180
going to store so you have a little bit of typing information in there yeah it's kind of little on this screen I
00:07:06.539
I had thought maybe the screen was going to be bigger but you can see that bottom line
00:07:12.419
there where it says array there's an amp32 in there to tell it what the type of the array is but that's the only
00:07:18.539
difference um
00:07:24.060
yeah so actually I just minimized it completely out of view um
00:07:30.660
where'd it go um all right
00:07:35.940
yeah I minimized my my view of it there we go um
00:07:42.060
I don't think
00:07:49.259
yeah I'm not sure why it's not showing me the normal full screen controls right
00:07:54.300
now when I'm plugged in but um I guess we'll just we'll just roll with
00:08:00.960
it here um so Crystal is a compiled language it
00:08:07.919
compiles your your code down to an executable and it's built on top of llvm um anybody here use rust
00:08:15.599
okay so so you know you know how that works um rust also compiles down to llvm
00:08:21.780
um so it and Crystal share that common layer underneath
00:08:28.139
and this is just a a little snippet just showing you that that if you build build
00:08:34.320
something with Crystal it is in fact a elf executable on my system yeah
00:08:42.060
well let's try it no
00:08:48.600
laughs
00:09:10.980
nope anyway the the binaries tend to also be
00:09:16.680
very fast to execute um in the the repo that that you can get
00:09:22.560
from that QR code there's a fib bench directory that has four implementations
00:09:28.440
of a simple Fibonacci calculator that just recursively calculates Fibonacci numbers and
00:09:35.100
um on my laptop these are the timings for those so you can see that rust is a little bit faster but
00:09:42.420
um yeah crystal out runs everything else by by a substantial margin and this this
00:09:48.240
was simply calculating the 42nd Fibonacci number because if I go bigger than that on my laptop Ruby's really
00:09:54.959
really slow and if if I go smaller you know everything happens too fast so that
00:10:02.040
that's the reason for that number um so Crystal has some answers to some
00:10:07.080
of these these things while still remaining a versatile productive
00:10:12.380
language with with a lot of the same syntax as Ruby
00:10:17.820
so if you don't have Crystal installed on your system and you want to install it it's really easy to do that and you
00:10:25.500
know for like once we're done with kind of the me Talking part of this and we're to the you guys playing part of this you
00:10:32.160
might want to install it if you want to play with it and ask me questions but if you go to crystalllang.org install it's
00:10:39.959
got guided installation steps for any operating system you might be using out there
00:10:50.339
if you need a second to grab that URL I can wait here a second but it's just Crystal lang.org install
00:10:57.839
and if you want to just play on your browser without installing anything you can go to
00:11:03.380
play.crystalling.org and you'll have a a in browser console where you can type
00:11:08.519
code and you can run it and see what happens it's a full uncrippled Crystal running
00:11:14.519
you know running there and letting you see what happens so it's really nice to play with little code Snippets and
00:11:20.100
things like that so I'm going to go through really quickly
00:11:25.980
what the differences are between Ruby and Crystal at a very high level and
00:11:31.320
again if you have questions about anything that I say interrupt me this is you know this is a conversation if you
00:11:37.860
want it to be a conversation and the first thing I want to say is that while Crystal looks a lot like Ruby and in
00:11:44.820
fact there is a lot of Ruby code that you can just throw the crystal compiler at and it'll build it and it'll run it
00:11:50.220
Crystal isn't Ruby there's some significant differences um it's it's a
00:11:57.540
statically type checked compiled language that doesn't have a lot of the dynamic qualities that Ruby has so there
00:12:04.680
is no eval there is no send it's a possible to get a lot of the same
00:12:11.760
capabilities using a different mechanism but those things don't exist in in
00:12:17.579
Crystal um and so you got to keep that in mind that
00:12:22.920
it's not just a funny Ruby it is actually a different language it's just one that leverages your Ruby quite
00:12:28.380
extensively and I also want to mention here just because it's a historically interesting thing the reason why Crystal
00:12:35.220
looks so much like Ruby is that the the people that originally built it they
00:12:40.860
built it using Ruby the first Crystal compilers were built with Ruby and the
00:12:47.880
original goal was basically to take Ruby and see if they could make a compiled
00:12:52.980
language that looked like Ruby and felt like Ruby but was compiled and was fast
00:13:01.200
so that is that is the first difference Ruby's interpreted crystal is compiled
00:13:06.839
however there is an interpreter for Crystal right now it's considered experimental
00:13:12.300
um there's some things that don't work on it but um you can actually run um a large subset of your Crystal code
00:13:20.279
AS interpreted code just like you would Ruby
00:13:26.160
crystal is dynamically typed arubia is dynamically type checked what that means
00:13:31.320
is that the Ruby interpreter is checking the types of of your your data objects
00:13:36.920
at runtime and if you get something wrong you're not going to know it until you run your code and Ruby figures out
00:13:43.860
oh there's a mismatch here and throws an error crystal is statically type checked which means that when the compiler
00:13:51.180
builds the software it goes and it checks before it ever builds the executable to make sure that all of the
00:13:58.380
types make sense and match the way they're supposed to and like I mentioned before Ruby does have static type
00:14:03.779
checking with RBS or sorbet but it is not directly integrated into the
00:14:09.060
language it's kind of a bolt-on so it's a little bit different
00:14:14.160
so here's a quick example what happens if you do this in Ruby
00:14:21.360
yeah yeah so Keith Keith said it's an error if you run it in Ruby and again
00:14:29.279
unfortunately this might be a little hard to read um but Ruby gives you a type error
00:14:34.680
because you Ruby doesn't know how to add a string to a number
00:14:42.360
if you do the same thing in Crystal it's also going to throw an error but it will throw it at compile time instead of at
00:14:48.360
runtime and it's going to give you an explanation of what's wrong and what's
00:14:53.760
wrong is that it has an unexpected argument to the number
00:14:59.760
it expected it to be one of those types and it wasn't that type it was a string and then it goes and it tells you you
00:15:05.940
know what all of the things are that it could be
00:15:11.579
now Crystal does have type inference which means that in a lot of cases it can figure out the types of things so
00:15:17.579
you don't have to specify those types you know back in that early example where you had the array with the the
00:15:24.420
type specified in the array um if if in Crystal code you went and
00:15:29.459
you just used the the syntax to specify a static array
00:15:35.399
um with strings in it or whatever Crystal's going to see that it's going
00:15:40.920
to know okay you mean an array of strings and you won't have to specifically tell it that you have an array of strings that you're storing
00:15:46.440
strings into it's only when it's ambiguous and you can't figure it out that you have to tell it what your types
00:15:52.740
are and so in this example there's nothing in there
00:15:58.500
anywhere that's telling Crystal what a is or what B is whether they're numbers or whether
00:16:03.839
they're strings and this will work exactly the same in Crystal as it does in Ruby
00:16:16.860
just like that no difference same code both languages
00:16:24.300
now in Crystal because it was inspired by Ruby and Ruby informed a lot of the design
00:16:31.740
choices a lot of the method names are identical so a lot of your code will work identically all of this code here
00:16:38.220
will work exactly the same in either language and you run this and you'll get the same out almost the same output
00:16:44.399
there is a difference in how scan in the the what is returned by scan as far as
00:16:51.899
how regular expression matching is there's a slightly different data type that's returned but all this code will
00:16:57.120
execute exactly the same but this will not
00:17:04.500
um in Ruby you do time.now
00:17:09.720
Crystal doesn't have a Time dot now it has a timed out local or time.utc
00:17:15.559
depending upon whether you want the time now in local time or the time now in UTC
00:17:20.819
time but it doesn't have a Time dot now and that one when I was very first you
00:17:26.579
know but first working with Crystal and I was porting some of my code I could not figure out why it didn't work
00:17:32.520
because time.now this why isn't time.now we're not working
00:17:38.160
and it took me longer than I will admit um before I realized that it didn't work
00:17:43.980
because it wasn't implemented and I didn't have the right method um and so you you will run into some
00:17:50.520
places where those things are just different um inject is another one you know inject on
00:17:57.780
on an array in order to to Loop over an array and execute a block on it and gather up a result it's called reduce in
00:18:05.039
Crystal a lot of these name changes by the way are inspired by go where there are name changes in a lot of
00:18:12.120
cases it was because the authors thought that another language typically golang had
00:18:18.960
named it in a way that made more sense and so rather than carrying on with the Ruby influence
00:18:26.220
they chose something that was clear or made more sense to them and then
00:18:32.059
sticking with our Fibonacci theme that piece of code down below
00:18:38.580
there is two really really really terse ways of very efficiently calculating
00:18:45.360
Fibonacci numbers and the one in comments is Ruby and you can calculate
00:18:50.820
more or less any Fibonacci number that you want with that and it will be very fast you want the thousandth Fibonacci
00:18:56.460
number you know that little bit of Ruby will give it to you um and it'll be very very fast
00:19:02.580
um slightly different in Crystal because in Ruby Ruby will cast between
00:19:09.660
um your your regular integer types and a big int if
00:19:14.880
you overflow that integer so when your number gets too big Ruby will say oh it's too big time to use bigint and it
00:19:21.539
will transparently cast that for you Crystal doesn't do any of that automatic
00:19:26.700
casting and so in order to implement this in a nice tighter swaying Crystal
00:19:34.340
we just use big int right from the beginning and avoid that issue of casting so you can
00:19:41.580
see the code's almost the same but just that little bit of typing difference in there
00:20:00.140
oh so so yeah so yeah so that's that's basically what I'm
00:20:06.600
doing um so if if you look
00:20:12.120
so in Crystal we have whoops in Crystal you have to tell it
00:20:17.400
for a hash or an array where oh you I'm on the wrong window again having two windows all right so
00:20:25.760
this part here we're saying we've got a hash and the key is 32-bit integers and
00:20:33.840
the values are big ends and then what we're doing is we're just casting
00:20:41.400
just the very first value that's going to go into there as a big end because when the math happens then in the next
00:20:47.940
part because one value is a bigint just like in Ruby if you're doing integer math
00:20:55.280
you know you don't have to you don't have to specify your types all
00:21:01.380
the way through you know it will if you have an integer and a float it will say okay I guess the whole thing needs to be
00:21:06.720
afloat well because we have a big int and regular ins it's going to say okay the whole thing needs to be a big end
00:21:13.200
and so it converts it all to Big end so it can stay nice and terse and
00:21:19.140
concise but you do need that little bit of extra typing information in there in Crystal that you don't need in Ruby
00:21:32.460
um it will it depends upon the math operators they use for all of the math
00:21:38.820
operators there's there's two variations one of them will throw an error and the other one will wrap
00:21:45.360
so you know if you're doing multiplication or addition or something and maybe you have a use case for just
00:21:50.880
wrapping it back around there's an operator that will do that
00:22:02.400
now concurrency I mentioned it earlier and concurrency is one of those things that's quite a bit different
00:22:08.580
um Ruby has fibers threads reactors and Via gem
00:22:14.340
libraries you have event-based concurrency and um so when you're trying to do something
00:22:20.340
that is concurrent in Ruby it can be quite a bit of work
00:22:26.700
so this is a fiber-based Fibonacci calculator it sets up a fiber and then every time
00:22:35.760
you resume that fiber it calculates the next value of the Fibonacci sequence and
00:22:42.539
you can see that yeah go ahead
00:22:48.720
there isn't any it's just an example yeah yeah yeah there's absolutely no benefit to this yeah it is simply an
00:22:55.320
example of um a fiber that's out there separate from your main program and
00:23:02.280
um so what we're doing here is that every time we allow that fiber to execute
00:23:07.620
it'll calculate the next number and then return it but what we have to do to do that is we
00:23:14.280
have to do a lot of manual herding of that fiber we have to declare it we have
00:23:19.919
to yield to it we have to resume it and if you're doing anything that's really complicated all of that fiber herding
00:23:27.480
can can get really involved you know there's a lot of little details you have
00:23:33.240
to keep track of if you're trying to write fiber code and do it all yourself
00:23:39.900
yeah yeah and I didn't do a ractor example mostly
00:23:45.720
because I ran out of time to pull one together but nobody's really using reactors yet anyway because there's
00:23:52.320
still some Growing Pains there and this is the same thing in Ruby
00:23:59.940
written with threads and so you can see that it's similar there's some things
00:24:06.120
that are a little bit different but um written with threads what we're doing is we're feeding that value into a cue
00:24:13.320
and then we're popping the values off of that Q
00:24:22.200
yeah if you're using jruby it'd be multiple CPUs um in regular MRI Ruby it's still going
00:24:29.340
to be one CPU typically because of the the the global global lock that is on on
00:24:36.780
those in order to prevent conflicts between shared data um
00:24:42.299
now when we do it in Crystal it's a little bit different Crystal looks if if any of you have ever
00:24:48.960
used go with um with goes
00:24:54.120
um go routines and channels Crystal basically has that model of concurrency
00:25:00.720
and so what happens here with with Crystal is we're spawning a separate
00:25:07.559
um a separate execution unit and you don't really have
00:25:12.600
to worry about whether that's a fiber or that's a thread that's kind of a background implementation detail
00:25:18.620
we're spawning an external unit that is responsible responsible for calculating
00:25:24.900
the Fibonacci numbers and then we're communicating to it through a channel and you can think of as a channel as as
00:25:31.080
a a one-directional pipe so you you can
00:25:37.140
feed data in one end and you can pull it out the other end and this is how
00:25:42.240
all concurrency Works in Crystal um so you have coordinated sequential
00:25:48.000
processes that that are talking to each other through these channels
00:25:55.140
um it doesn't have a lot of the the same
00:26:00.840
um with with Ruby you have to make these choices or am I going to use threads am I going to use reactors am I going to
00:26:06.779
use fibers am I going to use some combination I'm going to use fibers with threads um and you have to do a lot of things
00:26:13.740
very manually to handle all of that with Crystal um
00:26:19.380
hides a lot of those details if you turn on multi-threading because right now multi-threading is is an option with
00:26:26.039
Crystal that you can turn on or not when you compile your program if you turn on multi-threading it will have one or more
00:26:33.840
threads with fibers running distributed through those threads but you don't have
00:26:39.539
to worry about hurting any of that you don't have to worry about managing any of that it manages it all for you so all
00:26:44.820
you have to do is send your communication to your processes get your communication back from your processes
00:26:49.980
and let it worry about handling all of that
00:26:56.340
now some other just little differences um this is yeah Ruby libraries are gems
00:27:04.919
Crystal libraries or shards and just like you know with Ruby you have a gem command and Crystal you have a Shard
00:27:10.799
command um the actual low level management of
00:27:15.840
those is a little bit different because shards uses a yaml file to describe
00:27:20.940
everything in it since um because crystal is not a dynamic
00:27:29.340
interpreted language you can't describe your your library in code within that so
00:27:38.400
it's described in yaml and it parses the yaml to get the information out um
00:27:46.080
and just like Ruby has bundler um
00:27:52.200
Crystal has tooling that is inherent in the language to allow you to do a lot of
00:27:58.320
the same things that you do with bundler and with shards
00:28:03.539
and somehow I got that slide in there twice
00:28:08.580
um so this is a quick example when it comes
00:28:14.340
up there we go
00:28:21.740
this is a quick example of something you're probably familiar with this is how it would look if you wanted to
00:28:26.820
create a new project with bundler you do bundle Gem and then you can give it some
00:28:32.460
some command line options to tell it what kind of test Suite you want to use and how you want to do your CI and
00:28:38.580
whatever and it'll go create your stubs for you and Crystal provides the same
00:28:44.100
basic Tooling in a slightly different different shape you know the crystal command itself has this functionality so
00:28:52.080
it's not in a separate tool so you can just do crystal init and you get much the same thing
00:29:00.120
um just in a different tool
00:29:06.539
testing is one of the things that I think in Ruby is a real strength there's there's a strong testing culture in Ruby
00:29:14.100
yeah go for it both both yes so so there's there's two
00:29:22.380
where it says app there if you change that to lib it will change very slightly what it generates to be a
00:29:29.820
library versus an you know something that's meant to be executed separately
00:29:36.419
yeah so so Ruby has you know strong testing history and the two main you
00:29:42.000
know testing libraries are are spec and mini tests and Crystal essentially has the same thing
00:29:48.360
um its testing library is simply called spec and it's built in to to Crystal
00:29:54.240
um and it is extremely similar to our spec um
00:29:59.580
slight differences but extremely similar when you look at a crystal spec if you're familiar with our spec you can
00:30:05.700
read it and likewise there is a mini test that actually was implemented more or less as
00:30:12.899
a direct Port of Ruby's mini test um and so if you like test unit style
00:30:19.020
tests that's available to you as well
00:30:24.779
and so this is just an example actually it's an example pulled out of of
00:30:29.940
a real library of what the specs might look like in Crystal you
00:30:36.779
know it's got the same described the whole it syntax
00:30:42.000
you know event.name dot should equal test event
00:30:47.760
um so it's very very similar to our spec slight differences EQ versus equal eql
00:30:55.020
um some things like that but more or less if you can read our spec you can read
00:31:00.419
read Crystal tests
00:31:05.580
and then yeah kind of wrap up back to the beginning Crystal isn't Ruby but its
00:31:10.980
syntax is close enough that you can use your Ruby knowledge to bootstrap yourself into Crystal really effectively
00:31:20.220
so this is the part where I'm done just talking and the part where maybe we work
00:31:25.679
on something you know we we you know pair programmer we talk through something or whatever it is you guys
00:31:31.860
might find valuable um one of the things that I found really
00:31:37.679
valuable when I first started learning Crystal was just going and taking pieces of Ruby code where I knew the
00:31:43.860
functionality I knew how it worked and rewriting it in Crystal because sometimes it's it's extremely trivial
00:31:51.240
but you can see the little differences and then every once in a while you run into something that is significantly
00:31:57.179
different and you know so then then it sort of breaks your brain and so you
00:32:03.299
know I had I guess two two concepts in mind here and one was we can just you
00:32:09.659
know go to exorcism and take some of the Ruby tasks that are in exorcism how many of you are familiar with exorcism
00:32:16.919
maybe I should explain exorcism first I I made an assumption that seems to be an erroneous assumption
00:32:23.820
um exorcism is a website that is intended to teach programming and tended
00:32:31.559
to teach programming languages and it does it by providing um
00:32:38.220
for any given language and they have dozens and dozens and dozens of them they have programming tasks little tiny
00:32:45.240
challenges that each teach individual Concepts and you can go right in your
00:32:50.700
web browser and you can you can code and you can work on those challenges and you can run your tests and when they pass
00:32:56.520
then you get to move on to the next exercise and so it's a really cool way to learn a language and they have both a
00:33:03.299
ruby track and a crystal track and honestly tracks for just about any language you can think of and a lot that
00:33:08.820
you've never ever heard of so if you've never looked at exorcism before it's a
00:33:14.340
really cool thing to take a look at and you know even without I was just looking at why
00:33:21.779
the the URL is blocked by something down there but um even without
00:33:28.260
um doing anything with Crystal I would say exorcism is worth your time to go take a look at if you're interested in
00:33:33.779
in working on your Ruby skills or or your rust skills or any other language
00:33:41.760
and then the other thing that that I have is um
00:33:46.980
a little it's actually in the repo there is a ruby program that was implemented
00:33:52.260
as a as a dice roller for like a role-playing game and I implemented it in Ruby and there's
00:33:58.019
a stub in the repo of a crystal implementation but it's not completed
00:34:04.140
and so that the challenge would be to take the Ruby version and make it work in Crystal and there is
00:34:11.099
if you want to cheat a finished version also in the repo but if you don't want
00:34:16.379
to cheat um it's it's an interesting exercise and taking a working piece of Ruby that
00:34:24.179
isn't just two or three lines and converting it into a piece of working
00:34:29.460
Crystal and I'm completely open to what people might be interested in if you
00:34:35.580
just want to ask me questions or you want to work on something um this is your turn to shine
00:34:42.599
um yeah
00:34:50.159
what's something okay so so I'm going to repeat your question because the microphone yeah so so he asked what is
00:34:58.200
something that I found that Crystal isn't great at where I would go to Ruby first
00:35:04.200
um and that's an interesting question I think that
00:35:12.180
I think that for most um
00:35:17.400
most significant projects most projects that are intended to have some longevity
00:35:22.980
um crystal is comparable to Ruby I mean you know
00:35:29.040
there's reasons for one or the other you know if if you really like the rails
00:35:34.440
ecosystem and you're building a website you know it's hard to go wrong with rails you know but
00:35:39.780
um there are also very productive options in Crystal I think that probably
00:35:45.599
the place where there might be a difference is if I have something where
00:35:50.940
I really really really need that Dynamic code evaluation
00:35:56.280
um you know like I said there are ways around it that I haven't gone into in
00:36:01.920
this because you know there'd be dragons there um you know if you're familiar with with rust rust has macros Crystal has macros
00:36:09.300
too so you can write you know Crystal has a macro language which is a crystal-like language that exists only
00:36:15.660
to write code so so it's it's code that writes code and so you know doing that you can do
00:36:22.920
all sorts of of dynamic looking things but without going there
00:36:28.920
um anything where you really need that Dynamic code execution or anything that
00:36:33.960
maybe is just a quick you don't care if
00:36:39.000
if it's might have typing errors that that you're not going to run into anyway because it's not going to be in
00:36:45.300
production forever it's some quick little thing you're going to bang out you're going to get a task done and you're done
00:36:51.839
um you know all that kind of stuff I think Ruby is definitely better for
00:36:56.880
um for the other stuff you know I think it's a much harder
00:37:02.040
thing to decide that one is better than the other because they're pretty comparable
00:37:09.780
yeah so what are things that in the real world that are powered by Crystal
00:37:16.680
um so that's a good question that it's it's
00:37:21.960
something that is growing um there's
00:37:28.800
yeah what's so a lot of it is is fairly similar to
00:37:36.060
Ruby in a lot of ways I mean there's a lot of web development that that happens with Crystal
00:37:41.160
um there's some very productive web development Frameworks for Crystal um there's also I think the biggest
00:37:48.839
project that I'm personally aware of is something called Place OS it's a
00:37:56.240
infrastructure management system so you have some giant building with a whole bunch of complex mechanical systems and
00:38:02.339
rooms to reserve and all kinds of stuff like that with a hospital or or an office building
00:38:08.579
with with offices and desks and you know that are being reserved and stuff like that place OS is is a system that
00:38:16.740
manages all of that and some very very big companies like Cisco use it and and
00:38:21.900
large hospitals use it and things like that and then it's all written in Crystal
00:38:26.940
um but it has it has a lot of overlap with
00:38:32.460
with Ruby in where it is currently being used um I know of a company in Las Vegas that
00:38:39.660
is a a small twitch competitor um that uses it for all of their
00:38:46.020
all of their infrastructure um and I know that there are people that are using it for
00:38:52.740
um gaming development because this is another thing that I didn't go over because
00:38:58.079
too much complexity and too much talk talk but
00:39:03.540
Crystal has a really really really nice facility for interfacing with C libraries Ruby is pretty good at that
00:39:10.680
but crystal is is just stupid stupidly easy you know basically
00:39:17.099
it you can just link to a C library and use it almost like almost like Crystal code
00:39:23.339
um so it's it's really nice for interfacing with with Graphics libraries and things
00:39:30.839
like that and I know some people are doing that
00:39:43.260
um so so it's not really that Crystal has plans to deviate from Ruby it's just that
00:39:49.560
um as crystal is innovating on their Syntax for like things like pattern matching
00:39:54.720
um there's ongoing discussions in in the the core development community on
00:40:00.180
Crystal and Crystal is actually a very very open development environment anybody who wants to get
00:40:07.440
involved in actually working on the core of Crystal can it's really open and accepting in
00:40:14.400
that way but there are ongoing discussions about language features whether they're from
00:40:21.119
from Ruby or from other languages like go um or or Elixir or or wherever
00:40:27.140
that might be good ones to implementing Crystal and some of those things will be
00:40:32.760
followed and some won't pattern matching is an example because pattern matching is something that has
00:40:38.820
been discussed recently yeah please yeah
00:40:52.260
so the question is whether in Crystal you can reopen a class like in Ruby and add a method and you absolutely can it's
00:40:58.020
it's exactly like Ruby in that respect so if you wanted to make a ruby compatibility later layer that implemented that stuff you can do that
00:41:05.099
yeah and actually crystal is implemented in Crystal entirely so
00:41:11.099
um you know basically down at the low level it's reopening itself all over the
00:41:16.320
place to add add things
00:41:21.660
Yankee oh
00:41:27.839
I guess it's um so so there was a central person but
00:41:37.680
um it's more now of a um a community effort um and I can't pronounce his last name
00:41:45.300
his first name is Ari um but he's from Argentina and he was a
00:41:51.480
longtime Ruby guy he's still in the in the Ruby Community but um there's a a
00:41:56.760
consulting company in Argentina Manis Tech that provides a lot of the monetary
00:42:05.099
support for Crystal they have um some developers who are on staff
00:42:10.680
specifically to work on crystal because they use crystal with a lot of their clients but it is very much a sort of a
00:42:18.119
decentralized development environment it's just shepherded by mana's Tech right now
00:42:30.300
we'll be running out of questions okay cool I mean if if you want to hang
00:42:37.680
out we've got the room until two um so you know if you want to hang out
00:42:43.140
and ask me more questions or you want to work on on some code or whatever
00:42:49.500
um I'll be here otherwise you know I'm not going to keep you all prisoner you're you're you're welcome to to go go
00:42:57.300
mingle and and do your thing thank you all for coming
00:43:09.839
so how robustly has the the go Lang model of the current
00:43:17.579
um pretty robustly I mean it it um it's in
00:43:22.680
pretty pretty heavy use um you know and and
00:43:28.800
speaking from my own experience um it's it's really easy to use it
00:43:36.119
um it's it is it is a little different I mean there's
00:43:41.700
certain certain thought processes that take a little bit of getting used to when you're talking about passing messages around and receiving them like
00:43:47.940
that um but it's pretty solid the thing that isn't
00:43:53.400
quite there yet is um just in general the language is the
00:43:58.800
multi-threading support because um there's certain well you know you get into to you know
00:44:06.540
resource sharing issues and there's a lot of the standard library that still
00:44:11.760
shares data um and so isn't it self-thread safe and so when you turn on multi-threading
00:44:18.720
um there's there's some risks which is why it isn't enabled by default
00:44:25.079
um but as long as you pay attention to those things that also
00:44:31.920
was working pretty flawlessly now golang
00:44:46.260
yeah no I mean I'm I'm with you there I I
00:44:52.140
golang is one of those languages that I've used it before and I understand okay you know the the fact that you've
00:45:00.060
got a standard Library that's statically linked so you can just share your binary
00:45:05.760
anywhere that's pretty useful but it's it's just kind of a ugly no fun language
00:45:12.900
skills to me like genetic programming yeah
00:45:24.839
yeah I thought about that because the source
00:45:29.940
but still behind you yeah
00:45:37.020
writing something
00:45:52.079
yep that's production and I need to
00:46:03.780
yeah so um I've got a couple
00:46:09.359
couple thoughts there um and I'm not sure I'm not sure if this
00:46:14.640
this exactly applies to what you're talking about but there is a um a
00:46:21.060
library and now that I'm up here on stage I'm blanking on its exact name it starts
00:46:27.780
with an A um that lets you run
00:46:33.359
lets you embed Ruby in Crystal essentially um so that you can you can run both
00:46:41.880
on pass data back and forth between them but it sounds like you're saying you've
00:46:46.920
got one body of code
00:47:00.060
uh-huh
00:47:24.920
I mean you can you know Crystal will will compile something even if it's
00:47:31.319
called dot RB yeah yeah yeah that that's actually in some in some of the you know
00:47:37.920
examples that that you didn't see that's exactly what I did is I had one file called dot RB and I just compile it you
00:47:44.520
know yeah you so you can actually physically use the same file as long as it'll compile
00:47:54.960
yep yeah you can just require blah blah.rb and it should work
00:48:09.960
and does crystal generate a single binary yeah it generates a single binary um
00:48:16.319
So like um okay let's just go
00:48:24.119
well actually let's do this so if we do
00:48:31.020
um if you want to see if you want to see
00:48:37.140
all of the steps you can do it PST and then Dash release builds a slightly
00:48:42.359
optimized version um
00:48:48.060
now the the compiling is a little bit slower than say golang because at the
00:48:55.079
llvm level it's applying quite a few optimizations and so most of the time
00:49:00.660
taken is waiting for that final step um
00:49:09.540
but then if we do a yes so
00:49:17.579
oh I edited it and then messed that up but that's okay
00:49:22.740
um it's still built
00:49:30.060
oh it didn't build okay but um I have I've got the rest version there so you
00:49:35.400
can see that the rest version is about three megabytes the crystal version is
00:49:40.560
987 kilobytes it's just a single executable um
00:49:58.800
so basically the same thing just yeah
00:50:07.200
and there is that that is actually strippable um so if you really wanted a very small file size you can
00:50:19.200
you can knock it down quite a bit um let's find out
00:50:25.140
um
00:50:33.660
so it actually strips down slightly smaller yeah
00:50:42.180
and that that is I guess one of the um I guess one of the negatives to Crystal is
00:50:47.640
that if you have if you have a very very large piece of software um when you compile it
00:50:54.720
especially if you're running on a laptop that's not plugged in you know it can it can take a little bit
00:51:01.920
of time but most you know most of the time you aren't going to be compiling it in
00:51:07.619
release mode and if you compile it not in release mode it's a lot faster
00:51:13.020
the thing that it doesn't do is it doesn't do partial partial compilation
00:51:18.420
so it doesn't it isn't very good at reusing things that had already compiled because you
00:51:24.660
can reopen classes and you can change them and stuff like that and so it's a really hard problem for it to know what
00:51:31.200
it can actually reuse so it ends up just rebuilding everything most of the time
00:51:38.579
yeah yeah if if it doesn't yeah if it does cache them so like you know I
00:51:44.940
just I just built that and if I built it again um
00:51:51.540
it was always small enough that there wasn't a lot of difference but it was faster um because it does cash in but if I go
00:51:57.000
change anything it's going to rebuild everything
00:52:03.240
yeah so
00:52:09.300
so so the primary use case is debugging because um
00:52:15.119
you know you know whoops you know if you're writing Ruby code and you're you're hacking on something sometimes the easiest way to debug it is just to
00:52:21.900
drop into a price session or use IRB um and so with
00:52:28.619
with the the interpreted mode you have essentially it's essentially pry
00:52:33.900
basically they duplicated pry here um and so you have a price session and
00:52:40.559
you can use it exactly the same way pretty much but you can also use it just
00:52:46.260
to directly run your stuff so you can do um
00:52:52.020
and actually the Fibonacci calculator is a terrible one because it'll be really slow on my unplugged in computer but um
00:53:01.020
you can go ahead and run it oh that was the execute that was the binary
00:53:06.900
yeah there yeah so this is a terrible example right now because The Interpreter is not as fast
00:53:14.940
as Ruby um yeah it's brand new it's completely
00:53:20.579
unoptimized so it is not as fast as Ruby and so on something like this it's it's pretty slow
00:53:26.339
but it's really useful for debugging and things like that yeah
00:53:34.319
um yeah it has some limitations because because it is so new um if you go and you go to the crystal Lang
00:53:41.040
install thing and you just install from from an apt um you know or something like that it's
00:53:47.579
not going to be enabled by default um because it's still considered experimental so you've got to go to the sources and build it but um
00:53:55.800
building it is incredibly easy basically it's just a you run make and it builds
00:54:01.740
um and so you can you can go if you want The Interpreter you go to the sources
00:54:07.559
and um let's make interpreter equals one
00:54:13.559
and that'll build it with The Interpreter enabled um however there are some there's some
00:54:19.680
bugs basically I mean that's what the limitations are there's just some bugs and so there's some some things where
00:54:25.079
you start doing especially when you start doing the more esoteric stuff there's some places some
00:54:30.300
edge cases where it just breaks but because crystal is implemented in Crystal essentially what The Interpreter
00:54:36.119
is doing is it's reusing all of those implementations that already exist that were already written in Crystal and
00:54:42.300
aren't just compiled it's just reusing them in an interpreted fashion
00:54:58.440
so yeah if you guys have any other questions anybody has any other questions at any point
00:55:04.680
um I I'm here and I'm happy to talk about it I love Ruby but I also really love
00:55:11.339
Crystal thank you