Subchapter 131.6
references/data-mobile.mdMarkdown6 KBView on GitHub
Initialize Amplify with Auth and API plugins before using this feature:
Flutter — lib/main.dart:
await Amplify.addPlugins([AmplifyAuthCognito(), AmplifyAPI()]);
await Amplify.configure(amplifyConfig);Generate dart outputs:
npx ampx sandbox --outputs-format dart --outputs-out-dir lib
Swift (Apple platforms):
try Amplify.add(plugin: AWSCognitoAuthPlugin())
try Amplify.add(plugin: AWSAPIPlugin())
try Amplify.configure(with: .amplifyOutputs)Drag
amplify_outputs.jsoninto the Xcode project navigator so it is included in the app bundle.
Android:
Amplify.addPlugin(AWSCognitoAuthPlugin())
Amplify.addPlugin(AWSApiPlugin())
Amplify.configure(AmplifyOutputs(R.raw.amplify_outputs), applicationContext)Place
amplify_outputs.jsoninapp/src/main/res/raw/. Enable core library desugaring for API level < 26.Backend required: Data must be defined in
amplify/data/resource.tsusingdefineData— see data-backend.md.
Import package:amplify_flutter/amplify_flutter.dart. All operations go through Amplify.API.
Queries: Amplify.API.query(request: ModelQueries.list(Todo.classType)) — response in .response.data?.items.
Same pattern for .get().
Mutations: Amplify.API.mutate(request: ModelMutations.create(todo)) — same shape for .update(), .delete().
Build updated models with todo.copyWith(done: true).
Subscriptions: Amplify.API.subscribe(ModelSubscriptions.onCreate(Todo.classType)) → returns a stream. Listen with .listen(), cancel with sub.cancel().
Supported: iOS 13+, macOS 12+, tvOS 13+, watchOS 9+, visionOS 1+ (preview).
Uses Amplify.API.query/mutate with async/await.
Swift uses shorthand request builders (.list(), .create(), .subscription(of:type:)) via GraphQLRequest extensions, unlike Flutter’s explicit ModelQueries/ModelMutations classes.
Queries: try await Amplify.API.query(request: .list(Todo.self)) — result is .success(let todos).
Mutations: try await Amplify.API.mutate(request: .create(newTodo)) — same for .update(), .delete().
Modify models directly: updated.done = true.
Subscriptions: Amplify.API.subscribe(request: .subscription(of: Todo.self, type: .onCreate)) → use for try await event in subscription. Cancel via task.cancel() when the view disappears.
Android supports both callback-based and coroutine-based APIs. Coroutine example (recommended):
Queries:
suspend fun getTodo(id: String) {
try {
val response = Amplify.API.query(ModelQuery.get(Todo::class.java, id))
Log.i("MyAmplifyApp", response.data.name)
} catch (error: ApiException) {
Log.e("MyAmplifyApp", "Query failed", error)
}
}Mutations:
val todo = Todo.builder()
.name("My todo")
.build()
try {
val response = Amplify.API.mutate(ModelMutation.create(todo))
Log.i("MyAmplifyApp", "Todo with id: ${response.data.id}")
} catch (error: ApiException) {
Log.e("MyAmplifyApp", "Create failed", error)
}Same pattern for .update() and .delete().
Build models via Todo.builder().name("text").build(); update via todo.copyOfBuilder().done(true).build().
Subscriptions (coroutine — uses Kotlin Flow):
val job = scope.launch {
try {
Amplify.API.subscribe(ModelSubscription.onCreate(Todo::class.java))
.catch { Log.e("MyAmplifyApp", "Error on subscription", it) }
.collect { Log.i("MyAmplifyApp", "Todo created: ${it.data.name}") }
} catch (error: ApiException) {
Log.e("MyAmplifyApp", "Subscription not established", error)
}
}
// When done:
job.cancel()Callback alternative: all operations also accept onSuccess/onError lambdas — e.g.
Amplify.API.query(ModelQuery.list(Todo::class.java), { response -> ... }, { error -> ... }).
npx ampx generate graphql-client-code to produce typed model
classes. Without this step, model types do not exist.Amplify.API.query/mutate), not REST. Using REST methods for model
CRUD returns errors..cancel() on Swift tasks, job.cancel() for
Kotlin coroutines, subscription.cancel() for callbacks, or
sub.cancel() for Flutter) — missing cleanup causes connection leaks and
stale data.DataStore.query() with
Amplify.API.query() in the same model workflow.