Automate Your Roam Workflows With SmartBlocks

Ramses Oudt
Ramses Oudt
Automate Your Roam Workflows With SmartBlocks

How much have you automated in Roam? Answer: not enough.

In this article I’ll introduce you to most valuable plugin to automate you workflows: SmartBlocks.

We’ll get into how to use existing workflows, create new ones, and automate so much that you can ditch your text expansion tool or even some wonky scripts you’ve created yourself. With Roam42’s SmartBlocks, even non-techies can program their workflows to perfection.

The basic components of SmartBlocks

SmartBlocks have four components:

  • Workflows—a collection of text blocks and action blocks (the latter making everything interactive).
  • Actions—the steps that are completed in the workflow.
  • Commands—the snippets of code that you add to actions, making them dynamic.
  • Triggers—used to execute a workflow (start by typing xx and then the name of the workflow).

You could compare workflows to text templates you set up in text expansion tools like TextExpander or Alfred. An important difference is that SmartBlocks exist entirely in Roam, meaning it works on all of your devices without additional installation necessary. Furthermore, SmartBlocks are smart, meaning they are dynamic (and so can change depending on the input) instead of static chunks of text like most text expansion templates.

Actions are the individual blocks that the SmartBlocks workflow executes. They can be either static (plain text) or dynamic (commands).

Commands are the snippets of code that make SmartBlocks dynamic. They often have a parameter, which gives you control over the data that is shown. If you’re familiar with programming, you can best compare commands to functions.

Finally, you run SmartBlocks workflows using the trigger, which always starts with xx followed by the name of the trigger (the examples below still use the old trigger ;;).

How to use existing workflows

Before diving into how to combine the building blocks to create your own SmartBlocks, let’s have a look at a few built-in workflows so we get a better sense of what’s possible.


Screenshot shows the old ;; trigger, now replaced by xx

Typing the trigger xxday, you get a list of predefined mini-workflows that do one thing: create a link to the date of a day between now and a week into the past or future.

Out of the box, Roam only has the /yesterday, /today, and /tomorrow triggers.


Screenshot shows the old ;; trigger, now replaced by xx

Typing the trigger xxtime, you get the option to insert the current time in 24-hour format (like the native /time trigger does), or in 12-hour format (AM/PM).

The triggers with the gear icon in front are commands (covered below).


Screenshot shows the old ;; trigger, now replaced by xx

Typing the trigger xxtodo, you get access to a few powerful workflows that now make Roam a mature task-management system. The predefined TODO workflows fetch the block references to all TODOs that meet the selected criterion.

It’s worth noting that the SmartBlock needs a way to associate a date with the TODO. It therefore only finds the TODOs that have a date link in the TODO block itself. Alternatively, you can pick a workflow that also fetches all matching TODOs from the Daily Notes page (DNP in the workflow name).

The triggers with the gear icon in front are commands (covered below).


Screenshot shows the old ;; trigger, now replaced by xx

Two small but handy predefined workflows allow for serendipitous encounters. By typing either xxrandom or xxseren, you get the option to either pull a random block reference or a page name (in the form of a link) from the database.

In the section below, we’ll dive into a command that lets you specify from what page you want to pull random block references.

How to create workflows with SmartBlocks

In the previous section you saw a few screenshots with a gear icon in front of the trigger name. These are triggers for commands, one of the key components that enable us to automate our workflows. We’ll use them to create a few simple workflows, which are good starting points to progressively build more complex ones.

But first, the basic format of a SmartBlock:

All SmartBlock workflows start with a parent block that contains the tag #42SmartBlock and the name of the workflow. Nested below this block are all the action blocks, containing either static text or dynamic content (using commands).

If you don’t want to remember this format, there’s also a starter workflow available. Simply type xxstarter and select the Workflow Starter workflow (how meta!). A prompt will appear, asking for the name you wish to give to your custom workflow:

That’s it! After this, start creating your workflow by adding text and commands. There are already many commands available, so I suggest checking out the official Roam42 documentation which explains all commands in detail.

Let’s now build two simple but dynamic workflows together.

Using commands to make workflows dynamic

Before we start building, it’s important to understand the basic structure of commands.

Each command starts with <% and ends with %>. Between those symbols, it always contains the command name (written in UPPERCASE) and sometimes also one or several parameters coming after the colon (:).

An example:

As you can see, SmartBlocks really are smart as you can enter natural language in some parameters and it’ll then interpret what you meant.

At other times, the parameter is simple and only limits how many blocks a command fetches. For example this command, which out-of-the-box comes with a parameter filled in that indicates that no more than 20 block references should be shown:

With that out of the way, let’s build some dynamic workflows!

Daily workflow with dynamic TODOs

One of the most common use cases of templates in Roam is probably to structure the Daily Notes page.

Roam doesn’t impose a structure on how you have to work, so every day you start with an empty page. How great would it be to have a dashboard ready in seconds that gives you an overview of what to focus on that day.

That’s exactly what we’re going to build now. The steps we’re going to take are as follows:

  • Create a new SmartBlock titled Daily;
  • Add the plain text blocks;
  • Add the dynamic blocks;
  • Test.

Step 1—Create the SmartBlock

Use the Workflow Starter by typing xxstarter and hitting return. In the prompt, give the workflow the name Daily.

Step 2—Add plain text blocks

Let’s give our daily template some structure by adding some headings. Personally, I like to work with links so I can quickly see how I did on other days:

Step 3—Add dynamic blocks

Using a SmartBlocks command, we now add a block that fetches all TODOs tagged for today. How? Simple, by typing xxtodotoday and selecting the TODOTODAY command:

Screenshot shows the old ;; trigger, now replaced by xx

By default, it shows a maximum of 20 TODOs: <%TODOTODAY:20%>

Let’s also add a dynamic block to fetch all overdue TODOs, just in case. For this, we use the TODOOVERDUEDNP command to see all TODOs that were explicitly tagged with a date and the ones on all Daily Notes pages before today.

The finished workflow looks like this:

Step 4—Test the workflow

Like any good programmer, it’s necessary to test all workflows before using them in the wild. Why? Because you don’t want to be confronted with errors when you’re ready to do some work.

To test, go to your Daily Notes page and type xxdaily. You’ll see the Daily workflow in the list. The colored blocks in front of the workflow name indicates it’s a custom-made workflow. Hit return/enter to activate the workflow.

Screenshot shows the old ;; trigger, now replaced by xx

Did the workflow run and did it retrieve TODOs? If not, check if you have any TODOs tagged for today or that were tagged with a date in the past. If none exist, create a TODO on today’s Daily Notes page and run the workflow again to test if it shows.

Random Journaling prompts

Another useful use case for SmartBlocks is when you use Roam for journaling. We’ll start by showing how to grab a writing prompt from a specific page and then link your journal entry to that prompt.

Our build steps are as follows:

  • Create a new SmartBlock titled Journaling prompt;
  • Randomly grab a prompt from the page Journaling prompts;
  • Link the journal entry to the prompt;
  • Test.

Step 1—Create the SmartBlock

Use the Workflow Starter by typing xxstarter and hitting return. In the prompt, give the workflow the name Journaling prompt.

Step 2—Add a command to grab a random journaling prompt

Make sure you have a page with journaling prompts (one per block). In this example, we’ll assume that page is titled Journaling prompts.

In the first child block of the SmartBlock just created, enter xxrandomblockfrom and select the command from the list:

Screenshot shows the old ;; trigger, now replaced by xx

After the colon, enter the page name Journaling prompts (don’t include the double brackets):

With this, the workflow is theoretically ready for use. But, we want to link the journal entry to its prompt, so an additional step is needed.

Each prompt we get by using this workflow will be a block reference. That means that any child block of the reference will be associated with it. This is useful if you want to see what you answered previously to specific prompts by checking its linked references.

To avoid the mistake of not nesting the journal entry under the prompt, we add an empty child block to the workflow. To make things easier, we also add the <%CURSOR%> command to put the cursor in the journal entry block as soon as the workflow is activated:

Step 4—Time to test!

Go to the Daily Notes page and trigger the workflow by typing xxJournaling and hitting return. Personally, I like to nest my journal entries underneath the Daily Log tag.

You should see the following:

Anything you write in the bullets nested underneath the prompt will be linked to it. You can verify this by going to the page with your prompts and check the references:

Clicking the number indicating the amount of references, you get to see them:

Closing words

And that’s how you use and create SmartBlocks! In future articles, we’ll dive deeper into specific commands and what cool things are possible with them.

Need more inspiration right now? Check out the official SmartBlocks repository on GitHub.

Join the conversation.

Great! Check your inbox and click the link
Great! Next, complete checkout for full access to Think Stack Club
Welcome back! You've successfully signed in
You've successfully subscribed to Think Stack Club
Success! Click here to start your premium onboarding.
Success! Your billing info has been updated
Your billing was not updated