---
title: Flutter beta
slug: v4-7/flutter/installation
icon: {"faIcon":"fa-solid fa-angle-left"}
docTags: 
createdAt: 2024-06-24T13:35:23.871Z
---

Welcome to the Flutter SDK Beta Installation Guide. This document provides step-by-step instructions for installing and configuring the Ditto SDK, enabling you to sync, query, and insert data seamlessly within your existing Flutter application.

If you're looking to get started quickly with an existing app we recommend following the [Flutter beta Quick Start](docId\:Ou7zm7LiPT8KG-3hQ5B41).

## Prerequisites

Before you begin, ensure you have the following installed:

- [ ] Installed code editor (preferably Visual Studio Code or Android Studio)
- [ ] Flutter SDK installed on your machine
- [ ] An existing Flutter application to integrate Ditto into
- [ ] Ditto Portal account wit a Ditto App (see [Sync Credentials](docId\:yMRWJNMDrNOvdT3qbPtXK))
- [ ] For Android development:
  - [ ] Android Studio installed on your machine
  - [ ] A physical Android device or Android emulator
- [ ] For iOS development:
  - [ ] macOS with the latest version of Xcode installed
  - [ ] A physical iOS device or an iOS simulator



## Step 1: Add the Ditto Dependency to the Application

:::::WorkflowBlock
:::WorkflowBlockItem
Run the following command in your terminal from the root of your application:

```shell
flutter pub add ditto_live
```
:::

::::WorkflowBlockItem
For iOS development, add the following permissions to `ios/Runner/Info.plist`:

:::CodeblockTabs
Info.plist

```xml
<key>NSBluetoothAlwaysUsageDescription</key>
<string>Uses Bluetooth to connect and sync with nearby devices</string>
<key>NSBluetoothPeripheralUsageDescription</key>
<string>Uses Bluetooth to connect and sync with nearby devices</string>
<key>NSLocalNetworkUsageDescription</key>
<string>Uses WiFi to connect and sync with nearby devices</string>
<key>NSBonjourServices</key>
```
:::
::::

:::WorkflowBlockItem
For Android development, add the following permissions to `android/app/src/main/AndroidManifest.xml`.

```xml
<uses-permission android:name="android.permission.BLUETOOTH"
        android:maxSdkVersion="30" />
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN"
        android:maxSdkVersion="30" />
<uses-permission android:name="android.permission.BLUETOOTH_ADVERTISE"
        tools:targetApi="s" />
<uses-permission android:name="android.permission.BLUETOOTH_CONNECT"
        tools:targetApi="s" />
<uses-permission android:name="android.permission.BLUETOOTH_SCAN"
        android:usesPermissionFlags="neverForLocation"
        tools:targetApi="s" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"
        android:maxSdkVersion="32" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"
        android:maxSdkVersion="30" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.CHANGE_NETWORK_STATE" />
<uses-permission android:name="android.permission.CHANGE_WIFI_MULTICAST_STATE" />
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />
<uses-permission android:name="android.permission.NEARBY_WIFI_DEVICES"
        android:usesPermissionFlags="neverForLocation"
        tools:targetApi="tiramisu" />
```
:::
:::::



## Step 2: Obtain Ditto AppID and Playground Token

::::WorkflowBlock
:::WorkflowBlockItem
Log in to your [Ditto Portal account](https://portal.ditto.live).
:::

:::WorkflowBlockItem
Navigate to your application and obtain the App ID and Playground Token. (See [Sync Credentials](docId\:yMRWJNMDrNOvdT3qbPtXK) for details)
:::

:::WorkflowBlockItem
Locate the `appID` and `playground token` for your application. These are required to initialize the Ditto Live SDK.
:::
::::



## Step 3: Import and Initialize the Ditto SDK

:::::WorkflowBlock
::::WorkflowBlockItem
Import the SDK in your Dart file where you plan to use it.

:::CodeblockTabs
Dart(beta)

```dart
import 'package:ditto_live/ditto_live.dart';
```
:::
::::

::::WorkflowBlockItem
Initialize the SDK to obtain an instance of `Ditto`. This is the main entry point into all Ditto-related functionality.

:::CodeblockTabs
Dart(beta)

```dart
Future<void> main() async {
	WidgetsFlutterBinding.ensureInitialized();
	
	// Request device permissions
	await [
      Permission.bluetoothConnect,
      Permission.bluetoothAdvertise,
      Permission.nearbyWifiDevices,
      Permission.bluetoothScan
    ].request();

    // Initialize Ditto with your Ditto AppId and Playground Token
    final identity = await OnlinePlaygroundIdentity.create(
      appId: "YOUR_APP_ID", // Replace with your specific id
      token: "YOUR_PLAYGROUND_TOKEN", // Replace with your specific token
    );
    final ditto = await Ditto.open(identity);
    
    // Start Ditto Sync
    await ditto.startSync();
        
    runApp(MyApp(ditto: ditto));
}

class MyApp extends StatelessWidget {
  final Ditto ditto;

  const MyApp({super.key, required this.ditto});

  @override
  Widget build(BuildContext context) {
    return Placeholder();
  }
}
```
:::
::::
:::::



## Step 4: Creating and Observing Data Store Changes

### Insert Data into the Ditto Store

To insert data into the Ditto store, use the following example. This demonstrates inserting a document into a collection named `items`:

:::CodeblockTabs
Dart(beta)

```dart
Future<void> insertData() async {
  final item = {'name': 'Sample Item', 'value': 100};
  await ditto.store.execute(
    "INSERT INTO items DOCUMENTS (:item)",
    arguments: {"item": item},
  );
}
```
:::

Call the `insertData` function wherever appropriate in your application, such as in a button press handler.

:::CodeblockTabs
Dart(beta)

```dart
FloatingActionButton(
  onPressed: insertData,
  child: Icon(Icons.add),
)
```
:::



### Register an Observer to Listen for Data Store Changes

To observe changes in the data store, register an observer. This example sets up an observer to listen for changes in the `items` collection:

:::CodeblockTabs
Dart(beta)

```dart
Future<void> observeData() async {
  final observer = await ditto.store.registerObserver(
    "SELECT * FROM items", 
    onChange: (event) {
	    // Handle data changed event
	    print("data changed");
	  },
  );
}
```
:::

Call the `observeData` function, typically in the `initState` method of a stateful widget to start observing when the widget is initialized.

:::CodeblockTabs
Dart(beta)

```dart
@override
void initState() {
  super.initState();
  observeData();
}
```
:::

Remember to cancel your observer in your widget’s `dispose()` method to prevent resource leaks

:::CodeblockTabs
Dart(beta)

```dart
@override
void dispose() {
  _observer.cancel();
  super.dispose();
}
```
:::



## Step 5: Syncing Data

To keep your data in sync across devices and with the Ditto Cloud (Big Peer), you need to register sync subscriptions. Sync subscriptions define the specific data that should be automatically synchronized to the device.

### Starting Sync

To start sync on the device you need to call `startSync`. This enables this device to sync data with other peers including the Ditto Cloud.

:::CodeblockTabs
Dart(beta)

```dart
await ditto.startSync();
```
:::

### Registering a Subscription

Register a subscription to a collection to keep the data in sync. Below is an example of how to register a subscription to the `items` collection:

:::CodeblockTabs
Dart(beta)

```dart
Future<void> syncData() async {
  await ditto.sync.registerSubscription("SELECT * FROM items");
}
```
:::

Call the `syncData` function, typically when initializing your Ditto instance.



## Step 6: Syncing Data Offline

Once your application is syncing data using Ditto, you can deploy it to multiple local devices, Android emulators, or iOS simulators. You can then disable the internet to observe the devices syncing offline.



## Step 7: Troubleshooting

- Ensure that all dependencies are up-to-date by updating to the latest version.
- Contact the Ditto team through [Human Help](docId\:zpBWWff8Rp7dKPVSAgKWo)&#x20;





