> For the complete documentation index, see [llms.txt](https://docs.intellicar.in/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.intellicar.in/flash-mobile-sdk/android-sdk.md).

# Android SDK

## Installation

#### Step 1: Add JitPack to your project `build.gradle`

```groovy
allprojects {
    repositories {
        ...
        maven { url "https://jitpack.io" }
    }
}  
```

> **Note**: As of the 7.X.X Gradle build tools, `allprojects` is deprecated.\
> In that case, follow **Step 3** below.

***

#### - Step 2 - Add the dependency in your app build.gradle

```groovy
dependencies {
    ...
    implementation 'com.github.intellicar:lafm_android_sdk:0.0.112'
}
```

> Replace `0.0.112` with the latest version number shown below:\
> ![](https://jitpack.io/v/intellicar/lafm_android_sdk.svg)

***

#### - Step 3 - (Optional)

As of the 7.X.X Gradle build tools, Android projects no longer generate `allprojects` blocks in their project `build.gradle` file. Instead, you get a `dependencyResolutionManagement` block in your `settings.gradle`.

```groovy
dependencyResolutionManagement {
    repositoriesMode.set(RepositoriesMode.FAIL_ON_PROJECT_REPOS)
    repositories {
        ...
        maven {
            url 'https://jitpack.io'
        }
    }
}
```

***

### Documentation

***

## Implementation

### Required Dependency

<details>

<summary>Groovy</summary>

```groovy
dependencies {
    implementation 'org.bouncycastle:bcprov-jdk15on:1.69'
    implementation 'com.github.kittinunf.fuel:fuel-json:2.3.1'
    implementation 'com.github.kittinunf.fuel:fuel:2.3.1'
    implementation 'org.jetbrains.kotlinx:kotlinx-serialization-json:1.5.1'
}
```

</details>

<details>

<summary>Kotlin DSL</summary>

```kotlin
dependencies {
    implementation("org.bouncycastle:bcprov-jdk15on:1.69")
    implementation("org.jetbrains.kotlinx:kotlinx-serialization-json:1.5.1")
    implementation("com.github.kittinunf.fuel:fuel-json:2.3.1")
    implementation("com.github.kittinunf.fuel:fuel:2.3.1")
}
```

</details>

***

### 1. Flash Initialization

```kotlin
val flash = Flash(context, callback)
```

***

### 2. Generating key pair

> **phonePrivateKey** & **phonePublicKey**

```kotlin
val keyPairX25519 = flash?.generateKeyPair()
val privateKeyX25519 = keyPairX25519?.privateKey
val publicKeyX25519 = keyPairX25519?.publicKey
```

***

### 3. Token Initialization

```kotlin
flash.setToken(
    token = tokenJson, 
    phonePrivateKey = privateKeyX25519, 
    scanTimeout = null
)
```

* `token` will be the response from the **getlaftoken** API.
* `scanTimeout` is optional.
* `setToken` will:
  * Set the `TOKEN`.
  * Connect to the device.

**Example** `TOKEN`

```json
{
  "vehicleno": "KA03MF8135",
  "device_id": "3B0D2AE9F56B7A34",
  "device_name": "3B0D2AE9F56B7A34",
  "debug": false,
  "token": "01586E784A26000000707B6540860100000093DEF3EC7E010000070100020003000400050006000C0024ECC9DFA26DB136498D204E80F604AA3352E019D37F937050F0722824795C3ADB6745BB159E85EEC52D356C36035D1E0968928391AAACFFC72C092E47C0554938DE2E2F3714897C1A5C420478E5C606AF4169058870B9CE82EE294C99B27FFCFF1A6FB6FE48830130AC1DCB48C4C4F5292BF0284BAA584C23245A0281433D06",
  "lockcmd": "1,1E0968928391AAACFFC72C0",
  "unlockcmd": "4,006000C0024ECC9DFA26DB13649"
}
```

***

### 4. Callback Handler

> **Example**

```kotlin
interface FlashCallback {

    //*** Scan only
    //Called when a nearby device is found during a Normal scan
    fun onDeviceFound(deviceId: String, rssi: Int, estDistanceInMeters: Double) 

    //Called when we scan for a specific Device
    fun onScanWithFilter(deviceId: String, rssi: Int, estDistanceInMeters: Double)

    //Called when an error occurs during scanning
    fun onScanError(errorDetails: JSONObject)


    //*** BLE (Bluetooth Low Energy) operations
    //Called when the connection status of a device changes (e.g., Scanning, Found, Connected, Authorized, Disconnected, etc.)
    fun onStatusChange(deviceId: String, statusDetails: JSONObject)

    //Called when data is received from a connected device (e.g., GPS, accelerometer, GSM, CAN data, etc.)
    fun onDataReceived(deviceId: String, data: JSONObject)
}
```

* Any operation or update from the device will be received through these callbacks.
* Data is in **JSON** format.
* The general structure for data received is:

```json
{
  "msgtype": "MsgType",
  "data": { ... },
  "err": { ... },
  "msg": "Your Message"
}
```

#### Types of `MsgType`

| MsgType              | Description                         |
| -------------------- | ----------------------------------- |
| gps                  | GPS information                     |
| gsm                  | GSM information                     |
| can                  | CAN information                     |
| acc                  | Accelerometer information           |
| device\_io           | Device I/O information              |
| device\_info         | Device Information                  |
| mosfet\_control\_cmd | Mosfet control commands             |
| cmd\_error           | If any key missing in the command   |
| **Status**           |                                     |
| connection\_status   | Current Bluetooth connection status |

**Example** callback response format for `connection_status`

```json
{
  "msgtype": "connection_status",
  "data": {
    "status": "Scanning"
  },
  "err": null,
  "msg": "Status updated"
}
```

#### Possible `connection_status` values

| Connection Status | Description                                          |
| ----------------- | ---------------------------------------------------- |
| Scanning          | Scanning for device                                  |
| Found             | Device found during scanning                         |
| NotFound          | Device not found after scanning                      |
| Connecting        | Starting the connection process for the found device |
| FailedToConnect   | Unable to establish a connection                     |
| Connected         | Connection with device established successfully      |
| DisConnecting     | In the process of disconnecting the device           |
| DisConnected      | Connection closed                                    |
| Authorized        | Valid connection to the device (valid token)         |
| UnAuthorized      | Invalid connection to the device (invalid token)     |

***

### 5. Sending Commands

```kotlin
val commandCAN = JSONObject()
commandCAN.accumulate("action","get_can")
flash.exec("YourDeviceName", commandCAN)
```

#### Types of `action`

| Action             | Description                 |
| ------------------ | --------------------------- |
| get\_gps           | Retrieve GPS data           |
| get\_gsm           | Retrieve GSM data           |
| get\_can           | Retrieve CAN data           |
| get\_acc           | Retrieve accelerometer data |
| get\_device\_io    | Retrieve device I/O         |
| get\_device\_info  | Retrieve device details     |
| disconnect         | End an existing connection  |
| kle\_lock          | Lock the vehicle            |
| kle\_unlock        | Unlock the vehicle          |
| mosfet\_cmd        | Send Mosfet control command |
| start\_charging    | Start charging command      |
| output\_1\_enable  | Enable output 1             |
| output\_2\_disable | Disable output 2            |
| io\_control        | Send IO control command     |
| get\_sys\_info     | Retrieve the system info    |

> **Example** callback response format for a command (e.g., `acc`)

```json
{
  "msgtype": "acc",
  "data": {
    "scale": 20,
    "freq": 1000,
    "nrecords": 1,
    "accrcds": [
      {
        "ax": -17.154,
        "ay": -9.186,
        "az": -20.478,
        "roll": -18.97664722871585,
        "pitch": -37.39081780900416
      }
    ],
    "starttime": 0,
    "endtime": 0
  },
  "err": null,
  "msg": "data received successfully"
}
```

***

### 6. Mosfet Control

```kotlin
// Structure for sending the command
val commandJson = JSONObject().apply {
  put("action", "mosfet_cmd")
  put("data", JSONObject().apply {
    // You get cmd, cmd_type from getbatterycancmds API
    put("cmd", "4C41356A0003001E000105001900030060EA000005014001999808AA01010000000000E8030001E47E")
    put("cmd_type", "allowchg")
  })
}

flash.exec("YourDeviceName", commandJson)
```

**Response of the command**

```json
{
  "msgtype": "mosfet_control_cmd",
  "data": {
    "cmd_type": "allowchg",
    "status": "CMD_RECEIVED",
    "message": "Command Received by Device"
  },
  "err": null,
  "msg": "Received data successfully"
}
```

#### Possible `status` values

| Status          | Description                      |
| --------------- | -------------------------------- |
| CMD\_INPROGRESS | Command is currently in progress |
| CMD\_RECEIVED   | Command received by the device   |
| CMD\_SUCCESS    | Command executed successfully    |
| CMD\_FAILED     | Command failed                   |

***

### 7. Scan and StopScan

```kotlin
// This will scan all nearby devices.
// You receive device info in onDeviceFound(deviceId, rssi, estDistanceInMeters).
flash?.startScan()

// This also works for scanning a specific device using deviceId:
flash?.startScan(deviceId = "81C7B92D7C6F070A")

// To stop the scan:
flash?.stopScan()
```

```
```
