Authentication check plus signin screen added to frontend

This commit is contained in:
2024-04-03 22:14:54 +02:00
parent 340e54a0bb
commit dc6f4e0ebd
29 changed files with 761 additions and 161 deletions

View File

@@ -0,0 +1,29 @@
import 'package:flutter/material.dart';
import 'package:patient_manager/main.dart';
import 'package:patient_manager/pages/home.dart';
import 'package:patient_manager/pages/signin.dart';
import 'package:supabase_flutter/supabase_flutter.dart';
class AuthCheck extends StatelessWidget {
@override
Widget build(BuildContext context) {
return StreamBuilder<AuthState>(
stream: client.auth.onAuthStateChange.distinct(),
builder: (context, snapshot) {
if (snapshot.connectionState == ConnectionState.active) {
final user = snapshot.data?.session;
if (user == null) {
// User not authenticated, show login screen
return SignIn();
} else {
// User authenticated, show home screen
return Home();
}
}
// Connection state not active, show loading indicator
return CircularProgressIndicator();
},
);
}
}

View File

@@ -1,4 +1,5 @@
import 'package:flutter/material.dart';
import 'package:patient_manager/main.dart';
class MyAppBar extends StatelessWidget {
final String barTitle;
@@ -11,6 +12,15 @@ class MyAppBar extends StatelessWidget {
backgroundColor: Colors.blueAccent,
elevation: 8,
shadowColor: Colors.black,
leading: IconButton(
onPressed: () {
client.auth.signOut();
Navigator.of(context).pushNamed('/');
},
icon: const Icon(Icons.logout),
iconSize: 35,
color: Colors.black,
),
title: Text(
barTitle,
style: const TextStyle(

View File

@@ -0,0 +1,39 @@
import 'package:flutter/material.dart';
class MyTextField extends StatelessWidget {
final controller;
final String hintText;
final bool obscureText;
const MyTextField({
super.key,
required this.controller,
required this.hintText,
required this.obscureText,
});
@override
Widget build(BuildContext context) {
return Padding(
padding: const EdgeInsets.symmetric(horizontal: 25.0),
child: TextField(
controller: controller,
obscureText: obscureText,
decoration: InputDecoration(
fillColor: Colors.white,
filled: true,
hintText: hintText,
hintStyle: TextStyle(color: Colors.blueGrey[400]),
enabledBorder: const OutlineInputBorder(
borderSide: BorderSide(
color: Colors.blueAccent,
width: 2.0,
)),
focusedBorder: const OutlineInputBorder(
borderSide: BorderSide(color: Colors.blue),
),
),
),
);
}
}

View File

@@ -0,0 +1,33 @@
import 'package:flutter/material.dart';
class MyButton extends StatelessWidget {
final void Function() onTap;
final String buttonText;
const MyButton({super.key, required this.onTap, required this.buttonText});
@override
Widget build(BuildContext context) {
return GestureDetector(
onTap: onTap,
child: Container(
padding: const EdgeInsets.all(25),
margin: const EdgeInsets.symmetric(horizontal: 25),
decoration: BoxDecoration(
color: Colors.blueAccent,
borderRadius: BorderRadius.circular(10),
),
child: Center(
child: Text(
buttonText,
style: const TextStyle(
fontWeight: FontWeight.bold,
fontSize: 20,
color: Colors.white,
),
),
),
),
);
}
}

View File

@@ -1,10 +1,19 @@
import 'package:flutter/material.dart';
import 'package:patient_manager/router/routeGenerator.dart';
import 'package:supabase_flutter/supabase_flutter.dart';
void main() {
void main() async {
WidgetsFlutterBinding.ensureInitialized();
await Supabase.initialize(
url: "https://stzluvsyhbwtfbztarmu.supabase.co",
anonKey:
"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJzdXBhYmFzZSIsInJlZiI6InN0emx1dnN5aGJ3dGZienRhcm11Iiwicm9sZSI6ImFub24iLCJpYXQiOjE3MTIwNzUyMTMsImV4cCI6MjAyNzY1MTIxM30.a7VHlk63JJcAotvsqtoqiKwjNK4EbnNgKilAqt1iRio",
);
runApp(const MzanziInnovationHub());
}
final client = Supabase.instance.client;
class MzanziInnovationHub extends StatelessWidget {
const MzanziInnovationHub({super.key});

View File

@@ -0,0 +1,155 @@
import 'package:flutter/material.dart';
import 'package:patient_manager/components/myTextField.dart';
import 'package:patient_manager/components/mybutton.dart';
import 'package:patient_manager/main.dart';
import 'package:supabase_auth_ui/supabase_auth_ui.dart';
class SignIn extends StatefulWidget {
const SignIn({super.key});
@override
State<SignIn> createState() => _SignInState();
}
class _SignInState extends State<SignIn> {
final emailController = TextEditingController();
final passwordController = TextEditingController();
//sign user in
Future<void> signUserIn() async {
try {
final response = await client.auth.signInWithPassword(
email: emailController.text,
password: passwordController.text,
);
if (response.session != null) {
Navigator.of(context).pushNamed('/homme');
}
} on AuthException catch (error) {
loginError(error.message);
emailController.clear();
passwordController.clear();
}
}
void loginError(error) {
showDialog(
context: context,
builder: (context) {
return AlertDialog(
title: Text(error),
);
},
);
}
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Colors.white,
body: SafeArea(
child: Center(
child: SingleChildScrollView(
physics: const BouncingScrollPhysics(),
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
//logo
const Icon(
Icons.lock,
size: 100,
color: Colors.blueAccent,
),
//spacer
const SizedBox(height: 10),
//Heading
const Text(
'Sign In',
style: TextStyle(
fontSize: 25,
fontWeight: FontWeight.bold,
color: Colors.blueAccent,
),
),
//spacer
const SizedBox(height: 25),
//email input
SizedBox(
width: 500.0,
child: MyTextField(
controller: emailController,
hintText: 'Email',
obscureText: false,
),
),
//spacer
const SizedBox(height: 25),
//password input
SizedBox(
width: 500.0,
child: MyTextField(
controller: passwordController,
hintText: 'Password',
obscureText: true,
),
),
//spacer
const SizedBox(height: 10),
// forgot password
const Padding(
padding: EdgeInsets.symmetric(horizontal: 25.0),
child: Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
Text(
'Forgot Password?',
style: TextStyle(
color: Colors.white,
),
),
],
),
),
//spacer
const SizedBox(height: 50),
// sign in button
SizedBox(
width: 500.0,
child: MyButton(
onTap: signUserIn,
buttonText: "Sign In",
),
),
//spacer
const SizedBox(height: 30),
//register text
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const Text(
'New User?',
style: TextStyle(fontSize: 18, color: Colors.grey),
),
const SizedBox(
width: 6,
),
GestureDetector(
onTap: () {},
child: const Text(
'Register Now',
style: TextStyle(
fontSize: 18,
color: Colors.blueAccent,
),
),
)
],
)
],
),
),
),
),
);
}
}

View File

@@ -1,6 +1,8 @@
// ignore: file_names
import 'package:flutter/material.dart';
import 'package:patient_manager/Authentication/authCheck.dart';
import 'package:patient_manager/pages/home.dart';
import 'package:patient_manager/pages/signin.dart';
class RouteGenerator {
static Route<dynamic> generateRoute(RouteSettings settings) {
@@ -8,11 +10,11 @@ class RouteGenerator {
switch (settings.name) {
case '/':
return MaterialPageRoute(builder: (_) => AuthCheck());
case '/home':
return MaterialPageRoute(builder: (_) => const Home());
// case '/business':
// return MaterialPageRoute(builder: (_) => const Business());
// case '/businessList':
// return MaterialPageRoute(builder: (_) => const BusinessList());
case '/signin':
return MaterialPageRoute(builder: (_) => const SignIn());
// //case '/signIn':
// // return MaterialPageRoute(builder: (_) => SignIn());
// case '/auth':

View File

@@ -6,6 +6,14 @@
#include "generated_plugin_registrant.h"
#include <gtk/gtk_plugin.h>
#include <url_launcher_linux/url_launcher_plugin.h>
void fl_register_plugins(FlPluginRegistry* registry) {
g_autoptr(FlPluginRegistrar) gtk_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "GtkPlugin");
gtk_plugin_register_with_registrar(gtk_registrar);
g_autoptr(FlPluginRegistrar) url_launcher_linux_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "UrlLauncherPlugin");
url_launcher_plugin_register_with_registrar(url_launcher_linux_registrar);
}

View File

@@ -3,6 +3,8 @@
#
list(APPEND FLUTTER_PLUGIN_LIST
gtk
url_launcher_linux
)
list(APPEND FLUTTER_FFI_PLUGIN_LIST

View File

@@ -5,6 +5,14 @@
import FlutterMacOS
import Foundation
import app_links
import path_provider_foundation
import shared_preferences_foundation
import url_launcher_macos
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
AppLinksMacosPlugin.register(with: registry.registrar(forPlugin: "AppLinksMacosPlugin"))
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin"))
SharedPreferencesPlugin.register(with: registry.registrar(forPlugin: "SharedPreferencesPlugin"))
UrlLauncherPlugin.register(with: registry.registrar(forPlugin: "UrlLauncherPlugin"))
}

View File

@@ -17,6 +17,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "6.2.0"
app_links:
dependency: transitive
description:
name: app_links
sha256: "3ced568a5d9e309e99af71285666f1f3117bddd0bd5b3317979dccc1a40cada4"
url: "https://pub.dev"
source: hosted
version: "3.5.1"
archive:
dependency: transitive
description:
@@ -209,6 +217,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.3.6"
email_validator:
dependency: transitive
description:
name: email_validator
sha256: e9a90f27ab2b915a27d7f9c2a7ddda5dd752d6942616ee83529b686fc086221b
url: "https://pub.dev"
source: hosted
version: "2.1.17"
fake_async:
dependency: transitive
description:
@@ -217,6 +233,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.3.1"
ffi:
dependency: transitive
description:
name: ffi
sha256: "7bf0adc28a23d395f19f3f1eb21dd7cfd1dd9f8e1c50051c069122e6853bc878"
url: "https://pub.dev"
source: hosted
version: "2.1.0"
file:
dependency: transitive
description:
@@ -251,6 +275,19 @@ packages:
description: flutter
source: sdk
version: "0.0.0"
flutter_web_plugins:
dependency: transitive
description: flutter
source: sdk
version: "0.0.0"
font_awesome_flutter:
dependency: transitive
description:
name: font_awesome_flutter
sha256: "275ff26905134bcb59417cf60ad979136f1f8257f2f449914b2c3e05bbb4cd6f"
url: "https://pub.dev"
source: hosted
version: "10.7.0"
frontend_server_client:
dependency: transitive
description:
@@ -259,6 +296,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "3.2.0"
functions_client:
dependency: transitive
description:
name: functions_client
sha256: "9a0ab83a525c8691a6724746e642de755a299afa04158807787364cd9e718001"
url: "https://pub.dev"
source: hosted
version: "2.0.0"
glob:
dependency: transitive
description:
@@ -267,6 +312,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.1.2"
gotrue:
dependency: transitive
description:
name: gotrue
sha256: "1bf6354278a98b8a1867263e94921da8a239de07e9babceab2b4e80af651a098"
url: "https://pub.dev"
source: hosted
version: "2.5.1"
graphs:
dependency: transitive
description:
@@ -275,6 +328,22 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.3.1"
gtk:
dependency: transitive
description:
name: gtk
sha256: e8ce9ca4b1df106e4d72dad201d345ea1a036cc12c360f1a7d5a758f78ffa42c
url: "https://pub.dev"
source: hosted
version: "2.1.0"
http:
dependency: transitive
description:
name: http
sha256: a2bbf9d017fcced29139daa8ed2bba4ece450ab222871df93ca9eec6f80c34ba
url: "https://pub.dev"
source: hosted
version: "1.2.0"
http_multi_server:
dependency: transitive
description:
@@ -315,6 +384,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "4.8.1"
jwt_decode:
dependency: transitive
description:
name: jwt_decode
sha256: d2e9f68c052b2225130977429d30f187aa1981d789c76ad104a32243cfdebfbb
url: "https://pub.dev"
source: hosted
version: "0.3.1"
lints:
dependency: transitive
description:
@@ -379,6 +456,70 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.8.3"
path_provider:
dependency: transitive
description:
name: path_provider
sha256: b27217933eeeba8ff24845c34003b003b2b22151de3c908d0e679e8fe1aa078b
url: "https://pub.dev"
source: hosted
version: "2.1.2"
path_provider_android:
dependency: transitive
description:
name: path_provider_android
sha256: "477184d672607c0a3bf68fbbf601805f92ef79c82b64b4d6eb318cbca4c48668"
url: "https://pub.dev"
source: hosted
version: "2.2.2"
path_provider_foundation:
dependency: transitive
description:
name: path_provider_foundation
sha256: "5a7999be66e000916500be4f15a3633ebceb8302719b47b9cc49ce924125350f"
url: "https://pub.dev"
source: hosted
version: "2.3.2"
path_provider_linux:
dependency: transitive
description:
name: path_provider_linux
sha256: f7a1fe3a634fe7734c8d3f2766ad746ae2a2884abe22e241a8b301bf5cac3279
url: "https://pub.dev"
source: hosted
version: "2.2.1"
path_provider_platform_interface:
dependency: transitive
description:
name: path_provider_platform_interface
sha256: "88f5779f72ba699763fa3a3b06aa4bf6de76c8e5de842cf6f29e2e06476c2334"
url: "https://pub.dev"
source: hosted
version: "2.1.2"
path_provider_windows:
dependency: transitive
description:
name: path_provider_windows
sha256: "8bc9f22eee8690981c22aa7fc602f5c85b497a6fb2ceb35ee5a5e5ed85ad8170"
url: "https://pub.dev"
source: hosted
version: "2.2.1"
platform:
dependency: transitive
description:
name: platform
sha256: "12220bb4b65720483f8fa9450b4332347737cf8213dd2840d8b2c823e47243ec"
url: "https://pub.dev"
source: hosted
version: "3.1.4"
plugin_platform_interface:
dependency: transitive
description:
name: plugin_platform_interface
sha256: "4820fbfdb9478b1ebae27888254d445073732dae3d6ea81f0b7e06d5dedc3f02"
url: "https://pub.dev"
source: hosted
version: "2.1.8"
pointycastle:
dependency: transitive
description:
@@ -395,6 +536,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.5.1"
postgrest:
dependency: transitive
description:
name: postgrest
sha256: "9a3b590cf123f8d323b6a918702e037f037027d12a01902f9dc6ee38fdc05d6c"
url: "https://pub.dev"
source: hosted
version: "2.1.1"
protobuf:
dependency: transitive
description:
@@ -419,6 +568,30 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.2.3"
realtime_client:
dependency: transitive
description:
name: realtime_client
sha256: efb053dd11e2b3cfcc1aa11b3a41842f109d582adccb244a56ed58acf2f6b9f5
url: "https://pub.dev"
source: hosted
version: "2.0.2"
retry:
dependency: transitive
description:
name: retry
sha256: "822e118d5b3aafed083109c72d5f484c6dc66707885e07c0fbcb8b986bba7efc"
url: "https://pub.dev"
source: hosted
version: "3.1.2"
rxdart:
dependency: transitive
description:
name: rxdart
sha256: "0c7c0cedd93788d996e33041ffecda924cc54389199cde4e6a34b440f50044cb"
url: "https://pub.dev"
source: hosted
version: "0.27.7"
scratch_space:
dependency: transitive
description:
@@ -427,6 +600,62 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.0.2"
shared_preferences:
dependency: transitive
description:
name: shared_preferences
sha256: "81429e4481e1ccfb51ede496e916348668fd0921627779233bd24cc3ff6abd02"
url: "https://pub.dev"
source: hosted
version: "2.2.2"
shared_preferences_android:
dependency: transitive
description:
name: shared_preferences_android
sha256: "8568a389334b6e83415b6aae55378e158fbc2314e074983362d20c562780fb06"
url: "https://pub.dev"
source: hosted
version: "2.2.1"
shared_preferences_foundation:
dependency: transitive
description:
name: shared_preferences_foundation
sha256: "7708d83064f38060c7b39db12aefe449cb8cdc031d6062280087bc4cdb988f5c"
url: "https://pub.dev"
source: hosted
version: "2.3.5"
shared_preferences_linux:
dependency: transitive
description:
name: shared_preferences_linux
sha256: "9f2cbcf46d4270ea8be39fa156d86379077c8a5228d9dfdb1164ae0bb93f1faa"
url: "https://pub.dev"
source: hosted
version: "2.3.2"
shared_preferences_platform_interface:
dependency: transitive
description:
name: shared_preferences_platform_interface
sha256: "22e2ecac9419b4246d7c22bfbbda589e3acf5c0351137d87dd2939d984d37c3b"
url: "https://pub.dev"
source: hosted
version: "2.3.2"
shared_preferences_web:
dependency: transitive
description:
name: shared_preferences_web
sha256: "7b15ffb9387ea3e237bb7a66b8a23d2147663d391cafc5c8f37b2e7b4bde5d21"
url: "https://pub.dev"
source: hosted
version: "2.2.2"
shared_preferences_windows:
dependency: transitive
description:
name: shared_preferences_windows
sha256: "841ad54f3c8381c480d0c9b508b89a34036f512482c407e6df7a9c4aa2ef8f59"
url: "https://pub.dev"
source: hosted
version: "2.3.2"
shelf:
dependency: transitive
description:
@@ -472,6 +701,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.11.1"
storage_client:
dependency: transitive
description:
name: storage_client
sha256: bf5589d5de61a2451edb1b8960a0e673d4bb5c42ecc4dddf7c051a93789ced34
url: "https://pub.dev"
source: hosted
version: "2.0.1"
stream_channel:
dependency: transitive
description:
@@ -496,6 +733,30 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.2.0"
supabase:
dependency: transitive
description:
name: supabase
sha256: b4bde1a8c4ebbc7bbad929f4a884f277343351bcc795a9b1e9e6a0a4148ad1fb
url: "https://pub.dev"
source: hosted
version: "2.0.9"
supabase_auth_ui:
dependency: "direct main"
description:
name: supabase_auth_ui
sha256: "9c12964ee213a0b6d5f26d4e7d5818a57df6a7060a7cf8a16bb54c4e5f46c666"
url: "https://pub.dev"
source: hosted
version: "0.4.1"
supabase_flutter:
dependency: "direct main"
description:
name: supabase_flutter
sha256: c425b1f7c1915a4208e9fcf85bfc10e60af0db5149a5cf4b33b7f4003c3a9a4b
url: "https://pub.dev"
source: hosted
version: "2.4.0"
term_glyph:
dependency: transitive
description:
@@ -528,6 +789,70 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.3.2"
url_launcher:
dependency: transitive
description:
name: url_launcher
sha256: "0ecc004c62fd3ed36a2ffcbe0dd9700aee63bd7532d0b642a488b1ec310f492e"
url: "https://pub.dev"
source: hosted
version: "6.2.5"
url_launcher_android:
dependency: transitive
description:
name: url_launcher_android
sha256: d4ed0711849dd8e33eb2dd69c25db0d0d3fdc37e0a62e629fe32f57a22db2745
url: "https://pub.dev"
source: hosted
version: "6.3.0"
url_launcher_ios:
dependency: transitive
description:
name: url_launcher_ios
sha256: "9149d493b075ed740901f3ee844a38a00b33116c7c5c10d7fb27df8987fb51d5"
url: "https://pub.dev"
source: hosted
version: "6.2.5"
url_launcher_linux:
dependency: transitive
description:
name: url_launcher_linux
sha256: ab360eb661f8879369acac07b6bb3ff09d9471155357da8443fd5d3cf7363811
url: "https://pub.dev"
source: hosted
version: "3.1.1"
url_launcher_macos:
dependency: transitive
description:
name: url_launcher_macos
sha256: b7244901ea3cf489c5335bdacda07264a6e960b1c1b1a9f91e4bc371d9e68234
url: "https://pub.dev"
source: hosted
version: "3.1.0"
url_launcher_platform_interface:
dependency: transitive
description:
name: url_launcher_platform_interface
sha256: "552f8a1e663569be95a8190206a38187b531910283c3e982193e4f2733f01029"
url: "https://pub.dev"
source: hosted
version: "2.3.2"
url_launcher_web:
dependency: transitive
description:
name: url_launcher_web
sha256: fff0932192afeedf63cdd50ecbb1bc825d31aed259f02bb8dba0f3b729a5e88b
url: "https://pub.dev"
source: hosted
version: "2.2.3"
url_launcher_windows:
dependency: transitive
description:
name: url_launcher_windows
sha256: ecf9725510600aa2bb6d7ddabe16357691b6d2805f66216a97d1b881e21beff7
url: "https://pub.dev"
source: hosted
version: "3.1.1"
vector_math:
dependency: transitive
description:
@@ -560,6 +885,22 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.4.0"
win32:
dependency: transitive
description:
name: win32
sha256: "464f5674532865248444b4c3daca12bd9bf2d7c47f759ce2617986e7229494a8"
url: "https://pub.dev"
source: hosted
version: "5.2.0"
xdg_directories:
dependency: transitive
description:
name: xdg_directories
sha256: faea9dee56b520b55a566385b84f2e8de55e7496104adada9962e0bd11bcff1d
url: "https://pub.dev"
source: hosted
version: "1.0.4"
yaml:
dependency: transitive
description:
@@ -568,5 +909,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "3.1.2"
yet_another_json_isolate:
dependency: transitive
description:
name: yet_another_json_isolate
sha256: e727502a2640d65b4b8a8a6cb48af9dd0cbe644ba4b3ee667c7f4afa0c1d6069
url: "https://pub.dev"
source: hosted
version: "2.0.0"
sdks:
dart: ">=3.2.4 <3.5.0"
flutter: ">=3.16.6"

View File

@@ -35,6 +35,8 @@ dependencies:
# The following adds the Cupertino Icons font to your application.
# Use with the CupertinoIcons class for iOS style icons.
cupertino_icons: ^1.0.2
supabase_auth_ui: ^0.4.1
supabase_flutter: ^2.4.0
dev_dependencies:
flutter_test:

View File

@@ -6,6 +6,12 @@
#include "generated_plugin_registrant.h"
#include <app_links/app_links_plugin_c_api.h>
#include <url_launcher_windows/url_launcher_windows.h>
void RegisterPlugins(flutter::PluginRegistry* registry) {
AppLinksPluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("AppLinksPluginCApi"));
UrlLauncherWindowsRegisterWithRegistrar(
registry->GetRegistrarForPlugin("UrlLauncherWindows"));
}

View File

@@ -3,6 +3,8 @@
#
list(APPEND FLUTTER_PLUGIN_LIST
app_links
url_launcher_windows
)
list(APPEND FLUTTER_FFI_PLUGIN_LIST