<commit_before>---
layout: documentation
description: "Blocks are the foundation of workflows. Each one represents a step to be completed."
icon: "fa-th-large"
title:  "Blocks"
---

* TOC
{:toc}

## Blocks

Blocks are the foundation of Zazu plugins and are defined in the `zazu.json`
file in each plugin. Each one represents a step to be completed. Along the way,
each block passes a value from one block to the next. If they fork, each block
will get their own copy of the current value.

Blocks link to other blocks via `connections`. Once a blocks gets executed,
it's connections will get executed after. You can link to both output and input
blocks. All blocks have connections unless the block explicitly mentions
otherwise.

All blocks can have the following properties:

* `id` *mixed*: Unique identifier of the block, used for logging and
  connections.
* `connections` *mixed[]*: Blocks to execute if one of the results are chosen.
* `type` *string*: Name of the block you wish to use.

Each unique block type can have it's own properties, listed below with their
descriptions.

If a block is missing a required argument, you will see an error in the `Plugin
Debugger` or in the logs in `~/.zazu/log/`.

## External Blocks

External blocks are ways of accessing Zazu plugins without using the Zazu search
bar. These types of blocks are unique because they cannot be used as a connection.

~~~ json
{
  "blocks": {
    "external": [
      // trigger blocks
    ]
  }
}
~~~

### Hotkey

When a user hits a specific set of keys, it can activate an input or output
block of your plugin.

A hotkey can be overwritten in the user's local [configuration file](/documentation/configuration/#plugins).

* `hotkey` *string*: Key combination to use. [[docs]](https://github.com/electron/electron/blob/master/docs/api/accelerator.md)

In this example you have a hotkey block named `Inverse`, when somebody hits that
hotkey it goes to the next block `PlayPandora` which is most likely a [user
script](#user-script).

~~~ json
[{
  "id": "Inverse",
  "type": "Hotkey",
  "hotkey": "cmd+shift+o",
  "connections": ["PlayPandora"]
}]
~~~

### Service Script

Often a plugin will need to run jobs in the background for things like indexing
files or checking the active application. This block allows you to run your
script on a set interval. Your service is not guaranteed to run on the given
interval.

NOTICE: The connections on this block will be ignored.

Variables defined in the [configuration](/documentation/configuration/) will be
used as environment variables passed into the script.

* `interval` *int*: Milliseconds between the time we run the script. Must be `>=100`.
* `script` *string*: Path to the node file to execute.

~~~ javascript
[{
  "id": "Cache Packages",
  "type": "ServiceScript",
  "script": "cachePackages.js",
  "interval": 100
}]
~~~

Below is an example of the `Cache Packages` block we defined earlier. It fetches
a JSON file from the [internet](https://en.wikipedia.org/wiki/Internet) and
store it in the plugin directory under the name `packages.json`.

The `pluginContext` is provided when your plugin is loaded, and the returned
function will be called as needed.

~~~ javascript
// cachePackages.js
const fs = require('fs')
const http = require('http')
const path = require('path')

module.exports = (pluginContext) => {
  const packageUrl = 'http://zazuapp.org/packages.json'
  const outputFile = path.join(pluginContext.cwd, 'packages.json')

  return (env = {}) => {
    return new Promise((resolve, reject) => {<commit_msg>Fix example endpoint url. [skip ci]<commit_after>---
layout: documentation
description: "Blocks are the foundation of workflows. Each one represents a step to be completed."
icon: "fa-th-large"
title:  "Blocks"
---

* TOC
{:toc}

## Blocks

Blocks are the foundation of Zazu plugins and are defined in the `zazu.json`
file in each plugin. Each one represents a step to be completed. Along the way,
each block passes a value from one block to the next. If they fork, each block
will get their own copy of the current value.

Blocks link to other blocks via `connections`. Once a blocks gets executed,
it's connections will get executed after. You can link to both output and input
blocks. All blocks have connections unless the block explicitly mentions
otherwise.

All blocks can have the following properties:

* `id` *mixed*: Unique identifier of the block, used for logging and
  connections.
* `connections` *mixed[]*: Blocks to execute if one of the results are chosen.
* `type` *string*: Name of the block you wish to use.

Each unique block type can have it's own properties, listed below with their
descriptions.

If a block is missing a required argument, you will see an error in the `Plugin
Debugger` or in the logs in `~/.zazu/log/`.

## External Blocks

External blocks are ways of accessing Zazu plugins without using the Zazu search
bar. These types of blocks are unique because they cannot be used as a connection.

~~~ json
{
  "blocks": {
    "external": [
      // trigger blocks
    ]
  }
}
~~~

### Hotkey

When a user hits a specific set of keys, it can activate an input or output
block of your plugin.

A hotkey can be overwritten in the user's local [configuration file](/documentation/configuration/#plugins).

* `hotkey` *string*: Key combination to use. [[docs]](https://github.com/electron/electron/blob/master/docs/api/accelerator.md)

In this example you have a hotkey block named `Inverse`, when somebody hits that
hotkey it goes to the next block `PlayPandora` which is most likely a [user
script](#user-script).

~~~ json
[{
  "id": "Inverse",
  "type": "Hotkey",
  "hotkey": "cmd+shift+o",
  "connections": ["PlayPandora"]
}]
~~~

### Service Script

Often a plugin will need to run jobs in the background for things like indexing
files or checking the active application. This block allows you to run your
script on a set interval. Your service is not guaranteed to run on the given
interval.

NOTICE: The connections on this block will be ignored.

Variables defined in the [configuration](/documentation/configuration/) will be
used as environment variables passed into the script.

* `interval` *int*: Milliseconds between the time we run the script. Must be `>=100`.
* `script` *string*: Path to the node file to execute.

~~~ javascript
[{
  "id": "Cache Packages",
  "type": "ServiceScript",
  "script": "cachePackages.js",
  "interval": 100
}]
~~~

Below is an example of the `Cache Packages` block we defined earlier. It fetches
a JSON file from the [internet](https://en.wikipedia.org/wiki/Internet) and
store it in the plugin directory under the name `packages.json`.

The `pluginContext` is provided when your plugin is loaded, and the returned
function will be called as needed.

~~~ javascript
// cachePackages.js
const fs = require('fs')
const http = require('http')
const path = require('path')

module.exports = (pluginContext) => {
  const packageUrl = 'http://zazuapp.org/api/packages.json'
  const outputFile = path.join(pluginContext.cwd, 'packages.json')

  return (env = {}) => {
    return new Promise((resolve, reject) => {
{'fraction_non_alphanumeric': 0.09803921568627451, 'fraction_numerical': 0.0016806722689075631, 'mean_word_length': 4.17463768115942, 'pattern_counts': {'":': 20, '<': 3, '<?xml version=': 0, '>': 11, 'https://': 4, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '493286', 'n_tokens_mistral': 2032, 'n_tokens_neox': 1949, 'n_words': 971}