How to upload files to ardrive manually and with ardrive CLI?
Tags: javascript, tutorial, arweave, blockchain
Published: 2022-08-10 23:04:00

In the following post I will explaining what is Arweave, how to create a wallet, and also how to upload files manually and with the CLI.

For this example I will be uploading some free images from [unsplash](https://unsplash.com/).

## What is Arweave?.

According to the [Arweave website](https://arweave.org/), Arweave is a protocol that allows you to store data permanently, sustainably, with a single upfront fee.

*You can think of it as an alternative to IPFS*

With [Ardrive](https://app.ardrive.io/#/sign-in), we will able to upload and share our files, there is also a [fee calculator](https://ardrive.io/pricing/) in case you want to know how much you will pay for the amount of data that you want store.

## Prerequisites

- [Node.js](https://nodejs.org/en/download/) installed
- [Arweave Wallet](https://faucet.arweave.net/)
- [Ardrive CLI](https://github.com/ardriveapp/ardrive-cli) installed


## Creating Our Project

1. Open your terminal and type the following commands
2. mkdir ardrive-tutorial
3. cd ardrive-tutorial
4. npm init --y
5. Open the project with your preferred code editor

## Dependencies

- [ardrive-core-js](https://www.npmjs.com/package/ipfs-core)
- [dotenv](https://www.npmjs.com/package/dotenv)
- [prompt-sync](https://www.npmjs.com/package/prompt-sync)

To install dependencies go to your project folder open a terminal and type the following.

```console
npm i ardrive-core-js dotenv prompt-sync
```

We will be using *import* so open `package.json` and add the following line **"type" : "module"**.

```json
"type" : "module",
"scripts": {
  "start": "node ./src index.js"
},
```

## Project File Structure

```code
arDrive-tutorial/
├── node_modules/
├── tutorial-images/
├── src/
│   └── index.js
├── .env
└── package.json
```


## Table of Contents

1. [Log in to ArDrive](#ardrive-login)
2. [Uploading files to ArDrive](#uploading-to-ardrive)
3. [Uploading files with ArDrive CLI](#uploading-with-ardrive-cli)
4. [Script to create a .json with files info](#custom-script)
5. [Conclusion](#conclusion)

---


## 1. Log in to ArDrive <a name="ardrive-login"></a>


This is not difficult to do, assuming that you created your wallet, you just go to [Ardrive login page](https://app.ardrive.io/#/sign-in), and log in with your wallet.

![login screen](https://res.cloudinary.com/codenjobs/image/upload/v1660137690/user/file/gcs51ym4tramrdbum3u8.png)

![user_pass](https://res.cloudinary.com/codenjobs/image/upload/v1660137711/user/file/qwrebpzdt2yic8eee5tw.png)

*The user and password are for private folders*.


## 2. Uploading Files to ArDrive <a name="uploading-to-ardrive"></a>

*Remember that all the files will be permanently stored, that means that the files cannot be deleted*.

The first thing that we will do is create a new drive by clicking on the **New** button.

![step1](https://res.cloudinary.com/codenjobs/image/upload/v1660137725/user/file/hvjen5eutrk9vpizzqip.png)


Then set a name and choose between public or private, I am going to choose *public*.

![step2](https://res.cloudinary.com/codenjobs/image/upload/v1660137732/user/file/i86s3ry1cgthvwhulgp5.png)

Then we are going to click the **New** button again, and this time select *"upload folder"* because we are going to upload a folder with files in it, like I said before in this example I will be using some free images from [unsplash](https://unsplash.com/). you can use whatever you want, just make sure that you have the permission to upload the files. 

You will also be able to see the price to upload those files, so you can decide if you want to upload them.

![step3](https://res.cloudinary.com/codenjobs/image/upload/v1660137738/user/file/galneggswpjjprci4btu.png)

![upload_cost](https://res.cloudinary.com/codenjobs/image/upload/v1660137744/user/file/e07negol4clovkdouit2.png)


Now you will be able to see a new folder in your drive, and if we open it we will be able to see the files in it, also we can download them, get details of each file, a preview link, etc.

![file list](https://res.cloudinary.com/codenjobs/image/upload/v1660148611/user/file/zjtzl9uceqzbb7fj48jd.png)



## 3. Uploading files with ArDrive CLI <a name="uploading-with-ardrive-cli"></a>

*To get more info about the commands that can be used type `ardrive -h` or in case you want more usage information about a command `ardrive create-drive -h`*.

Now we are going to repeat the process but using ardrive cli instead, so the first thing that we are going to do is open our terminal and check if the ardrive CLI is installed with this command:

```
ardrive --version
```

You should get your ardrive CLI version.

```console
1.19.0
```

Then we are going to create a new drive, we must specify our wallet location and a name for the new drive, you can also specify if you want it to be a private drive with **-p**

```
ardrive create-drive -w <YOUR\WALLET\LOCATION\FOLDER\wallet-file.json> -n cli-tut
```

You should get an object with information about the drive and the folder like the following one:

```console
{
  "created": [
    {
      "type": "drive",
      "metadataTxId": "0fzTAOPqIK4Imk2xGf3e9CDCXxO_k-xFFlOkAA-IXRg",
      "entityId": "5e219c5e-ed6a-497d-b225-b5d621eed097",
      "bundledIn": "GL725mzIbYgisddpaimoxs6lAdN9CjASmhhxqdP3agk",
      "entityName": "cli-tut"
    },
    {
      "type": "folder",
      "metadataTxId": "LGeONqTaoiE1m6_OXK2RcmsBZbkN0yxl-AKNUEn4ahs",
      "entityId": "1739f7e2-baa2-491a-a2ab-f406d778041a",
      "bundledIn": "GL725mzIbYgisddpaimoxs6lAdN9CjASmhhxqdP3agk",
      "entityName": "cli-tut"
    },
    {
      "type": "bundle",
      "bundleTxId": "GL725mzIbYgisddpaimoxs6lAdN9CjASmhhxqdP3agk"
    }
  ],
  "tips": [],
  "fees": {
    "GL725mzIbYgisddpaimoxs6lAdN9CjASmhhxqdP3agk": "52221667"
  }
}
```

Then we are going to upload some files to it, if we want upload them to the root folder we will need to add  the `entityId` of the previous object with `"type": "folder"`, anyways if you open your ardrive and look for the drive that you created you can get the root folder id like this.

![drive id and folder id](https://res.cloudinary.com/codenjobs/image/upload/v1660148651/user/file/i5bbruxoacjewwhuhvnd.png)

<!-- the file or folder location -->

We also need the file location, or folder location that we want to upload


```
ardrive upload-file -w <YOUR\WALLET\LOCATION\FOLDER\wallet-file.json> --local-path <FILE\OR\FOLDER\LOCATION\THAT\WANT\TO\UPLOAD> -F <folder-id>
```

You will get a message like this: 

```console
{
  "created": [
    {
      "type": "folder",
      "entityId": "4de053e3-cf7f-4da6-88bc-e238e7478226",
      "metadataTxId": "rhML7VdZDfm2R1sASWwiCVt-_eeGb38VOFMUOszgvlM",
      "bundledIn": "CjI3RTkum17KI5GHEiI6dC_gjq1dznylrA4pR5hk0E4",
      "entityName": "ardrive-cli-files",
    },
    {
      "type": "file",
      "entityName": "1.jpg",
      "entityId": "6cb92418-bf77-4edd-a271-a4981abb92bc",
      "dataTxId": "8y5PVi1V2WAF4etKv0lgbfx2tO2P_ekDu7PBFjhu4us",
      "metadataTxId": "LD2QI5erLPuvM39ptN0-G9vpLEGh4VXIdglhzS_oHEI",
      "bundledIn": "CjI3RTkum17KI5GHEiI6dC_gjq1dznylrA4pR5hk0E4",
    },
    {
      "type": "file",
      "entityName": "2.jpg",
      "entityId": "48c33090-a7e6-47d3-b974-924a09defbb4",
      "dataTxId": "oMEPmy2LIKL0RI2WSfMyT3XEo2aZ86zqDQrEcfteqVo",
      "metadataTxId": "m3cDLllbgTwg4rlKF_FivP5nSHRd7BZ9WIUY31NVlxE",
      "bundledIn": "CjI3RTkum17KI5GHEiI6dC_gjq1dznylrA4pR5hk0E4",
      "sourceUri": "file://C:\\Users\\Rob\\Downloads\\ardrive-cli-files\\2.txt"
    },
    {
      "type": "bundle",
      "bundleTxId": "CjI3RTkum17KI5GHEiI6dC_gjq1dznylrA4pR5hk0E4"
    }
  ],
  "tips": [
    {
      "recipient": "aVHpFhSorIljeZ9so8unOEnPkW3YqRbqG5cfM4aXxBI",
      "txId": "CjI3RTkum17KI5GHEiI6dC_gjq1dznylrA4pR5hk0E4",
      "winston": "10000000"
    }
  ],
  "fees": {
    "CjI3RTkum17KI5GHEiI6dC_gjq1dznylrA4pR5hk0E4": "52221667"
  }
}
```

So as you can see, a new folder was created, also two files with it.

Now we can download that folder (it will be downloaded in your current console location) with this command: 

```
ardrive download-folder -w <YOUR\WALLET\LOCATION\FOLDER\wallet-file.json> -f <folder-id>
```



## 4. Script to create a .json with files info <a name="custom-script"></a>

Now we are going to create a custom script to get files and folder information and finally create a .json file with it *that would be helpful for a real life NFT project*.

First create a `.env` file in the root of your project and create a `WALLET_PATH` variable and add your wallet path like this `C:\\YOUR\\WALLET\\PATH`.

Then go to `src` folder and open `index.js`, copy and paste the following code, don't worry I will explain it step by step.

*I am going to use a folder form our previous example, but you can also work for a folder arDrive structure like this*.

```code
driveName
├── imagesFolder/ //if we want imagesFolder info then we should provide this folder id
│   ├── folder1/
│   │   ├── 0.jpg
│   │   └── 1.jpg
│   ├── folder2/
│   │   ├── 2.jpg
│   │   └── 3.jpg
│   ├── folder3/
│   │   ├── 4.jpg
│   │   └── 5.jpg
│   ├── folder4/
│   │   ├── 6.jpg
│   │   └── 7.jpg
│   └── folder5/
│       ├── 8.jpg
│       └── 9.jpg
├── metadatasFolder/
└── anotherFolder/
```

1. We are going to `import {readJWKFile, arDriveFactory} from 'ardrive-core-js'`. we'll be able to read our wallet with `readJWKFile` and use arDrive operations with `arDriveFactory`.

2. We are going to create a .json file at the end of our script so we need to use `fs`.

3. The script will prompt the user for the folder ID, with the folder ID we can get all folders inside that folder and we can also get the drive ID that will be needed to build the link to the folder.

4. We need sort the folders in case there are more than one and have a project name e.g. (PROJECT_NAME_1, PROJECT_NAME_2, PROJECT_NAME_3, etc) because probably we won't get them sorted by default.

5. We will create a `const foldersId = []` that will store every folder name and folder id.

6. Now we will use a *for loop* to loop through foldersId and will get the files of each folder with .
```js
const getFiles = await arDrive.listPublicFolder({
    folderId: folderId
  })
```

7. We will sort those files because we could obtain them unsorted.

8. Then we are going to create a `const filesInformation = []` that will store the information of each one of the files per folder.  

9. After that we are going to use another *for loop* trough them inside our current loop, So with this approach we will get all the files info from the current folder.

10. Now we will store the folderName, folderLink, and also the filesInformation (fileName, fileId, and fileLink from the previous loop) and will be stored in a Files array.

11. Finally we will create a json file and we will write the stored data in Files.


```js
import {readJWKFile, arDriveFactory} from 'ardrive-core-js'
import fs from 'fs'
import dotenv from 'dotenv'
dotenv.config({path: '../.env'})
import ps from "prompt-sync";
const prompt = ps()

//read wallet from file
const myWallet = readJWKFile(process.env.WALLET_PATH)

const arDrive = arDriveFactory({ wallet: myWallet })

const folderID = prompt("insert the folder id ")

const getFolders = await arDrive.listPublicFolder({
  folderId: folderID 
})

const driveId = getFolders[0].driveId

const LINK_TO_FOLDERS = `https://app.ardrive.io/#/drives/${driveId}/folders/`

getFolders.sort((a, b) => {
  return a.name.localeCompare(b.name)
})

const foldersId = []

getFolders.forEach(folder => {
  foldersId.push({
    folderName: folder.name,
    folderId: folder.folderId.entityId
  })
})


const Files = []

for (let i = 0; i < foldersId.length; i++) {
  const folderId = foldersId[i].folderId
  const folderName = foldersId[i].folderName
  const getFiles = await arDrive.listPublicFolder({
    folderId: folderId
  })

  //create an array for eachFoldername
  const filesInformation = []

  // Format here
  getFiles.sort((a, b) => {
    return a.name.localeCompare(b.name)
  })

  for (let j = 0; j < getFiles.length; j++) {
    const file = getFiles[j]
    filesInformation.push({
      fileName: file.name,
      fileId: file.fileId.entityId,
      fileLink:'https://arweave.net/'+file.dataTxId.transactionId
    })
    
  
  }

  Files.push({
    folderName,
    folderLink: LINK_TO_FOLDERS + folderId,
    filesInformation
  })

}

fs.writeFileSync(`filesInfo.json`, JSON.stringify(Files))
```

The final output will be similar to this:

```json
[
  {
    "folderName": "arweave-images",
    "folderLink": "https://app.ardrive.io/#/drives/5791d389-438c-4af5-820f-a2fe0fb782a8/folders/3d124a11-ebb5-4c2e-9d2c-02d6f1700b4b",
    "filesInformation": [
      {
        "fileName": "1.jpg",
        "fileId": "b2ca111f-54c5-4515-b700-e055c3a4e7c1",
        "fileLink": "https://arweave.net/SrERAlYcB1v8D6ABRkP_QbHfRR6RdKTO3akSghPz3dM"
      },
      {
        "fileName": "2.jpg",
        "fileId": "2e791441-9404-4211-b618-2e580e110a15",
        "fileLink": "https://arweave.net/fsnAIp1VFBMqBhNYsejaI5BqqOuUNat0gnUE2CHevqY"
      },
      {
        "fileName": "3.jpg",
        "fileId": "1c40d120-fe1d-4394-93e3-f9df3bf0f176",
        "fileLink": "https://arweave.net/mSgGn1D_WPudzm0uROiJxegbZ760rhSNI8p5DGiy7hI"
      }
    ]
  }
]
```


## 5. Conclusion <a name="conclusion"></a>

We have learned how to upload and share files with arDrive manually and with the CLI, also how to create a custom script to interact with the files uploaded.

I really hope you have been able to follow the post without any trouble, otherwise I apologize, please leave me your doubts or comments.

[You can contact me by telegram if you need to hire a Full Stack developer.](https://t.me/rtagliajs)

You can also find me on Discord **Appu#9136**

Thank you for your time.