varroa/app/src/main/java/com/adamaps/varroa/api/AdaMapsApiClient.kt
kayos 74cdf6b381 Initial commit: Varroa ADAMaps Android app
Full rewrite of bee-debug-app as ADAMaps data proxy.
- Detection forwarder to ADAMaps API (polls landmarks/last/200, dedup by id+ts)
- 30s camera snapshot with 4-endpoint auto-detect
- GPS mini-map via osmdroid/OpenStreetMap
- Device status panel (firmware, GPS, AI ready flags)
- Connection status bar + forwarding toggle
- Foreground service with persistent notification
- Dark amber theme, no Google Play Services
- Package: com.adamaps.varroa, minSdk 26
2026-03-10 12:19:48 -07:00

65 lines
2.1 KiB
Kotlin

package com.adamaps.varroa.api
import com.adamaps.varroa.data.AdaMapsIngestRequest
import com.adamaps.varroa.data.ApiResult
import com.google.gson.Gson
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import okhttp3.MediaType.Companion.toMediaType
import okhttp3.OkHttpClient
import okhttp3.Request
import okhttp3.RequestBody.Companion.toRequestBody
import java.util.concurrent.TimeUnit
class AdaMapsApiClient(
private var apiUrl: String = "https://api.adamaps.org",
private var apiKey: String = "***REMOVED***"
) {
private val client = OkHttpClient.Builder()
.connectTimeout(15, TimeUnit.SECONDS)
.readTimeout(30, TimeUnit.SECONDS)
.writeTimeout(30, TimeUnit.SECONDS)
.build()
private val gson = Gson()
private val json = "application/json; charset=utf-8".toMediaType()
fun updateConfig(url: String, key: String) {
apiUrl = url.trimEnd('/')
apiKey = key
}
suspend fun ingest(request: AdaMapsIngestRequest): ApiResult<String> = withContext(Dispatchers.IO) {
try {
val body = gson.toJson(request).toRequestBody(json)
val req = Request.Builder()
.url("$apiUrl/api/ingest")
.addHeader("X-MapNet-Key", apiKey)
.addHeader("Content-Type", "application/json")
.post(body)
.build()
client.newCall(req).execute().use { resp ->
val respBody = resp.body?.string() ?: ""
if (resp.isSuccessful) ApiResult.Success(respBody)
else ApiResult.Error("HTTP ${resp.code}: ${resp.message}", resp.code)
}
} catch (e: Exception) {
ApiResult.Error(e.message ?: "Network error")
}
}
suspend fun checkReachability(): Boolean = withContext(Dispatchers.IO) {
try {
val req = Request.Builder()
.url("$apiUrl/health")
.head()
.build()
client.newCall(req).execute().use { resp ->
resp.code < 500
}
} catch (e: Exception) {
false
}
}
}