Skip to content

Instantly share code, notes, and snippets.

@foeken
Last active November 24, 2024 09:35
Show Gist options
  • Save foeken/9dd3d301a34b75ccf31348b52cac48c7 to your computer and use it in GitHub Desktop.
Save foeken/9dd3d301a34b75ccf31348b52cac48c7 to your computer and use it in GitHub Desktop.
Inbox AI LLM Instructions
# Inbox AI
> Inbox AI is a MacOS application that allows users to automate tasks on their mac using AI. It allows for the creation of custom voice interfaces, can automatically handle incoming mail, and process images from screenshots, or by watching directories.
Important notes:
- Users will likely have a specific goal or task to automate which often requires an integration surface. Inbox AI supports APIs, Terminal Commands, and x-callback URLs.
- To assist, you can generate Inbox AI compatible actions in the JSON format described in the docs. When this file is downloaded and has the .inboxai extension, users can double-click install them.
- When possible generate a **downloadable file** for the user after assisting them in the right format.
- Do not show JSON to the user, this is simply an intermediate format. Instead explain WHAT you are doing. The user will have UI fields they can use to adjust the action.
## Docs
- [Inbox AI Documentation](https://dreetje-1.gitbook.io/inbox-ai)
## JSON format for actions (.inboxai)
The JSON file can contain more than one action and thus is always an array. Below are several examples to assist you.
Inbox AI has the following action types:
- folder
- makeAPIRequest
- terminalCommand
There are more actions, which are not explained here.
### Action Standard Fields
Every action has the following standard fields which will not be explained again. When a field is optional, do not include them if left blank.
```json
[
{
"type" : "folder",
"displayName" : "Example Action",
"description" : "An example description",
"instructions" : "Find the manual [here](https://example.com)",
"icon" : "pencil.tip",
"identifier" : "example",
"id" : "B9635D37-8551-42F0-A1C4-BAB835D5DD28",
"variables": [],
"folderId": "B9635D22-8551-42F0-A1C4-BAB835D5BB28",
"nextActionId": "B9635D11-8551-42F0-A1C4-BAB822D5BB28",
"forceConfigurable" : false
}
]
```
- id :: Unique UUID for this action
- displayName :: The human readable name of the action
- identifier :: The ai name of the action (no spaces)
- icon :: A "SF Symbols" descriptor of an icon
- type :: The type of the action, available types are listed above.
- description :: (Optional) The description of the action used by both AI and Humans.
- instructions :: (Optional) Human-readable instructions on how to use the action inside the app (ie explain the variables used). Supports markdown links.
- variables :: (Optional) An array of variables for ai and humans. Explained below.
- folderId :: (Optional) The UUID of the parent folder. See "folder" actions below.
- nextActionId :: (Optional) The UUID of the next action to call in the chain, the output of this action will go to the first variable of the next action.
- forceConfigurable :: (Optional) Forces the human variable configure screen to show (even if there are no human variables)
#### Variables
Variables can be used to configure the action, you have human variables wich are used as static configuration (i.e. API keys) and AI variables which can be defined by the AI at runtime (i.e some content). Below is an example variable and its fields explained.
```json
{
"ai" : true,
"id" : "5448018F-EF70-426A-BAA4-598221EADDB0",
"value" : "",
"required" : true,
"description" : "One or more tasks",
"type" : "array",
"label" : "Task List",
"name" : "taskList"
}
```
ai :: Whether this is an AI variable or not
id :: UUID of the variable
name :: The identifier of the variable (no spaces, numbers, etc) used in templates (see below) and/or AI tool calls.
required :: Only applies to AI variables, whether the AI must specify it.
description :: The description of the variable for both Human and AI
type :: The type of variable, supported are "string" and "array" (of strings)
label :: The human name of the variable
value :: (Optional) The filled value of the variable (usually blank)
#### Templating
- [Inbox AI Templating Langauge](https://dreetje-1.gitbook.io/inbox-ai/templating)
- [Stentil Docs](https://stencil.fuller.li/en/latest/builtins.html#built-in-filters-1)
Most fields in Inbox AI support template variables. Any AI or Human variable can be used in the templates. The templating language is Stencil, which some extensions and built-in variables.
The basics:
{{ name }} inserts a variable. You can use filters to process variables. Useful filters:
- {{ name | jsonEscape }} for in JSON
- {{ name | doubleQuoteEscape }} for in quoted strings in Terminal Commands
- {{ name | percentEncode }} for in URLs
### Action: Folder (folder)
```json
[
{
"type" : "folder",
"displayName" : "Examples",
"icon" : "folder",
"identifier" : "examples",
"id" : "B9635D37-8551-42F0-A1C4-BAB835D5DD28"
}
]
```
### Action: Make API Request (makeAPIRequest)
```json
[
{
"instructions" : "Uses the Tana Input API to add nodes. Optionally with your given Supertag and fills a source field.",
"variables" : [
{
"type" : "array",
"required" : true,
"id" : "5448018F-EF70-426A-BAA4-598221EADDB0",
"label" : "",
"name" : "tasks",
"description" : "One or more tasks",
"value" : "",
"ai" : true
},
{
"required" : true,
"type" : "string",
"ai" : false,
"name" : "secretApiKey",
"id" : "44463E85-CB39-496E-AF3C-A5868E563645",
"value" : "",
"description" : "Your Tana Workspace API Key",
"label" : "API Key"
},
{
"name" : "targetNodeId",
"value" : "",
"label" : "Destination ID",
"description" : "Enter the destination id for the tasks (Defaults to your inbox)",
"type" : "string",
"ai" : false,
"required" : true,
"id" : "09A4C01D-6569-4D94-890C-FB73AACBAB10"
},
{
"id" : "573BB78D-F241-4496-B876-1706FB5935D9",
"label" : "Supertag ID",
"type" : "string",
"value" : "",
"name" : "supertagId",
"required" : true,
"description" : "Enter the supertag id of your task supertag (Optional)",
"ai" : false
},
{
"id" : "9EC07298-5741-42E1-9EEA-952E54CF21F0",
"ai" : false,
"description" : "Enter the field id where to put extra context (Optional)",
"required" : true,
"label" : "Field ID",
"value" : "",
"name" : "fieldId",
"type" : "string"
}
],
"type" : "makeAPIRequest",
"folderId" : "",
"forceConfigurable" : false,
"id" : "DB190A51-89ED-4141-B320-5593E04C0D95",
"identifier" : "createTaskApi",
"method" : "POST",
"url" : "https:\/\/europe-west1-tagr-prod.cloudfunctions.net\/addToNodeV2",
"description" : "Add a node to Tana",
"displayName" : "Create Task (API)",
"payload" : "{\n \"targetNodeId\": \"{{targetNodeId|default:\"INBOX\"}}\",\n \"nodes\": [\n {% for task in tasks %}{\n \"name\": \"{{ task | jsonEscape }}\",\n \"supertags\": [ {% if supertagId %}{\"id\": \"{{supertagId}}\"}{% endif %} ],\n \"children\": [ {% if fieldId %}{ \"type\": \"field\", \"attributeId\": \"{{ fieldId }}\", \"children\": [{% if originalInput | match:\"message-id: <(.+?)>\" %}{ \"name\": \"message:&lt;{{ originalInput | match:\"message-id: <(.+?)>\" }}&gt;\"}{% endif %}] }{% endif %} ]\n }{% if forloop.counter != forloop.length %},{% endif %}{% endfor %} \n ]\n}\n",
"headers" : [
{
"value" : "application\/json",
"key" : "Content-Type",
"id" : "0BBCD19C-12E1-4BDE-B754-BF7BF8C4CAC9"
},
{
"key" : "Authorization",
"id" : "D8895C27-9F76-4625-B1D1-D881CA4AFAB0",
"value" : "Bearer {{secretApiKey}}"
}
],
"nextActionId" : "10000000-0000-0000-0000-000000000007",
"icon" : "network"
},
{
"displayName" : "Tana",
"forceConfigurable" : false,
"description" : "",
"icon" : "folder",
"type" : "folder",
"variables" : [
],
"instructions" : "",
"id" : "B9635D37-8551-42F0-A1C4-BAB835D5DD25",
"identifier" : "tana",
"order" : 41
}
]
```
The example above shows a web request to Tana to create a task node. It has both human and AI variables. The human variables like AI key need to be set in the app, where the AI ones are set during execution (i.e the title of the task). Below we explain the new fields this action has over the basics.
- url :: The URL of the API request
- method :: The HTTP method (GET, POST, PUT, DELETE)
- payload :: The body of the request (note the heavy use of templating here)
- headers :: A list of header objects, with header key/value pairs and unique ids. Do not forget content-type, it is often a requirement.
### Action: Terminal Command (terminalCommand)
```json
[
{
"description" : "Append data to the daily note of an Obsidian Vault",
"identifier" : "appendToDailyNote",
"command" : "open --background \"obsidian:\/\/adv-uri?vault={{ vault | default:\"Obsidian Vault\" | percentEncode }}&daily=true&mode=append&{% if heading %}heading={{ heading | percentEncode }}{% endif %}&data={{ content | percentEncode }}{% if originalInput | match:\"message-id: (<.+?>)\" %}{{ \" ([Source](message:\" | percentEncode }}{{ originalInput | match:\"message-id: (<.+?>)\" | percentEncode }}{{ \"))\" | percentEncode }}{% endif %}\"",
"order" : 23,
"forceConfigurable" : false,
"useSSH" : false,
"icon" : "terminal",
"folderId" : "30E1CF2C-C707-4A8A-A5AE-A86FF2CC573B",
"type" : "terminalCommand",
"id" : "18AED962-9DD1-4CE6-BAE8-6E95AE0B4B13",
"displayName" : "Append to Daily Note",
"instructions" : "Append content to your daily note in Obsidian. Requires [Advanced URI Plugin](obsidian:\/\/show-plugin?id=obsidian-advanced-uri).",
"variables" : [
{
"required" : true,
"ai" : false,
"label" : "Vault",
"type" : "string",
"description" : "Your Obsidian Vault name, defaults to \"Obsidian Vault\"",
"name" : "vault",
"id" : "F40DF066-FEA8-424F-B23F-3FC57EAC62C1",
"value" : ""
},
{
"description" : "The string to append",
"id" : "BA130E59-F7F0-435F-9B34-69C52E58E8A2",
"type" : "string",
"ai" : true,
"value" : "",
"name" : "content",
"required" : true,
"label" : "Label"
},
{
"description" : "The heading to place the tasks under (Optional)",
"label" : "Heading",
"ai" : false,
"name" : "heading",
"id" : "8E0FF915-BE50-499D-B588-6E0C17074678",
"value" : "",
"type" : "string",
"required" : true
}
]
}
]
```
If terminal commands do not work, the user might better use SSH tunneling or check they have given Inbox AI sandbox access to the directory in question (under advanced settings)
- command :: The terminal command (note the templating, and filters used)
- useSSH :: Inbox AI runs under the Apple Sandbox, thus tunnels the more interesting commands through SSH.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment