# Async content

Often the tree has a big structure and it is not good to load immediately the whole tree items. The library has only 2 ways to load a data from a server, but this is quite enough for any, even the most complex requirements. See below for more details on each of them.

### Data initializing

Note that there is no data initialization parameter or something like that. Only `data` property. Let's examine how is **elementary** to load a data from the server.

```jsx
import React from 'react'
import EyzyTree from 'eyzy-tree'
import AwesomeLoadingIndicator from 'awesome-loading-indicator'
import 'eyzy-tree/style.css'

export default LazyTree extends React.Component {
    // https://babeljs.io/docs/en/babel-plugin-proposal-class-properties
    // instead you can use constructor :)
    state = {
        treeData: [],
        isDataLoaded: false
    }

    componentDidMount() {
        fetch('/awesome_API/v1/?tree')
            .then(response => response.json())
            .then(data => {
                this.setState({
                    isDataLoaded: true,
                    treeData: data
                })
            })
    }
    
    render() {
        if (!this.state.isDataLoaded) {
            return <AwesomeLoadingIndicator />
        }
        
        return (
            <EyzyTree data={this.state.treeData} />
        )
    }
}
```

### Node's property

Each node of a tree might has a `isBatch` property. The tree perceives this property as: node has children and it should be received from the server (see [fetchData ](/tree/component-props.md#options)property). It will show an arrow and an user is able to expand the node. Class `loading` will be added to the node. And upon completion, the class will be removed and new nodes will be added as children to this node.

Example of component data:

```jsx
const treeData = [
    { text: 'Item 1' },
    { text: 'Item 2' },
    { text: 'Item 3' },
    { text: 'Item 4', isBatch: true } // this node will has a "expandable" arrow
]

// This method must return a Promise
function handleFetchData(node) {
    // Note that it is important to return a valid JS object (not `fetch` response)
    return fetch(`/api?nodeText=${node.text}`)
        .then(response => response.json())

    // or you can use a library for the request
    return axios.get('/user', {
        params: {
            nodeText: node.text
        }
    })
}

// component example
<EyzyTree 
    data={treeData}
    fetchData={handleFetchData}
/>
```

### Using API

There are several methods that allow you to add new nodes as children asynchronously.

* append (see [API](/tree/api/basic.md#append))
* prepend (see [API](/tree/api/basic.md#prepend))

I see no reason to re-describe how the methods work (you can look at the link above). Better I will show a simple and real example.

```jsx
import React from 'react'
import EyzyTree from 'eyzy-tree'
import axios from 'axios'
import 'eyzy-tree/style.css'

export default LazyTree extends React.Component {
    treeApi = null

    constructor(props) {
        super(props)

        this.state = {
            data: [
                'Item 1',
                'Item 2',
                'Item 3',
                'Item 4',
                'Item 5',
            ]
        }
    }

    loadNode = (node) => {
        return axios.get('/awesome_API/v1/tree', {
            params: {
                nodeText: node.text
            }
        })
    }

    handleTreeReady = (api) => {
        this.treeApi = api
    }

    handleClick = () => {
        this.treeApi.append({ selected: true }, this.loadNode)
    }

    render() {
        return (
            <div className="tree">
                <EyzyTree 
                    data={this.state.treeData}
                    onReady={this.handleTreeReady}
                />
            </div>
            <div className="controls">
                <button onClick={this.handleClick}>Add to Selected</button>
            </div>        
        )
    }
}
```

### Insertion options

There are few options:

* `expand` whether to expand node
* `loading` whether to show loading indicator
* `index` insertion index

```javascript
const options = {
    expand: true,
    loading: false
}

this.api.append(/item/, (node) => {
    return axios.get('/awesome_API/v1/tree', {
        params: {
            nodeText: node.text
        }
    })
}, options)
```


---

# 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://eyzy.gitbook.io/tree/guides/async.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.
