WEBVTT
00:00.320 --> 00:00:03.679
Hello all! Welcome to EmacsConf 2021.
00:00:03.679 --> 00:00:05.040
I'm Tom Gillespie.
00:00:05.040 --> 00:00:06.799
Thank you to the organizers for
00:00:06.799 --> 00:00:07.680
all your hard work,
00:00:07.680 --> 00:00:08.639
and for inviting me to
00:00:08.639 --> 00:00:10.021
give this short talk on
00:00:10.021 --> 00:00:12.240
"Org as an executable format".
00:00:12.240 --> 00:00:13.840
The links to the talk page,
00:00:13.840 --> 00:00:16.000
the GitHub page for the project,
00:00:16.000 --> 00:00:18.880
and the package on MELPA
00:18.880 --> 00:00:20.160
are listed on the right.
00:00:20.160 --> 00:00:21.760
Let's start with one of the motivating
00:00:21.760 --> 00:00:25.920
use cases for executable Org files.
00:25.920 --> 00:00:29.339
Many users keep global configuration
00:00:29.339 --> 00:00:31.840
for Org in an init.el file,
00:00:31.840 --> 00:00:33.520
which works for many workflows.
00:00:33.520 --> 00:00:36.239
However, for reproducible research,
00:00:36.239 --> 00:00:37.600
this is a challenge
00:00:37.600 --> 00:00:39.280
because if an Org file is
00:00:39.280 --> 00:00:41.440
dissociated from the init.el file,
00:00:41.440 --> 00:00:43.040
then often it will no longer
00:00:43.040 --> 00:00:44.640
function as expected.
00:44.640 --> 00:46.719
One potential solution to this problem
00:46.719 --> 00:48.160
is to be able to include all of the
00:48.160 --> 00:00:50.239
global configuration for Emacs
00:00:50.239 --> 00:00:52.960
and the environment in the Org file itself,
00:00:52.960 --> 00:00:53.840
in which case when you
00:00:53.840 --> 00:00:55.440
go to reuse the Org file,
00:00:55.440 --> 00:00:58.640
it will work as expected.
00:58.640 --> 00:01:00.480
What does an executable Org file
00:01:00.480 --> 00:01:02.559
look like in action?
01:02.559 --> 01:05.280
Here's a demo of an executable Org file
01:05.280 --> 01:09.680
running in Bash, Dash, Zsh, and PowerShell.
01:09.680 --> 00:01:14.799
So, we are currently in Bash,
01:14.799 --> 01:19.360
and we can run our demo,
01:19.360 --> 00:01:21.119
and it will print some stuff,
00:01:21.119 --> 00:01:22.640
and wait for input.
01:22.640 --> 00:01:24.144
We can also run it in Dash,
00:01:24.144 --> 00:01:25.720
which is the default for Debian
00:01:25.720 --> 00:01:29.840
and derivatives.
01:29.840 --> 01:32.320
Same program works as expected.
01:32.320 --> 00:01:38.560
Zsh also. And lastly PowerShell,
01:38.560 --> 00:01:41.439
if we try to run demo.org itself,
00:01:41.439 --> 00:01:42.640
we see (that) we get an error
00:01:42.640 --> 00:01:43.764
because PowerShell cares
00:01:43.764 --> 00:01:45.439
about file extensions,
01:45.439 --> 00:01:49.840
so, if we symlink to ps1,
00:01:49.840 --> 00:01:51.680
then it works as expected,
00:01:51.680 --> 00:01:53.341
and there are ways to alias this,
00:01:53.341 --> 00:01:55.044
so that you can run it as a program
00:01:55.044 --> 00:01:58.640
without the ps1 extension.
01:58.640 --> 02:03.920
So, how does this work?
02:03.920 --> 00:02:05.759
There are three components
00:02:05.759 --> 00:02:07.352
to an executable Org file
00:02:07.352 --> 00:02:08.560
that all need to be present
00:02:08.560 --> 00:02:10.080
in order for this to work.
02:10.080 --> 02:11.920
Starting from the top of the file,
02:11.920 --> 02:14.239
we have a shebang block.
02:14.239 --> 00:02:16.640
Next we have an Org Babel block
00:02:16.640 --> 00:02:17.760
written in Emacs Lisp,
00:02:17.760 --> 00:02:20.000
which is what we actually saw executing,
00:02:20.000 --> 00:02:20.959
and then there are some
00:02:20.959 --> 00:02:23.520
eval local variables or Elvs
02:23.520 --> 02:25.200
that are involved in making this
02:25.200 --> 02:26.800
actually executable.
02:26.800 --> 02:29.760
Let's start with the shebang block.
02:29.760 --> 00:02:33.280
Org syntax does not have support
00:02:33.280 --> 00:02:34.959
for shebang lines.
02:34.959 --> 02:37.120
However, it supports the shebang block.
02:37.120 --> 02:39.440
This is because Org comments, blocks,
02:39.440 --> 00:02:41.760
keywords, etc. that start with the
00:02:41.760 --> 00:02:43.920
sharp sign have the same syntax as
00:02:43.920 --> 00:02:46.720
comments in POSIX and PowerShell.
02:46.720 --> 00:02:53.280
This block is in fact valid
02:53.280 --> 00:02:55.040
Bash, Dash, Zsh, PowerShell,
00:02:55.040 --> 00:02:57.280
and maybe some other shells as well.
02:57.280 --> 00:03:02.480
In essence what it does is,
03:02.480 --> 00:03:03.440
perform some setup
00:03:03.440 --> 00:03:06.080
to avoid polluting standard output,
00:03:06.080 --> 00:03:07.516
and then it runs Emacs
00:03:07.516 --> 00:03:08.959
to load the file itself.
00:03:08.959 --> 00:03:12.640
The Elisp that is passed on the command line
00:03:12.640 --> 00:03:14.959
is explicated over here on the right,
03:14.959 --> 00:03:17.920
and in essence what it does is,
00:03:17.920 --> 00:03:20.480
to keep the startup time minimal
00:03:20.480 --> 00:03:21.760
and as low as possible,
00:03:21.760 --> 00:03:24.080
it loads the absolute bare minimum
00:03:24.080 --> 00:03:25.120
needed for Babel,
00:03:25.120 --> 00:03:27.519
and then it calls hack-local-variables
00:03:27.519 --> 00:03:31.680
triggering the eval-local-variables.
03:31.680 --> 00:03:33.614
What do the eval-local-variables do,
00:03:33.614 --> 00:03:34.799
and how those work?
00:03:34.799 --> 00:03:36.319
The essence of the approach is to
00:03:36.319 --> 00:03:38.720
use org-confirm-babel-evaluate
00:03:38.720 --> 00:03:40.480
to allow Babel execution.
00:03:40.480 --> 00:03:43.360
We can't set it to nil because that is
00:03:43.360 --> 00:03:45.308
an arbitrary code execution vector,
00:03:45.308 --> 00:03:48.000
which we don't want if we're sharing files.
03:48.000 --> 00:03:49.555
Instead what we do is,
00:03:49.555 --> 00:03:52.000
we use the fact that it can be a function,
00:03:52.000 --> 00:03:55.280
and we normalize the block of code,
00:03:55.280 --> 00:03:57.320
we checksum it, and then we check
00:03:57.320 --> 00:03:59.280
that it matches this checksum up here
00:03:59.280 --> 00:04:00.400
at the top of the file,
00:04:00.400 --> 00:04:02.640
and then sort of inside there,
04:02.640 --> 00:04:04.159
inside of org-sbe,
00:04:04.159 --> 00:04:06.560
which is Org source block evaluate,
04:06.560 --> 04:08.959
we call the block.
04:08.959 --> 00:04:11.120
The actual implementation of this
00:04:11.120 --> 00:04:12.497
is somewhat more complicated.
00:04:12.497 --> 00:04:14.799
However, it's small enough to fit in
00:04:14.799 --> 00:04:17.519
the local variables at the end of the file.
04:17.519 --> 00:04:19.040
One thing to note is that
00:04:19.040 --> 00:04:20.799
if you are using PowerShell,
00:04:20.799 --> 00:04:23.919
PowerShell parses the whole file
00:04:23.919 --> 00:04:25.040
which means that
00:04:25.040 --> 00:04:27.759
for any normal Org content,
00:04:27.759 --> 00:04:28.639
you need to put it in
04:28.639 --> 00:04:30.240
a multi-line PowerShell comment,
00:04:30.240 --> 00:04:31.199
and close it.
00:04:31.199 --> 00:04:32.371
So, once we hit
00:04:32.371 --> 00:04:34.160
hack-local-variables at the end,
00:04:34.160 --> 00:04:37.120
we run the eval-local-variables block,
00:04:37.120 --> 00:04:40.880
then we enter this Elisp block,
04:40.880 --> 00:04:42.720
and you can write whatever you want.
00:04:42.720 --> 00:04:44.160
All the power of Org Babel is
00:04:44.160 --> 00:04:45.360
now at your fingertips
00:04:45.360 --> 00:04:47.199
in order to do what you need
04:47.199 --> 04:48.800
for this file.
04:48.800 --> 00:04:50.320
Finally, let's do a quick demo
00:04:50.320 --> 00:04:52.453
of how to use this to make
00:04:52.453 --> 00:04:54.800
your own Org files executable.
04:54.800 --> 00:05:01.840
Orgstrap is available on MELPA as mentioned,
05:01.840 --> 00:05:06.080
and it can be installed using package.el
00:05:06.080 --> 00:05:11.280
by calling package-install orgstrap.
05:11.280 --> 05:13.520
It will download, and it will install.
05:13.520 --> 00:05:18.720
Then you can open an existing file
05:18.720 --> 00:05:21.919
or a new file. In this case,
00:05:21.919 --> 00:05:25.199
let me open a file called example.org.
05:25.199 --> 00:05:26.996
And then orgstrap provides
00:05:26.996 --> 00:05:29.360
command called orgstrap-init.
05:29.360 --> 00:05:30.953
What orgstrap-init does is,
00:05:30.953 --> 00:05:33.759
it populates a file with the machinery
05:33.759 --> 00:05:36.639
needed to run an orgstrap block.
00:05:36.639 --> 00:05:38.560
We're just going to do a message
05:38.560 --> 05:43.440
"hello orgstrap!".
05:43.440 --> 00:05:46.160
If you look up at the top,
00:05:46.160 --> 00:05:47.386
you will see that the
00:05:47.386 --> 00:05:50.320
orgstrap-block-checksum will change
05:50.320 --> 00:05:51.520
when I save the file.
00:05:51.520 --> 00:05:53.840
This makes it much easier to author files
00:05:53.840 --> 00:05:55.120
with orgstrap blocks.
00:05:55.120 --> 00:05:56.560
And then we need one last piece
00:05:56.560 --> 00:05:57.876
of machinery,
00:05:57.876 --> 00:06:00.400
which is the shebang block.
00:06:00.400 --> 00:06:01.520
I am just going to steal
00:06:01.520 --> 00:06:02.560
the shebang block from
00:06:02.560 --> 00:06:06.080
this other file over here
06:06.080 --> 00:06:07.039
since it is available.
00:06:07.039 --> 00:06:08.880
You can also get it from shebang.org,
00:06:08.880 --> 00:06:10.800
and I have plans to add a command
00:06:10.800 --> 00:06:12.560
to insert this into the file directly,
00:06:12.560 --> 00:06:15.600
which may actually be done by the time
00:06:15.600 --> 00:06:19.520
this video is actually posted and visible.
06:19.520 --> 00:06:21.120
There's one last step,
00:06:21.120 --> 00:06:24.160
which is that we need to run dired
06:24.160 --> 00:06:27.520
in order to… There we go.
06:27.520 --> 06:31.039
So, we use Shift m, capital m,
06:31.039 --> 00:06:32.800
in order to make our
00:06:32.800 --> 00:06:35.520
example file executable,
06:35.520 --> 00:06:42.140
and then if we come back to here,
00:06:42.140 --> 00:06:47.360
we see that example.org is now executable,
00:06:47.360 --> 00:06:48.000
and we can run it.
06:48.000 --> 06:50.560
"hello orgstrap!", and we're done.
06:50.560 --> 06:52.639
So, that's the basic workflow
06:52.639 --> 06:54.880
for getting orgstrap files
06:54.880 --> 00:06:56.240
to be executable.
00:06:56.240 --> 00:06:58.960
I will be around to answer questions live,
00:06:58.960 --> 00:07:00.800
and I will be also available in
00:07:00.800 --> 00:07:03.280
the #emacsconf IRC channel all day.
00:07:03.280 --> 00:07:04.960
I hope you have found this useful,
00:07:04.960 --> 00:07:08.160
and thank you very much for watching.
00:07:08.160 --> 00:07:09.160
[captions by bhavin192 (Bhavin Gandhi)]