One week ago I started a discussion in Raku community on testing Raku modules suggesting Sparrow as a solution. While the discussion has been being held and various opinions have been being given, I’d like to share my experience and indeed some good results I’ve had with applying Sparrow tool to the task of testing Raku modules.
First results
* It reveals bugs – drforr/raku-OLE-Storage_Lite/issues/1 , FCO/Red/issues/421 , titsuki/raku-Chart-Gnuplot/issues/40 , HomoGlypher/issues/2
* It’s flexible enough to create even complicated tests involving databases and services, see FCO/Red/issues/421
* It’s dead simple. Taking me around 1-2 minutes to write a test for an average module. See the list of examples
* It’s light. With Alpine OS image weighted 5MB and very small Sparrow6 dependency tree, the overall test of average module would take no more 2-3 minutes. If we run on already bootstrapped instance – it’s even a seconds!
* It’s has clear and understandable syntax. Sparrow6 DSL is dead simple and easy to read and write, just see a following example
Let’s get started
The main workflow is dead easy. Spin up a docker instance, install Sparrowdo, drop a simple scenario and give it a run! Boom, within a couple of minutes you’ll get your report nice and readable. No need to wait in queue in Travis, it’s cheap, it’s easy and it’s yours!
Spin a docker instance.
Choose an alpine OS image, 5 MB. You pull it and run it with literally seconds!
docker pull alpine docker run -d -t --rm --name alpine-rakudist alpine
Bootstrap docker instance
Install Sparrowdo – a thin client to run Sparrow6 tasks on docker instance. It’s really light, just a few Raku modules as dependencies. Then bootstrap your docker instance with Rakudo and Sparrow6 environment, the last one is also extremely light and it won’t take more then a couple of minutes for the whole process and should be done only once.
zef install --/test Sparrowdo sparrowdo --bootstrap --no_sudo --docker=alpine-rakudist
Create your test
Sparrow6 DSL has all you need. Nice wrappers around zef installer, user management to create users if you need to test users installations and git-scm wrapper to fetch a module source code from Git repositories.
The simplest scenario would be something like that:
$ cat sparrowfile:
my $user = config()<user>; my $directory = "/data/test/{$user}"; my $scm = config()<scm>; user $user; directory $directory, %( owner => $user, group => $user ); git-scm $scm, %( to => $directory, user => $user, ); if os() eq 'alpine' { # this is needed for alpine rakudo installation unless "/bin/zef".IO ~~ :e { copy "/opt/rakudo-pkg/share/perl6/core/bin/zef", "/bin/zef" } # this is needed for alpine rakudo installation unless "/bin/perl6".IO ~~ :e { copy "/opt/rakudo-pkg/bin/perl6", "/bin/perl6" } } zef $directory, %( force => False, depsonly => True, user => $user, description => "Install module dependencies" ); bash "cd {$directory} && zef test .", %( description => "zef test", user => $user );
The scenario takes some parameters from config.pl6 , e.g. source code repository url and user name to run tests under:
%( user => "kind", scm => "https://github.com/Kaiepi/p6-Kind.git" )
Users installations allows to reuse the same docker instance to test various modules. Because dependencies get installed under user’s account and never clash with other modules. Another option would be – relaunch a new docker instance for every test and start from the scratch but this will add time for initialization phase.
Run scenario
I promised it’d be easy, so just launch our new shiny test on docker alpine instance:
sparrowdo --no_sudo --docker=alpine-rakudist --repo=http://repo.westus.cloudapp.azure.com
And here the report:
16:50:02 01/09/2020 [repository] index updated from http://repo.westus.cloudapp.azure.com/api/v1/index 16:50:07 01/09/2020 [create user kind] uid=1006(kind) gid=1006(kind) groups=1006(kind) 16:50:07 01/09/2020 [create user kind] user kind created [task check] stdout match <created> True 16:50:11 01/09/2020 [create directory /data/test/kind] directory path: /data/test/kind 16:50:11 01/09/2020 [create directory /data/test/kind] directory owner: <kind> 16:50:11 01/09/2020 [create directory /data/test/kind] directory group: <kind> 16:50:11 01/09/2020 [create directory /data/test/kind] directory access rights: drwxr-xr-x [task check] stdout match <owner: <kind>> True [task check] stdout match <group: <kind>> True 16:50:15 01/09/2020 [bash: git checkout https://github.com/Kaiepi/p6-Kind.git] /data/test/kind 16:50:15 01/09/2020 [bash: git checkout https://github.com/Kaiepi/p6-Kind.git] stderr: Cloning into '.'... 16:50:17 01/09/2020 [bash: last commit] commit c08acf1e4a52491a3b09e19e129efc3092cef745 16:50:17 01/09/2020 [bash: last commit] Author: Ben Davies <kaiepi@outlook.com> 16:50:17 01/09/2020 [bash: last commit] Date: Tue Dec 24 16:28:29 2019 -0400 16:50:17 01/09/2020 [bash: last commit] 16:50:17 01/09/2020 [bash: last commit] Release v0.1.0 16:50:17 01/09/2020 [bash: last commit] 16:50:17 01/09/2020 [bash: last commit] M CHANGELOG 16:50:17 01/09/2020 [bash: last commit] M META6.json 16:50:17 01/09/2020 [bash: last commit] M lib/Kind.pm6 16:50:19 01/09/2020 [bash: cd /data/test/kind && ls -l] total 32 16:50:19 01/09/2020 [bash: cd /data/test/kind && ls -l] -rw-r--r--. 1 kind kind 191 Jan 9 16:50 CHANGELOG 16:50:19 01/09/2020 [bash: cd /data/test/kind && ls -l] -rw-r--r--. 1 kind kind 8902 Jan 9 16:50 LICENSE 16:50:19 01/09/2020 [bash: cd /data/test/kind && ls -l] -rw-r--r--. 1 kind kind 408 Jan 9 16:50 META6.json 16:50:19 01/09/2020 [bash: cd /data/test/kind && ls -l] -rw-r--r--. 1 kind kind 3230 Jan 9 16:50 README.md 16:50:19 01/09/2020 [bash: cd /data/test/kind && ls -l] -rw-r--r--. 1 kind kind 3337 Jan 9 16:50 README.pod6 16:50:19 01/09/2020 [bash: cd /data/test/kind && ls -l] -rw-r--r--. 1 kind kind 114 Jan 9 16:50 dist.ini 16:50:20 01/09/2020 [bash: cd /data/test/kind && ls -l] drwxr-xr-x. 2 kind kind 22 Jan 9 16:50 lib 16:50:20 01/09/2020 [bash: cd /data/test/kind && ls -l] drwxr-xr-x. 2 kind kind 23 Jan 9 16:50 t 16:50:24 01/09/2020 [bash: Install module dependencies] stderr: All candidates are currently installed 16:50:24 01/09/2020 [bash: Install module dependencies] <empty stdout> 16:50:27 01/09/2020 [bash: zef test] ===> Testing: Kind:ver<0.1.0> 16:50:29 01/09/2020 [bash: zef test] [Kind] t/01-kind.t .. ok 16:50:29 01/09/2020 [bash: zef test] [Kind] All tests successful. 16:50:29 01/09/2020 [bash: zef test] [Kind] Files=1, Tests=3, 2 wallclock secs ( 0.02 usr 0.00 sys + 2.68 cusr 0.21 csys = 2.91 CPU) 16:50:29 01/09/2020 [bash: zef test] [Kind] Result: PASS 16:50:29 01/09/2020 [bash: zef test] ===> Testing [OK] for Kind:ver<0.1.0>
Conclusion
Sparrow could be a reasonable alternative to existing CI tools allowing test Raku distributions easy and fast. Give it a try and say you comments! Follow the RakuDist project for examples of test scenarios and further updates.
Leave a Reply