# Show attached messages

In the basic examples we still show how to use SignumJS depending the way you are using SignumJS, i.e. imported via NodeJS package manager or as minified bundle. In case you haven't read about the module system, take a quick look there:

{% content-ref url="/pages/5LpyrKz8NZepdbWjzEW9" %}
[Modules](/signumjs/getting-started/modules.md)
{% endcontent-ref %}

{% hint style="info" %}
A fully working example is available [here](https://github.com/signum-network/signumjs/blob/main/examples/nodejs/basic/listMessages.js)
{% endhint %}

Following functions from SignumJS are used in this example&#x20;

* [composeApi](https://signum-network.github.io/signumjs/modules/core_api.html#composeapi) function to create the api instance
* [api.account.getAccountTransactions](https://signum-network.github.io/signumjs/interfaces/core_api.accountapi.html#getaccounttransactions) function to fetch the transactions from the blockchain
* [isAttachmentVersion](https://signum-network.github.io/signumjs/modules/core.html#isattachmentversion) function to check, whether a message is encrypted or not.
* [TransactionType](https://signum-network.github.io/signumjs/enums/core.transactiontype.html) enums to filter for the specific message types
* [Address](https://signum-network.github.io/signumjs/classes/core.address.html) Value Object to parse and convert the given address&#x20;
* [ChainTime](https://signum-network.github.io/signumjs/classes/util.chaintime.html) Value Object to convert between blockchain timestamp and real date

{% tabs %}
{% tab title="Javascript" %}

```javascript
const {
    composeApi,
    isAttachmentVersion,
    TransactionType,
    TransactionArbitrarySubtype, 
    Address
} = require('@signumjs/core');
const {ChainTime} = require('@signumjs/util')

// Create the Api instance to connect to a blockchain node
const api = composeApi({
    nodeHost: "https://europe.signum.network"
});

// here we check for a certain attachment type, and get the text message if not encrypted
const getMessageText = transaction =>
    isAttachmentVersion(transaction, 'EncryptedMessage')
        ? '<encrypted>'
        : transaction.attachment.message;

async function listMessages(account) {
    try {
        const accountId = Address.create(account).getNumericId()

        // here we can explicitly filter by Transaction Types
        const {transactions} = await api.account.getAccountTransactions(
            {
                accountId,
                lastIndex: 20, // getting only the most recent 20
                type: TransactionType.Arbitrary,
                subtype: TransactionArbitrarySubtype.Message
            }
        );

        // now we iterate through the transactions and print in a formatted way
        transactions.forEach(t => {
            console.info(`On ${ChainTime.fromChainTimestamp(t.blockTimestamp).getDate()}`)
            console.info(`From ${t.senderRS}`)
            console.info(`To ${t.recipientRS}`)
            console.info('Message:\n', getMessageText(t), '\n---')
        })

    } catch (e) {
        handleError(e)
    }
}
```

{% endtab %}

{% tab title="Typescript" %}

```typescript
import {
    composeApi,
    isAttachmentVersion,
    TransactionType,
    TransactionArbitrarySubtype, 
    Address,
    Transaction
} from '@signumjs/core';
import {ChainTime} from '@signumjs/util'

// Create the Api instance to connect to a blockchain node
const api = composeApi({
    nodeHost: "https://europe.signum.network"
});

// here we check for a certain attachment type, and get the text message if not encrypted
const getMessageText = (transaction: Transaction): string =>
    isAttachmentVersion(transaction, 'EncryptedMessage')
        ? '<encrypted>'
        : transaction.attachment.message;

async function listMessages(account: string): Promise<void> {
    try {
        const accountId = Address.create(account).getNumericId()

        // here we can explicitly filter by Transaction Types
        const {transactions} = await api.account.getAccountTransactions(
            {
                accountId,
                lastIndex: 20, // getting only the most recent 20
                type: TransactionType.Arbitrary,
                subtype: TransactionArbitrarySubtype.Message
            }
        );

        // now we iterate through the transactions and print in a formatted way
        transactions.forEach(t => {
            console.info(`On ${ChainTime.fromChainTimestamp(t.blockTimestamp).getDate()}`)
            console.info(`From ${t.senderRS}`)
            console.info(`To ${t.recipientRS}`)
            console.info('Message:\n', getMessageText(t), '\n---')
        })

    } catch (e:any) {
        console.log(e)
    }
}
```

{% endtab %}

{% tab title="<script/>" %}

```javascript
// you need to have imported in your index.html:
/*
<script src='https://cdn.jsdelivr.net/npm/@signumjs/core/dist/signumjs.min.js'></script>
<script src='https://cdn.jsdelivr.net/npm/@signumjs/util/dist/signumjs.util.min.js'></script>
*/

// Create the Api instance to connect to a blockchain node
const api = sig$.composeApi({
    nodeHost: "https://europe.signum.network"
});

// here we check for a certain attachment type, and get the text message if not encrypted
const getMessageText = transaction =>
    sig$.isAttachmentVersion(transaction, 'EncryptedMessage')
        ? '<encrypted>'
        : transaction.attachment.message;

async function listMessages(account) {
    try {
        const accountId = sig$.Address.create(account).getNumericId()

        // here we can explicitly filter by Transaction Types
        const {transactions} = await api.account.getAccountTransactions(
            {
                accountId,
                lastIndex: 20, // getting only the most recent 20
                type: sig$.TransactionType.Arbitrary,
                subtype: sig$.TransactionArbitrarySubtype.Message
            }
        );

        // now we iterate through the transactions and print in a formatted way
        transactions.forEach(t => {
            console.info(`On ${sig$util.ChainTime.fromChainTimestamp(t.blockTimestamp).getDate()}`)
            console.info(`From ${t.senderRS}`)
            console.info(`To ${t.recipientRS}`)
            console.info('Message:\n', getMessageText(t), '\n---')
        })

    } catch (e) {
        console.error(e)
    }
}
```

{% endtab %}
{% endtabs %}


---

# 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://signum-network.gitbook.io/signumjs/recipes/basics/show-attached-messages.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.
