> ## Documentation Index
> Fetch the complete documentation index at: https://docs.bijection.com/llms.txt
> Use this file to discover all available pages before exploring further.

# iOS Swift Quickstart

> Add Bijection to an iOS Swift project

Learn how to query data from Bijection in an application targeting iOS and MacOS
devices built with Swift and SwiftUI.

This quickstart assumes that you have a Mac with Xcode and the Bijection CLI
installed. Install the CLI with:

```sh theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
curl -fsSL https://bijection.com/install.sh | sh
```

See [Install Bijection](/get-started/install) for PATH setup. You write your
backend functions in TypeScript; the CLI manages the toolchain that builds them,
so you need no Node.js install.

<Steps>
  <Step title="Create a new iOS app in Xcode">
    1. Click *Create New Project*
    2. Select iOS App and click *Next*
    3. Name your project something like “BijectionQuickstart”
    4. Ensure Language is set to Swift and User Interface is SwiftUI
    5. Click *Next*

    <p style={{textAlign: 'center'}} />
  </Step>

  <Step title="Configure dependencies">
    1. Click on the top-level BijectionQuickstart app container in the project
       navigator on the left
    2. Click on BijectionQuickstart under the PROJECT heading
    3. Click the Package Dependencies tab
    4. Click the + button (See Screenshot)
    5. Paste
       ```
       https://github.com/bijectionhq/bijection-swift
       ```
       into the search box and press enter
    6. When the `bijection-swift` package loads, click the *Add Package* button
    7. In the *Package Products* dialog, select BijectionQuickstart in the
       *Add to Target* dropdown
    8. Click the Add Package button

    <p style={{textAlign: 'center'}} />
  </Step>

  <br />

  <Step title="Add a Bijection backend">
    Open a terminal and `cd` to the directory for the Xcode project you
    created. Run `bijection init` to add a `bijection/` folder, where you write
    your backend functions, with a sample schema, query and mutation, and
    `bijection.json`.

    ```sh theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    bijection init
    ```
  </Step>

  <Step title="Start Bijection">
    Log this machine in to Bijection, once per machine, then start a Bijection
    dev deployment. The first run of `bijection dev` creates it and saves its
    URL in `.env.local` as `BIJECTION_URL`; the command then keeps running to
    push your functions on every change.

    ```sh theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    bijection login
    bijection dev
    ```

    <Note>
      Bijection's hosted service is not yet open for public sign-up, and the CLI
      has no default management service. Before running `bijection login`, set
      `BIJECTION_MANAGEMENT_URL` to the management service URL you were given, in
      your shell's startup file so that every later `bijection` command sees it too:

      ```sh theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
      export BIJECTION_MANAGEMENT_URL=https://<your management service>
      ```
    </Note>
  </Step>

  <Step title="Create sample data for your database">
    Create a new `sampleData.jsonl` file in your Swift project directory with
    these contents

    ```json theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    {"text": "Buy groceries", "isCompleted": true}
    {"text": "Go for a swim", "isCompleted": true}
    {"text": "Integrate Bijection", "isCompleted": false}
    ```
  </Step>

  <Step title="Add the sample data to a table called `tasks` in your database">
    Open another terminal tab by pressing ⌘+T which should open in your Swift
    project directory and run

    ```sh theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    bijection import --table tasks sampleData.jsonl
    ```
  </Step>

  <Step title="Declare the tasks table">
    `bijection init` created `bijection/schema.ts`, which declares the tables of
    your database, starting with a sample `messages` table. Add a `tasks` table
    beside it. The schema gives your functions TypeScript types, and Bijection
    enforces it at runtime.

    ```ts bijection/schema.ts theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    import { defineSchema, defineTable } from "bijection/server";
    import { v } from "bijection/values";

    export default defineSchema({
      messages: defineTable({
        author: v.string(),
        body: v.string(),
      }),
      tasks: defineTable({
        text: v.string(),
        isCompleted: v.boolean(),
      }),
    });
    ```
  </Step>

  <Step title="Expose a database query">
    Create a `tasks.ts` file in the `bijection/` directory within your Swift
    project with the following contents

    ```tsx theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    import { query } from "./_generated/server";

    export const get = query({
      args: {},
      handler: async (ctx) => {
        return await ctx.db.query("tasks").collect();
      },
    });
    ```
  </Step>

  <Step title="Create a Swift struct">
    Back in Xcode, create a `struct` at the bottom of the `ContentView` file to
    match the sample data

    ```swift theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    // We're using the name Todo instead of Task to avoid clashing with
    // Swift's builtin Task type.
    struct Todo: Decodable {
      let _id: String
      let text: String
      let isCompleted: Bool
    }
    ```
  </Step>

  <Step title="Connect the app to your backend">
    1. Get the deployment URL of your dev server
       with `cat .env.local | grep BIJECTION_URL`
    2. Create a `BijectionClient` instance near the top of the file, just above the
       `ContentView` struct

    ```swift {4} theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    import SwiftUI
    import BijectionMobile

    let bijection = BijectionClient(deploymentUrl: "YOUR_BIJECTION_URL")

    struct ContentView: View {
    ...
    ```
  </Step>

  <Step title="Create your UI">
    Replace the default `ContentView` with the following code that will
    refresh the list of todo items whenever the backend data changes.

    ```swift theme={"theme":{"light":"github-light-default","dark":"github-dark-default"}}
    struct ContentView: View {
      @State private var todos: [Todo] = []

      var body: some View {
        List {
          ForEach(todos, id: \._id) { todo in
            Text(todo.text)
          }
        }.task {
          for await todos: [Todo] in bijection.subscribe(to: "tasks:get")
            .replaceError(with: []).values
          {
            self.todos = todos
          }
        }.padding()
      }
    }
    ```
  </Step>

  <Step title="Run the app">
    1. Press ⌘+R or click *Product → Run*
    2. You can also try adding, updating or
       deleting documents in your `tasks` table at `console.bijection.com` - the app
       will update with the changes in real-time.

    <p style={{textAlign: 'center'}} />
  </Step>
</Steps>

See the complete [iOS Swift documentation](/client/swift/overview).
