# Set Actions

The `setActions` method let's you add custom, contract and fetch actions that are executed by the nodes on the Lit Network. These actions are only invoked if the conditions set in [`setConditions`](/sdk-reference/set-conditions.md) are met.

When invoking this method, you provide an array of actions that you want to set. The `setActions` returns the Lit Action code as a `string` that will be executed on the Lit Nodes and an `unsignedTransactionDataObject` that is only populated when instantiating `ContractActions`.

This is an asynchronous method, make sure to use `await`.&#x20;

{% hint style="info" %}
If undefined is passed to either of the `gasLimit`, `maxPriorityFeePerGas` or `maxFeePerGas` fields they will be calculated internally as the transaction is simulated. If you'd like more control over these fields please pass in correctly calculated values.&#x20;

If you're transaction requires **approval** or **funding** of the PKP Wallet before it's broadcast, these values must be passed in manually. This is necessary due to the transaction simulation process, to obtain the expected gas price, which occurs prior to the minting of the PKP.&#x20;
{% endhint %}

{% hint style="info" %}
Before Lit.Action.executeJS is called with each run of the Circuit the nonce value for ContractActions will be recalculated by invoking `getTransactionCount()` on the provider.&#x20;
{% endhint %}

{% hint style="info" %}
If you are sending any `value` along with the Contract Action, make sure that it is specified correctly in **wei**.&#x20;
{% endhint %}

<pre class="language-typescript" data-overflow="wrap" data-full-width="true"><code class="lang-typescript">import { FetchAction, ContractAction } from "lit-listener-sdk"

const fetchAction: FetchAction = {
  type: "fetch", // type
  priority: 1, // execution priority 
  baseUrl: "https://api.example.com", // baseUrl
  endpoint: "/data", // endPoint
  responsePath: "data.value", // responsePath
  apiKey: "your_api_key", // apiKey
  toSign: [72, 101, 108, 108, 111, 32, 87, 111, 114, 108, 100], // toSign
  signCondition: [
    {
      type: "&#x26;&#x26;",
      operator: "==",
      value: "expected_value",
    },
  ], // signCondition
};

const contractAction: ContractAction = {
  type: "contract", // type
  priority: 2, // execution priority
  contractAddress: "0x6968105460f67c3bf751be7c15f92f5286fd0ce5", // contract address
  abi: [
     {
      constant: true,
      inputs: [{ name: "numberValue", type: "uint256" }],
      name: "your_function_name",
      outputs: [{ name: "", type: "uint256" }],
      payable: false,
      stateMutability: "external",
      type: "function",
      },
  ], // abi
  functionName: "your_function_name", // function name
  chainId: "polygon", // chainId
  providerURL: "https://polygon-provider-url.com" // provider URL
  nonce: 1, // nonce
  gasLimit: 100000, // gas Limit
  value: 0, // value
  maxPriorityFeePerGas: 1000, // max priority gas fee
  maxFeePerGas: 10000, // max fee per gas
  args: [20], // function arguments
};
<strong>
</strong>const {unsignedTransactionDataObject, litActionCode} = await newCircuit.setActions(
    [
        fetchAction,
        contractAction
    ]
)
</code></pre>

To easily generate the unsigned transaction data that is passed to executeJS (signed by your PKP) for Contract Actions, you can invoke the asynchronous LitListenerSDK helper function `generateUnsignedTransactionData`. &#x20;

{% code overflow="wrap" fullWidth="true" %}

```typescript
import { generateUnsignedTransactionData, CustomAction, CHAIN_NAME, LitUnsignedTransaction } from "lit-listener-sdk";

const unsignedTransactionArgs = await newCircuit.generateUnsignedTransactionData({
    chainId: CHAIN_NAME.polygon,
    abi: [
      {
        constant: false,
        inputs: [
          {
            name: "_value",
            type: "uint256",
          },
        ],
        name: "setValue",
        outputs: [],
        payable: true,
        stateMutability: "nonpayable",
        type: "function",
      },
    ],
    contractAddress: "0x6968105460f67c3bf751be7c15f92f5286fd0ce5",
    nonce: 2, // optional param
    gasLimit: "21000", // optional param
    maxFeePerGas: "10000000000", // optional param
    maxPriorityFeePerGas: "1", // optional param
    from: "{{publicKey}}",
    functionName: "setValue",
    args: [5],
    value: "1000000000000000000", // optional param
}, "https://the-provider-url.com")

const customFunction = `async () => {
   try {
   
    const hashTransaction = (tx) => {
        return ethers.utils.arrayify(
          ethers.utils.keccak256(
            ethers.utils.arrayify(ethers.utils.serializeTransaction(tx)),
            ),
          );
        };
        
    await LitActions.signEcdsa({
        toSign: hashTransaction(unsignedTransactionArgs),
        publicKey: publicKey,
        sigName: sigName,
        });
        
    Lit.Actions.SetResponse({response: "Transaction Signed Successfully."});
        
    } catch (err) {
    console.log('Error thrown on signing transaction.', err)
  }
}`;

const customAction: CustomAction = {
  type: "custom",
  priority: 0,
  code: customFunction
  args: {
   unsignedTransactionArgs
  }
}

const { litActionCode } = newCircuit.setActions([customAction]);
```

{% endcode %}

**Contract Action Parameters:**

{% hint style="info" %}
If the from address passed to a `ContractAction` is left blank it will be populated with the minted PKP Address during execution of the Lit Action.
{% endhint %}

<pre class="language-typescript" data-overflow="wrap" data-full-width="true"><code class="lang-typescript">import { CHAIN_NAME,  } from "lit-listener-sdk";
import { InterfaceAbi } from "ethers";

/* The type of the action, always "contract" for this interface.*/
<strong>type: "contract";
</strong>
/*  A numerical value representing the priority of the action. The lower the 
    value, the higher the priority.*/
priority: number;

/* The Ethereum address of the smart contract with which to interact.*/
contractAddress: `0x${string}`;

/* The ABI (Application Binary Interface) of the smart contract, which 
    describes its functions and events.*/
abi: InterfaceAbi;

/* The name of the smart contract function to call.*/
functionName: string;

/* The compatible blockchain network chainId. Import 
    CHAIN_NAME from lit-listener-sdk*/
chainId: CHAIN_NAME;

/* The provider URL for the indicated network.*/
providerURL: string;

/* The transaction nonce.*/
nonce?: number;

/* The transaction gas limit.*/
gasLimit?: BigNumberish;

/* Any value to be passed with the transaction.*/
value?: BigNumberish;

/* The address from which the transaction as called. This will usually be the PKP address.*/
from?: `0x${string}` | {{publicKey}};

/* The max priority fee per gas for the transaction.*/
maxPriorityFeePerGas?: BigNumberish;

/* The max fee per gas for the transaction.*/
maxFeePerGas?: BigNumberish;

/* An array of arguments to pass to the function call.*/
args?: any[];
</code></pre>

**Fetch Action Parameters:**

{% code overflow="wrap" fullWidth="true" %}

```typescript
/* The type of the action, always "fetch" for this interface.*/
type: "fetch";

/* A numerical value representing the priority of the action. The lower the value, the higher the priority. */
priority: number;

/* The base URL of the API endpoint. */
baseUrl: string;

/* The specific endpoint to fetch. */
endpoint: string;

/* The path to access the expected value in the response body.*/
responsePath: string;

/* Optional API key for authorization.*/
apiKey?: string;

/* The data to sign. If left blank the response returned from the API will be signed. */
toSign?: Uint8Array;

/* The condition under which to sign the data.*/
signCondition?: {
    type: "&&" | "||";
    operator: "<" | ">" | "==" | "===" | "!==" | "!=" | ">=" | "<=";
    value:
      | number
      | string
      | bigint
      | string[]
      | number[]
      | bigint[]
      | undefined
      | (string | number | bigint)[];
 }[];
```

{% endcode %}

**Custom Action Parameters:**

{% hint style="info" %}
When creating a `CustomAction` and invoking a `Lit Action` to sign unsigned transaction data you will need to pass in the unsigned transaction data as an argument, however you do not need need to include the `PKP PublicKey`, `PKP Address` or `Auth Signature` as arguments as these parameters are passed to `Circuit.start()`
{% endhint %}

{% code overflow="wrap" fullWidth="true" %}

```typescript
/* The type of the action, always "custom" for this interface.*/
type: "custom";

/* A numerical value representing the priority of the action. The 
    lower the value, the higher the priority.*/
priority: number;

/* A function string representing the custom action to be performed. This 
    function is defined by the user.*/
code: string;

/* The type of the action, always "custom" for this interface.*/
args?: Object;

```

{% endcode %}


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.irrevocable.dev/sdk-reference/set-actions.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
