# Custom Code

The **Custom Code** tool allows you to add complex logic to a workflow that might otherwise be difficult with MESA's built-in tools. You can create custom integrations to third-party services, even those that MESA does not yet integrate, and code custom business logic using JavaScript.

## Configure

### To open the code editor

Click the **\</> Edit Code** button to edit your custom code.

<figure><img src="https://3425906282-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F1H6u1HQc3Iew7ATmmiCi%2Fuploads%2FVgF1nP7H2reGOlVDlN9i%2Fimage.png?alt=media&#x26;token=1fc413d2-9aeb-450c-a500-7cbc6a2190f3" alt=""><figcaption></figcaption></figure>

### Anatomy of a Custom Code step

```javascript
const Mesa = require('vendor/Mesa.js');

/**
 * A MESA Script exports a class with a script() method.
 */
module.exports = new class {

  /**
   * MESA Script
   *
   * @param {object} prevResponse The response from the previous step
   * @param {object} context Additional context about this task
   */
  script = (prevResponse, context) => {

    // Retrieve the Variables Available to this step
    const vars = context.steps;

    // Add your custom code here
    let response = {}

    // Call the next step in this workflow
    // response will be the Variables Available from this step
    Mesa.output.next(response);
  }

}
```

Code is executed in a V8 environment and can be written in standard JavaScript or ES6. When this step is run, the `script()` method will be called with two parameters: `prevResponse` and `context`. In order for your workflow to continue its subsequent steps, be sure to include a call to `Mesa.output.next(response);` somewhere within your `script()` method.

#### The `context` object

<table><thead><tr><th width="169">Property</th><th width="133">Type</th><th>Description</th></tr></thead><tbody><tr><td>steps</td><td><code>Object</code></td><td><p>An object containing the variables for each step that has been run so far, named with the step's unique key.</p><p>For example, to access a step with a key of "shopify" use: <code>context.steps['shopify']</code>.</p></td></tr><tr><td>trigger</td><td><a href="#the-trigger-object">Trigger</a></td><td>This object is the configuration of the current step being run.</td></tr><tr><td>task</td><td><a href="#the-task-object">Task</a></td><td>This object is information about the current task's execution.</td></tr></tbody></table>

#### The `Trigger` object

<table><thead><tr><th width="167">Property</th><th width="133">Type</th><th>Description</th></tr></thead><tbody><tr><td>metadata</td><td><code>Object</code></td><td>The values entered in configuration fields, with variable replacements.</td></tr><tr><td>raw_metadata</td><td><code>Object</code></td><td>The values entered in configuration fields, without variable replacements.</td></tr><tr><td>fields</td><td><code>Object</code></td><td>An object of the configuration fields from the UI.</td></tr></tbody></table>

#### The `Task` object

<table><thead><tr><th width="168">Property</th><th width="133">Type</th><th>Description</th></tr></thead><tbody><tr><td>context.headers</td><td><code>Object</code></td><td>A key-value object of the HTTP headers passed to this task.</td></tr><tr><td>is_test</td><td><code>Object</code></td><td>Is the current task being run as a test?</td></tr></tbody></table>

### Using Libraries

Libraries offer built-in functionality that extends the power of your code. The [MESA SDK library](https://docs.getmesa.com/tools/custom-code/libraries/sdk) is included by default and [other libraries](https://docs.getmesa.com/tools/custom-code/libraries) can be imported as needed.

## Going Further

### Logging information

To debug your script, it can be helpful to log data at a particular step in your code. This can be done by calling [`Mesa.log.info()`](https://docs.getmesa.com/tools/libraries/sdk#mesa.log.info-message-meta). This is equivalent to `console.log()` in browser-based JavaScript. When the workflow runs, the info will be available in your workflow's [Logs tab](https://docs.getmesa.com/workflow-activity/logs).

<figure><img src="https://3425906282-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F1H6u1HQc3Iew7ATmmiCi%2Fuploads%2F6apBakugfH0F0ffcKUWv%2Fimage.png?alt=media&#x26;token=fbeb730c-b689-4def-90d9-551e778a0492" alt=""><figcaption></figcaption></figure>

### Throwing errors

Throw a JavaScript error to halt the execution of your workflow:

```javascript
throw new Error("your error description")
```

In the User Interface, this will look like:

<figure><img src="https://docs.getmesa.com/~gitbook/image?url=https%3A%2F%2F3425906282-files.gitbook.io%2F%7E%2Ffiles%2Fv0%2Fb%2Fgitbook-x-prod.appspot.com%2Fo%2Fspaces%252F1H6u1HQc3Iew7ATmmiCi%252Fuploads%252Fgit-blob-8a5e2b2128c4b36c509295e5388274a9fc4ea252%252Ffile-m3mgczb5y3.png%3Falt%3Dmedia&#x26;width=768&#x26;dpr=4&#x26;quality=100&#x26;sign=943c5393&#x26;sv=1" alt=""><figcaption></figcaption></figure>

### Interacting with external APIs <a href="#how-do-i-get-advanced-details-related-to-my-automation" id="how-do-i-get-advanced-details-related-to-my-automation"></a>

Use [`Mesa.request.get()`](https://docs.getmesa.com/tools/libraries/sdk#mesa.request.get-path-options) to make HTTP requests to external APIs. This is the equivalent to `fetch()` in browser-based JavaScript.

## Technical Notes

### Timezones

All system timezones use your Shopify Store's timezone. You can view and update your timezone from the Shopify Dashboard: Admin > Settings > General, under "Standards and formats". If you need to get dates in a different timezone, use the [Mesa.date.setTimezone(timezone)](https://docs.getmesa.com/tools/libraries/sdk#mesa.date.settimezone-timezone) method.

### Unsupported NodeJS methods

Scripts are run in a stock V8 environment. This means that some common NodeJS methods are not available:

* `request()`: Alternative: `Mesa.request.*()` [Documentation](https://docs.getmesa.com/tools/libraries/sdk#mesa.request.get-path-options).
* `console.log()`: Alternative: `Mesa.log.*()` [Documentation](https://docs.getmesa.com/tools/libraries/sdk#mesa.log.info-message-meta).
* `async` or `await`: All `Mesa.request.*()`  methods are synchronous, so `async` and `await`  are not necessary.
* DOM manipulation methods: Alternative: `Mesa.xml.decode()` [Documentation](https://docs.getmesa.com/tools/libraries/sdk#mesa.xml.decode-xmlstring-namespacesep).
