Clean Your Storage Using Appwrite's Swift Cloud Functions
Tags: appwrite, swift, cloud, serverless
Published: 2021-10-23 07:44:01

![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/u46i2voh9hi6qch63tmn.png) 

For all those Swift developers out there, we have a good news! We have just announced our Swift SDK to work with the server-side APIs of Appwrite. You can learn more about our Swift SDK in our [Swift SDK announcement post](swift-SDK-announcement-post).

In this tutorial however, we are going to write, deploy and run a storage cleaner cloud function with Swift. Let's get started.

## 🤔 What are Appwrite Cloud functions?
[Appwrite Functions](https://appwrite.io/docs/functions) are a way for you to extend and customize your [Appwrite BaaS](https://appwrite.io) functionality by executing your custom code. Appwrite can execute your custom code in response to any Appwrite system event like account creation, user login, or document update. You can also schedule your functions to run according to a CRON schedule or start them manually by triggering your function from an HTTP endpoint using the Appwrite client or server APIs.

## 🗒️ Prerequisites
In order to continue with this tutorial, you need to have an latest version of Appwrite console that you can access and have a project you can use to test this function. If you have not already installed Appwrite, please do so. Installing Appwrite is really simple. Based on your operating system, run one of the following commands. Installation should be done in less than 2 minutes.

### Unix
```bash
docker run -it --rm \
    --volume /var/run/docker.sock:/var/run/docker.sock \
    --volume "$(pwd)"/appwrite:/usr/src/code/appwrite:rw \
    --entrypoint="install" \
    appwrite/appwrite:0.11.0
```

### Windows CMD
```powershell
docker run -it --rm ^
    --volume //var/run/docker.sock:/var/run/docker.sock ^
    --volume "%cd%"/appwrite:/usr/src/code/appwrite:rw ^
    --entrypoint="install" ^
    appwrite/appwrite:0.11.0
```

### Windows PowerShell
```powershell
docker run -it --rm ,
    --volume /var/run/docker.sock:/var/run/docker.sock ,
    --volume ${pwd}/appwrite:/usr/src/code/appwrite:rw ,
    --entrypoint="install" ,
    appwrite/appwrite:0.11.0
```

You can also find detailed installation instructions on the Appwrite official [installation docs](https://appwrite.io/docs/installation).

## 🔓️ Activate Swift Functions Environment
In order for the Swift environment to be available in Appwrite Cloud Functions, you need to enable it. It can easily be done using the environment variables. In the Appwrite installation folder  find `.env` file. In the file find the environment variable `_APP_FUNCTIONS_RUNTIMES` and there in the comma separated list add `swift-5.5` to make Swift environment available in the Appwrite Functions. After that, you can load updated configuration using `docker-compose up -d`.

## 🔑 Initialize Function Project
First, create a project folder where you will create all the necessary files for your function. We will call this folder `storage-cleaner`. Inside run the following command to create a new Swift project

```bash
docker run --rm -it -v $(pwd):/app -w /app swift:5.5 swift package init StorageCleaner
```

This will initialize a new Swift package project. It should create bunch of files, important ones to notice are:

```
.
├── Sources/StorageCleaner/main.swift
└── Package.swift
```

## ➕ Add Appwrite Swift SDK dependency
Open `storage-cleaner` folder in your favorite text editor. Add the following code to `Package.swift` file.

```swift
import PackageDescription

let package = Package(
    name: "StorageCleaner",
    dependencies: [
        .package(url: "https://github.com/appwrite/sdk-for-swift", "0.1.0") //TODO update version
    ],
    targets: [
        .executableTarget(
            name: "StorageCleaner",
            dependencies: [
                .product(name: "Appwrite", package: "sdk-for-swift"),
            ]),
        .testTarget(
            name: "StorageCleanerTests",
            dependencies: ["StorageCleaner"]),
    ]
)
```
Here we are adding Appwrite sdk for swift under dependencies as well as under executable target dependencies.

## ✍️  Write your Function
Open `Sources/StorageCleaner/main.swift` and update it with the following code:

```swift
import Appwrite
import Foundation

func cleanStorage() throws -> Void {
    let group = DispatchGroup()
    group.enter()
    let daysToExpire = ProcessInfo.processInfo.environment["DAYS_TO_EXPIRE"] 
    if(daysToExpire == nil) {
        throw NSError(domain: "DAYS_TO_EXPIRE environment is required", code: 0)
    }
    let endpoint = ProcessInfo.processInfo.environment["APPWRITE_ENDPOINT"] ?? ""
    let project = ProcessInfo.processInfo.environment["APPWRITE_FUNCTION_PROJECT_ID"] ?? ""
    
    let key = ProcessInfo.processInfo.environment["APPWRITE_API_KEY"] ?? ""

    let client = Client()
        .setEndpoint(endpoint)
        .setProject(project)
        .setKey(key)

    let storage = Storage(client)

    var deletedFiles = 0
    storage.listFiles(limit: 100, orderType: "DESC") { result in
        switch result {
            case .failure(let error):
                print(error.message)
            case .success(let fileList):
                let timestamp = Calendar.current.date(byAdding: .second, value: -Int(daysToExpire!)!, to: Date())!.timeIntervalSince1970
                print("Timestamp: \(timestamp)")
                for file in fileList.files {
                    let dateCreated = Double(file.dateCreated)
                    print("dateCreated \(dateCreated)")
                    if dateCreated < timestamp {
                        group.enter()
                        storage.deleteFile(fileId: file.id) { result in
                            switch result {
                                case .failure(let error):
                                    print(error)
                                case .success:
                                    deletedFiles += 1
                            }
                            group.leave()
                        }
                    }
                }
        }
        group.leave()
    }
    group.wait()
    print("Total files deleted: \(deletedFiles)")
}

try!
cleanStorage()
```
The environment variables that we are accessing here are either already available or are later set on the Appwrite Function's settings.

## ⚙️ Build
In order to deploy this to Appwrite Functions, we need to build the project. Our runtime is based on the slim version of official Swift docker image so we will use the official Swift docker image to build our project.

Using the terminal in the `storage-cleaner` directory, run the following command

```bash
$ docker run --rm -it -v $(pwd):/app -w /app swift:5.5 swift build
```
This should build the project. Ensure that your folder structure looks like this:
```
.
├── .build/x86_64-unknown-linux-gnu/debug/StorageCleaner
├── Sources/StorageCleaner/main.swift
└── Package.swift
```

There might be other files and folders as well.

## ☁️ Create a Function in Your Appwrite Console
Login to your Appwrite console and open the project of your choosing. There, from the sidebar, tap on the `Functions` menu. In the functions dashboard, tap the `Add Function` button.

![Add function](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/eo6ew64agz0j7pfvrlcd.png)

A dialog will be presented. Give your function a name of your choosing. We will call it `storage cleaner`. Next to the environment, we are using Swift, so we will choose Swift 5.5. Then tap create.

## 🧑‍💻 Deploy Tag
Once you tap create in the above step, you are taken to the newly created functions overview page.

You will find the ' Deploy Tag ' button at the bottom of the function's overview page. If you tap that button, you will get instructions for deploying. Switch to the `Manual` tab.

![Deploy](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/b0tuvysc8gnsexdxwu54.png) 

You will need to create a tarfile of your code first. In the command line within your code folder and in bash go ahead and run this:
```bash
$ tar -zcvf code.tar.gz --strip-components 1 -C .build/x86_64-unknown-linux-gnu/ debug/StorageCleaner
```

Once the tarfile is ready, in the Manual tab in the deploy tag dialog, attach the code.tar.gz and in command type `./StorageCleaner`.

## ✅ Activate tag
Once you deploy the tag, it will be listed under tags on the `Overview` page. And there you will find the option to upgrade

## 💡 Adding Environment Variables and Schedules
On the function's page, switch to the `Settings` tab from the `Overview` tab. A function can be triggered based on an event or a schedule you choose. This particular function will be scheduled. We will schedule it to run every day.

Scroll below to find the Schedule text field. There, paste a CRON Syntax for scheduling. For every day use `0 0 * * *`. 

Below that, under the `Variables` section, tap the `Add Variable` button. and add the following variables

* **APPWRITE_ENDPOINT** - Your Appwrite Endpoint (instead of localhost, use the ip address of your machine)
* **APPWRITE_API_KEY** - Your Appwrite API key with `files.read` and `files.write` permissions
* **DAYS_TO_EXPIRE** - Days for files to expire

Finally, tap Update.

## ✨️ Verify it's working
To verify everything is working, in the Overview tab, tap the `Execute Now` button. Then visit the `Logs` tab to verify the output or errors are as expected.


## 📚️ Resources

Hope you enjoyed this article! We love contributions and encourage you to take a look at our [open issues](https://github.com/appwrite/appwrite/issues) and [ongoing RFCs](https://github.com/appwrite/rfc/pulls).

If you get stuck anywhere, feel free to reach out to us on our [friendly support channels](https://appwrite.io/discord) run by humans 👩‍💻.

Here are some handy links for more information:

- [Appwrite Contribution Guide](https://github.com/appwrite/appwrite/blob/master/CONTRIBUTING.md)
- [Appwrite Github](https://github.com/appwrite)
- [Appwrite Documentation](https://appwrite.io/docs)