In this article, we will implement jwt auth with provider(app state)
Install prerequisites:
flutter pub add http flutter pub add provider flutter pub add flutter_secure_storage flutter pub add shelf flutter pub add shelf_router
flutter_secure_storage requires minSdk version >= 18
Implement a simple endpoint for getting a fake jwt token
We will use shelf_router to implement our authentication server. In an actual situation, you can use any way to implement it.
Implement fake jwt server:
lib/jwt_server.dart
import 'dart:convert'; import 'package:shelf_router/shelf_router.dart'; import 'package:shelf/shelf.dart'; import 'package:shelf/shelf_io.dart' as io; void main() async { var app = Router(); app.post('/login', (Request request) { var json = jsonEncode({ 'access_token': 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c' }); return Response.ok(json, headers: { 'Access-Control-Allow-Origin': '*' }); }); await io.serve(app, 'localhost', 8080); }
Now we have the server for testing our jwt auth
Implement authorizaion
Create auth model:
lib/models/auth.dart
import 'package:flutter/material.dart'; import 'package:flutter_secure_storage/flutter_secure_storage.dart'; class AuthModel extends ChangeNotifier { final storage = const FlutterSecureStorage(); String? _token; bool isAuthorized = false; init() async { _token = await storage.read(key: 'token'); isAuthorized = _token != null; notifyListeners(); } login(String token) async { storage.write(key: 'token', value: token); _token = token; isAuthorized = true; notifyListeners(); } logout() { _token = null; isAuthorized = false; storage.delete(key: 'token'); notifyListeners(); } }
Register auth model:
lib/main.dart
import 'package:flutter/material.dart'; import 'package:jwt_example/models/auth.dart'; import 'package:provider/provider.dart'; void main() { runApp(const MyApp()); } class MyApp extends StatelessWidget { const MyApp({Key? key}) : super(key: key); // This widget is the root of your application. @override Widget build(BuildContext context) { var authModel = AuthModel(); authModel.init(); return ChangeNotifierProvider( create: (context) => authModel, child: const MaterialApp( home: MyHomePage(), )); } }
Implement view depends on auth:
lib/main.dart
... import 'package:http/http.dart' as http; import 'package:jwt_example/models/auth.dart'; ... class MyHomePage extends StatelessWidget { const MyHomePage({Key? key}) : super(key: key); @override Widget build(BuildContext context) { // Listen auth model changes var auth = context.watch<AuthModel>(); return OutlinedButton( onPressed: () async { if (auth.isAuthorized) { auth.logout(); } else { var url = Uri.parse('http://localhost:8080/login'); var response = await http.post(url); var decodedResponse = jsonDecode(response.body) as Map; auth.login(decodedResponse['access_token']); } }, child: auth.isAuthorized ? const Text("Logout") : const Text("Login"), ); } } ...
Run application:
dart run lib/jwt_server.dart flutter run -d chrome
This simple example can be a point for extending to the specific realization of auth logic in your project.
Useful links:
Get and upgrade Dart
Creating app template
Simple app state management
JSON Web Token
Authentication with JWT in Dart(server)
Top comments (0)