From 06a352d8bfc42fb9e0f6e4b4e1ebcced078dd239 Mon Sep 17 00:00:00 2001 From: Nilo Roberto C Paim Date: Wed, 30 Aug 2023 16:10:02 -0300 Subject: [PATCH] changes on login process --- lib/main.dart | 14 ++++- lib/models/login_model.dart | 53 +++++++++++++++++++ lib/pages/initial_page.dart | 4 +- lib/pages/login_page.dart | 11 ++-- lib/pages/register_page.dart | 2 +- lib/routes.dart | 11 ++-- lib/services/login_service.dart | 39 ++++++++++++++ lib/services/snackbar_service.dart | 27 ++++++++++ lib/stores/login_store.dart | 85 ++++++++++++++++++++++++++++++ pubspec.lock | 24 +++++++++ pubspec.yaml | 3 +- test/widget_test.dart | 30 ----------- 12 files changed, 258 insertions(+), 45 deletions(-) create mode 100644 lib/models/login_model.dart create mode 100644 lib/services/login_service.dart create mode 100644 lib/services/snackbar_service.dart create mode 100644 lib/stores/login_store.dart delete mode 100644 test/widget_test.dart diff --git a/lib/main.dart b/lib/main.dart index ac06d34..33b30fd 100644 --- a/lib/main.dart +++ b/lib/main.dart @@ -1,13 +1,23 @@ import 'package:flutter/material.dart'; import 'package:flutter_web_plugins/flutter_web_plugins.dart'; -import 'package:lixo/routes.dart'; +import 'package:pcastlivetv/globals.dart'; +import 'package:pcastlivetv/routes.dart'; +import 'package:pcastlivetv/stores/login_store.dart'; +import 'package:velocity_x/velocity_x.dart'; void main() { setUrlStrategy(NoHistoryUrlStrategy()); WidgetsFlutterBinding.ensureInitialized(); - runApp(const MyApp()); + baseURL = 'https://api.pcastlivetv.com'; + + runApp( + VxState( + store: LoginStore(), + child: const MyApp(), + ), + ); } class MyApp extends StatelessWidget { diff --git a/lib/models/login_model.dart b/lib/models/login_model.dart new file mode 100644 index 0000000..0cb1f42 --- /dev/null +++ b/lib/models/login_model.dart @@ -0,0 +1,53 @@ +import 'dart:convert'; + +class LoginModel { + String? message; + String? token; + int? userId; + String? userName; + String? userType; + + LoginModel._(); + + bool get isLogged => token != null && token!.isNotEmpty; + + String get loginMessage => message ?? ""; + + String get userRole => userType == "A" + ? "Administrador" + : userType == "R" + ? "Revendedor" + : "Usuário"; + + Map toMap() { + return { + 'token': token, + }; + } + + static LoginModel instance = LoginModel._(); + + factory LoginModel.fromMap(Map map) { + var authModel = LoginModel._(); + authModel.message = map['message'] as String; + authModel.token = map['token'] as String; + authModel.userId = map['userId'] as int; + authModel.userName = map['userName'] as String; + authModel.userType = map['userType'] as String; + return authModel; + } + + String toJson() => json.encode(toMap()); + + factory LoginModel.fromJson(String source) => LoginModel.fromMap(json.decode(source) as Map); + + @override + bool operator ==(covariant LoginModel other) { + if (identical(this, other)) return true; + + return other.token == token; + } + + @override + int get hashCode => token.hashCode; +} diff --git a/lib/pages/initial_page.dart b/lib/pages/initial_page.dart index 7d20c6c..368310b 100644 --- a/lib/pages/initial_page.dart +++ b/lib/pages/initial_page.dart @@ -1,7 +1,7 @@ import 'package:flutter/material.dart'; import 'package:go_router/go_router.dart'; -import 'package:lixo/components/nc_base_page.dart'; -import 'package:lixo/components/nc_button.dart'; +import 'package:pcastlivetv/components/nc_base_page.dart'; +import 'package:pcastlivetv/components/nc_button.dart'; class InitialPage extends StatelessWidget { const InitialPage({super.key}); diff --git a/lib/pages/login_page.dart b/lib/pages/login_page.dart index 81cf72f..42f06b3 100644 --- a/lib/pages/login_page.dart +++ b/lib/pages/login_page.dart @@ -1,4 +1,7 @@ import 'package:flutter/material.dart'; +import 'package:pcastlivetv/routes.dart'; +import 'package:pcastlivetv/services/snackbar_service.dart'; +import 'package:pcastlivetv/stores/login_store.dart'; import 'package:validatorless/validatorless.dart'; import 'package:velocity_x/velocity_x.dart'; @@ -17,7 +20,7 @@ class LoginPage extends StatefulWidget { class _LoginPageState extends State { @override Widget build(BuildContext context) { - // LoginStore store = VxState.store as LoginStore; + LoginStore store = VxState.store as LoginStore; final formKey = GlobalKey(); @@ -92,7 +95,7 @@ class _LoginPageState extends State { ), ), onPressed: () async { - //await verifyLogin(formKey, store, email, password); + await verifyLogin(formKey, store, email, password); }, child: const Padding( padding: EdgeInsets.all(8.0), @@ -113,7 +116,6 @@ class _LoginPageState extends State { ); } -/* Future verifyLogin(GlobalKey formKey, LoginStore store, String email, String password) async { processAuth(formKey, store, email, password); } @@ -135,6 +137,8 @@ class _LoginPageState extends State { close(); if (store.isLogged) { + SnackBarService.showSnackBar(content: "Login efetuado com sucesso!", error: false); + router.go('/home'); return true; } @@ -150,5 +154,4 @@ class _LoginPageState extends State { } return false; } - */ } diff --git a/lib/pages/register_page.dart b/lib/pages/register_page.dart index c7df27f..6c84abb 100644 --- a/lib/pages/register_page.dart +++ b/lib/pages/register_page.dart @@ -1,5 +1,5 @@ import 'package:flutter/material.dart'; -import 'package:lixo/components/nc_base_page.dart'; +import 'package:pcastlivetv/components/nc_base_page.dart'; class RegisterPage extends StatelessWidget { const RegisterPage({super.key}); diff --git a/lib/routes.dart b/lib/routes.dart index 1fa24bb..6d3066d 100644 --- a/lib/routes.dart +++ b/lib/routes.dart @@ -1,21 +1,22 @@ import 'package:go_router/go_router.dart'; -import 'package:lixo/pages/initial_page.dart'; -import 'package:lixo/pages/login_page.dart'; -import 'package:lixo/pages/register_page.dart'; +import 'package:pcastlivetv/pages/initial_page.dart'; +import 'package:pcastlivetv/pages/login_page.dart'; + +import 'pages/register_page.dart'; // GoRouter configuration final router = GoRouter( initialLocation: '/', routes: [ GoRoute( - name: 'home', // Optional, add name to your routes. Allows you navigate by name instead of path + name: 'home', path: '/', builder: (context, state) => const InitialPage(), ), GoRoute( name: 'login', path: '/login', - builder: (context, state) => LoginPage(), + builder: (context, state) => const LoginPage(), ), GoRoute( name: 'register', diff --git a/lib/services/login_service.dart b/lib/services/login_service.dart new file mode 100644 index 0000000..224d824 --- /dev/null +++ b/lib/services/login_service.dart @@ -0,0 +1,39 @@ +import 'dart:convert'; + +import 'package:dio/dio.dart'; +import 'package:pcastlivetv/globals.dart'; + +import '../models/login_model.dart'; + +class AuthService { + Future login(String email, String password) async { + final dio = Dio(); + try { + final data = { + "email": email, + "password": password, + }; + + final response = await dio.post( + Endpoints.login, + options: Options( + headers: { + 'Content-Type': 'application/json', + }, + ), + data: jsonEncode(data), + ); + + switch (response.statusCode) { + case 200: + print(jsonDecode(response.data)); + var authModel = LoginModel.fromJson(jsonDecode(response.data)); + return authModel; + default: + throw Exception('Erro inesperado no login: ${response.statusCode} - ${response.data.toString()}'); + } + } on Exception catch (e) { + throw Exception('Exception inesperada no login: $e'); + } + } +} diff --git a/lib/services/snackbar_service.dart b/lib/services/snackbar_service.dart new file mode 100644 index 0000000..53b7b4b --- /dev/null +++ b/lib/services/snackbar_service.dart @@ -0,0 +1,27 @@ +import 'package:flutter/material.dart'; + +import '../globals.dart'; + +class SnackBarService { + static void showSnackBar({required String content, bool error = false}) { + snackbarKey.currentState?.showSnackBar( + SnackBar( + content: Text( + content, + textAlign: TextAlign.center, + style: const TextStyle( + fontSize: 20, + fontWeight: FontWeight.bold, + color: Colors.black, + ), + ), + backgroundColor: error ? Colors.red : Colors.green, + duration: const Duration(seconds: 3), + shape: RoundedRectangleBorder( + borderRadius: BorderRadius.circular(10.0), + ), + elevation: 8.0, + ), + ); + } +} diff --git a/lib/stores/login_store.dart b/lib/stores/login_store.dart new file mode 100644 index 0000000..e203a7f --- /dev/null +++ b/lib/stores/login_store.dart @@ -0,0 +1,85 @@ +import 'package:velocity_x/velocity_x.dart'; + +import '../services/login_service.dart'; + +class LoginStore extends VxStore { + AuthService service = AuthService(); + + var isLogged = false; + + String? message = ''; + + String email = ''; + String password = ''; + + String? token; + int? userId; + String? userName; + String? userType; + + Future login() async { + try { + var response = await service.login(email, password); + AuthMessage(response.message!); + if (response.token != '' || response.message == '') { + token = response.token; + userId = response.userId; + userName = response.userName; + userType = response.userType; + isLogged = true; + AuthLogged(true); + } + } catch (e) { + AuthMessage("SETEI NA STORE UMA EXCEPTION: $e"); + } + } + + Future logout() async { + message = null; + token = null; + userId = null; + userName = null; + userType = null; + isLogged = false; + } +} + +class AuthLogged extends VxMutation { + final bool value; + AuthLogged(this.value); + + @override + perform() { + store!.isLogged = value; + } +} + +class AuthMessage extends VxMutation { + final String value; + AuthMessage(this.value); + + @override + perform() { + store!.message = value; + } +} + +class AuthEmail extends VxMutation { + final String value; + AuthEmail(this.value); + + @override + perform() { + store!.email = value; + } +} + +class AuthPassword extends VxMutation { + final String value; + AuthPassword(this.value); + + @override + perform() { + store!.password = value; + } +} diff --git a/pubspec.lock b/pubspec.lock index 380f7d6..ea93242 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -57,6 +57,14 @@ packages: url: "https://pub.dev" source: hosted version: "1.0.5" + dio: + dependency: "direct main" + description: + name: dio + sha256: ce75a1b40947fea0a0e16ce73337122a86762e38b982e1ccb909daa3b9bc4197 + url: "https://pub.dev" + source: hosted + version: "5.3.2" fake_async: dependency: transitive description: @@ -96,6 +104,14 @@ packages: url: "https://pub.dev" source: hosted version: "10.1.0" + http_parser: + dependency: transitive + description: + name: http_parser + sha256: "2aa08ce0341cc9b354a498388e30986515406668dbcc4f7c950c3e715496693b" + url: "https://pub.dev" + source: hosted + version: "4.0.2" intl: dependency: transitive description: @@ -205,6 +221,14 @@ packages: url: "https://pub.dev" source: hosted version: "0.6.0" + typed_data: + dependency: transitive + description: + name: typed_data + sha256: facc8d6582f16042dd49f2463ff1bd6e2c9ef9f3d5da3d9b087e244a7b564b3c + url: "https://pub.dev" + source: hosted + version: "1.3.2" validatorless: dependency: "direct main" description: diff --git a/pubspec.yaml b/pubspec.yaml index a5afe07..e2ad977 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -1,4 +1,4 @@ -name: lixo +name: pcastlivetv description: A new Flutter project. publish_to: 'none' # Remove this line if you wish to publish to pub.dev @@ -18,6 +18,7 @@ dependencies: flutter_web_plugins: sdk: flutter + dio: ^5.3.2 dev_dependencies: flutter_test: diff --git a/test/widget_test.dart b/test/widget_test.dart deleted file mode 100644 index 1ac27b0..0000000 --- a/test/widget_test.dart +++ /dev/null @@ -1,30 +0,0 @@ -// This is a basic Flutter widget test. -// -// To perform an interaction with a widget in your test, use the WidgetTester -// utility in the flutter_test package. For example, you can send tap and scroll -// gestures. You can also use WidgetTester to find child widgets in the widget -// tree, read text, and verify that the values of widget properties are correct. - -import 'package:flutter/material.dart'; -import 'package:flutter_test/flutter_test.dart'; - -import 'package:lixo/main.dart'; - -void main() { - testWidgets('Counter increments smoke test', (WidgetTester tester) async { - // Build our app and trigger a frame. - await tester.pumpWidget(const MyApp()); - - // Verify that our counter starts at 0. - expect(find.text('0'), findsOneWidget); - expect(find.text('1'), findsNothing); - - // Tap the '+' icon and trigger a frame. - await tester.tap(find.byIcon(Icons.add)); - await tester.pump(); - - // Verify that our counter has incremented. - expect(find.text('0'), findsNothing); - expect(find.text('1'), findsOneWidget); - }); -}