Working with APIs in Dart
In real-world applications, Dart programs rarely work in isolation. They usually communicate with APIs (Application Programming Interfaces) to fetch or send data such as users, products, orders, or analytics.
In this lesson, you will learn how to consume APIs in Dart, send HTTP requests, receive JSON responses, and convert them into usable Dart objects.
What is an API?
An API is a bridge that allows two applications to communicate.
For example:
- A mobile app requests user data from a server
- The server responds with JSON data
- The app processes and displays the data
Most modern APIs use the HTTP protocol and return JSON.
Installing the HTTP Package
To work with APIs, Dart provides the http package.
Add the dependency in pubspec.yaml:
dependencies:
http: ^1.1.0
Then run:
dart pub get
Importing Required Libraries
import 'dart:convert';
import 'package:http/http.dart' as http;
Making a GET Request
Let’s fetch a list of users from a public API.
API Endpoint:
https://jsonplaceholder.typicode.com/users
Future fetchUsers() async {
final url = Uri.parse(
'https://jsonplaceholder.typicode.com/users',
);
final response = await http.get(url);
print(response.statusCode);
print(response.body);
}
If the request is successful, the server returns status code 200.
Decoding API Response
The response body is a JSON string. We convert it into Dart objects.
List users = jsonDecode(response.body);
print(users[0]['name']);
print(users[0]['email']);
Sample output:
- Leanne Graham
- Sincere@april.biz
Using a Model Class (Best Practice)
Professional applications always use strongly typed model classes.
User Model
class User {
final int id;
final String name;
final String email;
User({
required this.id,
required this.name,
required this.email,
});
factory User.fromJson(Map json) {
return User(
id: json['id'],
name: json['name'],
email: json['email'],
);
}
}
Fetching API Data into Model Objects
Future> fetchUsers() async {
final url = Uri.parse(
'https://jsonplaceholder.typicode.com/users',
);
final response = await http.get(url);
if (response.statusCode == 200) {
List data = jsonDecode(response.body);
return data.map((u) => User.fromJson(u)).toList();
} else {
throw Exception('Failed to load users');
}
}
Displaying the API Data
void main() async {
List users = await fetchUsers();
for (var user in users) {
print('${user.id}: ${user.name} - ${user.email}');
}
}
Making a POST Request
POST requests send data to the server.
Future createUser() async {
final url = Uri.parse(
'https://jsonplaceholder.typicode.com/users',
);
final response = await http.post(
url,
headers: {'Content-Type': 'application/json'},
body: jsonEncode({
"name": "Alice",
"email": "alice@example.com",
}),
);
print(response.statusCode);
print(response.body);
}
Handling API Errors
- Check status codes
- Handle network failures
- Use try-catch blocks
try {
await fetchUsers();
} catch (e) {
print('Error: $e');
}
Real-World Use Cases
- User authentication systems
- Fetching product catalogs
- Submitting orders
- Analytics and reporting dashboards
📝 Practice Exercises
Exercise 1
Fetch posts from /posts endpoint and display titles.
Exercise 2
Create a model for API posts.
Exercise 3
Send a POST request with new post data.
What’s Next?
In the next lesson, you will learn how to use the HTTP package in depth, including headers, query parameters, and timeouts.