Executable Markdown
Transform code blocks into executable cells with powerful directives
What is Executable Markdown?
In Spry, fenced code blocks in your Markdown files become executable cells. Each code block can:
- Execute code in multiple languages (SQL, Bash, TypeScript, Python)
- Define dependencies on other code blocks
- Include metadata for routing and caching
- Be named and referenced throughout your pipeline
Basic Syntax
A basic executable code block looks like this:
```bash
echo "Hello from Spry!"
```Named Tasks
Give your code blocks names to reference them elsewhere:
```bash setup-db
sqlite3 app.db < schema.sql
```The task name comes after the language identifier.
Directives
Directives are special flags that control how code blocks are executed:
--descr
Add a description to your task:
```bash setup-db --descr "Initialize the database"
sqlite3 app.db < schema.sql
```--dep
Define dependencies on other tasks:
```bash seed-data --dep setup-db
sqlite3 app.db < seed.sql
```This task will only run after setup-db completes successfully.
Multiple Dependencies
Tasks can depend on multiple other tasks:
```bash deploy --dep setup-db --dep seed-data
echo "Deployment complete"
```SQL Code Blocks
SQL code blocks are special - they can become SQLPage routes:
```sql index.sql
SELECT 'hero' AS component,
'Welcome!' AS title,
'Build apps with Spry' AS description;
```The filename (e.g., index.sql) becomes the route path.
Metadata
Add JSON5 metadata to control routing and other behaviors:
```sql users.sql { route: '/admin/users', cache: 300 }
SELECT 'table' AS component;
SELECT id, name, email FROM users;
```Supported Languages
SQL
Primary language for SQLPage routes and database operations
Bash
Shell commands for setup, deployment, and file operations
TypeScript
Complex logic, API calls, and data transformations
Python
Data analysis, ML, and scientific computing tasks
Complete Example
Here's a complete example showing multiple features:
# My Application
## Setup Tasks
```bash create-db --descr "Create database file"
rm -f app.db && touch app.db
```
```bash setup-schema --dep create-db --descr "Setup schema"
sqlite3 app.db < schema.sql
```
## Application Routes
```sql index.sql { route: '/' }
SELECT 'hero' AS component,
'My App' AS title;
```
```sql users.sql { route: '/users', cache: 60 }
SELECT 'table' AS component;
SELECT * FROM users;
```Explore Task Orchestration to learn how Spry executes your code blocks in the optimal order.
How is this guide?
Last updated on