Skip to content

Commit 216ecfa

Browse files
committed
show list of users in setting screen
1 parent e328115 commit 216ecfa

File tree

9 files changed

+274
-16
lines changed

9 files changed

+274
-16
lines changed

lib/Api/auth_api.dart

Lines changed: 69 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import 'dart:convert';
33
import 'package:dio/dio.dart';
44
import 'package:flood_mobile/Model/register_user_model.dart';
55
import 'package:flood_mobile/Provider/user_detail_provider.dart';
6+
import 'package:flood_mobile/Model/current_user_detail_model.dart';
67
import 'package:flutter/cupertino.dart';
78
import 'package:provider/provider.dart';
89
import 'package:shared_preferences/shared_preferences.dart';
@@ -45,8 +46,9 @@ class AuthApi {
4546
// Setting token in shared preference
4647
SharedPreferences prefs = await SharedPreferences.getInstance();
4748
await prefs.setString('floodToken', token);
49+
await prefs.setString('floodUsername', username);
4850
Provider.of<UserDetailProvider>(context, listen: false)
49-
.setToken(token);
51+
.setUserDetails(token, username);
5052
return true;
5153
}
5254
return false;
@@ -82,8 +84,73 @@ class AuthApi {
8284
print(rawBody);
8385
response = await dio
8486
.post(url, data: rawBody, queryParameters: {"cookie": false});
85-
print(response);
8687
if (response.statusCode == 200) {
88+
print(response);
89+
getUsersList(context);
90+
} else {}
91+
} catch (e) {
92+
print('--ERROR--');
93+
print(e.toString());
94+
}
95+
}
96+
97+
static getUsersList(BuildContext context) async {
98+
try {
99+
String url = Provider.of<ApiProvider>(context, listen: false).baseUrl +
100+
ApiProvider.getUsersList;
101+
print('---GET USERS LIST---');
102+
print(url);
103+
Response response;
104+
Dio dio = new Dio();
105+
//Headers
106+
dio.options.headers['Accept'] = "application/json";
107+
dio.options.headers['Content-Type'] = "application/json";
108+
dio.options.headers['Connection'] = "keep-alive";
109+
dio.options.headers['Cookie'] =
110+
Provider.of<UserDetailProvider>(context, listen: false).token;
111+
response = await dio.get(
112+
url,
113+
);
114+
if (response.statusCode == 200) {
115+
List<CurrentUserDetailModel> usersList = [];
116+
for (final user in response.data) {
117+
usersList.add(CurrentUserDetailModel.fromJson(user));
118+
}
119+
Provider.of<UserDetailProvider>(context, listen: false)
120+
.setUsersList(usersList);
121+
print('---USERS LIST---');
122+
print(response);
123+
} else {}
124+
} catch (e) {
125+
print('--ERROR--');
126+
print(e.toString());
127+
}
128+
}
129+
130+
static deleteUser(BuildContext context, String username) async {
131+
try {
132+
String url = Provider.of<ApiProvider>(context, listen: false).baseUrl +
133+
ApiProvider.deleteUser +
134+
"/" +
135+
username;
136+
print('---DELETE USER---');
137+
print(url);
138+
Response response;
139+
Dio dio = new Dio();
140+
//Headers
141+
dio.options.headers['Accept'] = "application/json";
142+
dio.options.headers['Content-Type'] = "application/json";
143+
dio.options.headers['Connection'] = "keep-alive";
144+
dio.options.headers['Cookie'] =
145+
Provider.of<UserDetailProvider>(context, listen: false).token;
146+
response = await dio.delete(
147+
url,
148+
);
149+
if (response.statusCode == 200) {
150+
print(response);
151+
print('---USER DELETED---');
152+
// *Getting the users list again
153+
getUsersList(context);
87154
} else {}
88155
} catch (e) {
89156
print('--ERROR--');

lib/Components/user_list.dart

Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
import 'package:flood_mobile/Api/auth_api.dart';
2+
import 'package:flood_mobile/Constants/theme_provider.dart';
3+
import 'package:flood_mobile/Model/current_user_detail_model.dart';
4+
import 'package:flutter/cupertino.dart';
5+
import 'package:flutter/material.dart';
6+
7+
class UsersListView extends StatelessWidget {
8+
final List<CurrentUserDetailModel> usersList;
9+
final String currentUsername;
10+
11+
const UsersListView({
12+
Key? key,
13+
required this.usersList,
14+
required this.currentUsername,
15+
}) : super(key: key);
16+
17+
@override
18+
Widget build(BuildContext context) {
19+
return ListView.builder(
20+
shrinkWrap: true,
21+
itemCount: usersList.length,
22+
itemBuilder: (context, index) {
23+
return Container(
24+
height: 50.0,
25+
padding: EdgeInsets.symmetric(vertical: 5),
26+
decoration: BoxDecoration(
27+
color: ThemeProvider.theme.primaryColorLight,
28+
borderRadius: BorderRadius.circular(8),
29+
border: Border.all(
30+
color: ThemeProvider.theme.primaryColor,
31+
width: 1.0,
32+
),
33+
),
34+
child: Padding(
35+
padding: const EdgeInsets.all(8.0),
36+
child: Row(
37+
children: [
38+
Text(
39+
usersList[index].username,
40+
style: TextStyle(
41+
color: ThemeProvider.theme.textTheme.bodyText1?.color,
42+
),
43+
),
44+
Spacer(),
45+
(usersList[index].username == currentUsername)
46+
? Container(
47+
decoration: BoxDecoration(
48+
color: ThemeProvider.theme.highlightColor,
49+
borderRadius: BorderRadius.circular(20),
50+
),
51+
child: Padding(
52+
padding: const EdgeInsets.symmetric(
53+
horizontal: 6.0,
54+
vertical: 4.0,
55+
),
56+
child: Text(
57+
'Current User',
58+
style: TextStyle(
59+
color: ThemeProvider.theme.primaryColor),
60+
),
61+
),
62+
)
63+
: Center(
64+
child: IconButton(
65+
padding: EdgeInsets.zero,
66+
onPressed: () {
67+
AuthApi.deleteUser(
68+
context, usersList[index].username);
69+
},
70+
icon: Icon(
71+
Icons.close,
72+
size: 20.0,
73+
),
74+
),
75+
),
76+
SizedBox(
77+
width: 8.0,
78+
),
79+
],
80+
),
81+
),
82+
);
83+
},
84+
);
85+
}
86+
}

lib/Constants/theme_provider.dart

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,8 @@ class MyThemes {
3838
color: Colors.white,
3939
),
4040
),
41+
highlightColor: Color(0xff415062),
42+
errorColor: Color(0xffF34570),
4143
);
4244
static final lightTheme = ThemeData(
4345
brightness: Brightness.light,
@@ -62,5 +64,7 @@ class MyThemes {
6264
color: Colors.black,
6365
),
6466
),
67+
highlightColor: Color(0xff415062),
68+
errorColor: Color(0xffF34570),
6569
);
6670
}

lib/Pages/home_screen.dart

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import 'dart:convert';
33
import 'dart:io';
44
import 'package:badges/badges.dart';
55
import 'package:dio/dio.dart';
6+
import 'package:flood_mobile/Api/auth_api.dart';
67
import 'package:flood_mobile/Api/client_api.dart';
78
import 'package:flood_mobile/Api/notifications_api.dart';
89
import 'package:flood_mobile/Components/add_automatic_torrent.dart';
@@ -13,6 +14,7 @@ import 'package:flood_mobile/Components/nav_drawer_list_tile.dart';
1314
import 'package:flood_mobile/Components/notification_popup_dialogue_container.dart';
1415
import 'package:flood_mobile/Components/toast_component.dart';
1516
import 'package:flood_mobile/Constants/theme_provider.dart';
17+
import 'package:flood_mobile/Model/current_user_detail_model.dart';
1618
import 'package:flood_mobile/Pages/about_screen.dart';
1719
import 'package:flood_mobile/Pages/settings_screen.dart';
1820
import 'package:flood_mobile/Pages/torrent_screen.dart';
@@ -60,6 +62,7 @@ class _HomeScreenState extends State<HomeScreen> {
6062
);
6163
_processInitialUri();
6264
_listenForUri();
65+
AuthApi.getUsersList(context);
6366
}
6467

6568
@override
@@ -450,8 +453,11 @@ class _MenuState extends State<Menu> {
450453
SharedPreferences prefs =
451454
await SharedPreferences.getInstance();
452455
prefs.setString('floodToken', '');
456+
prefs.setString('floodUsername', '');
453457
Provider.of<UserDetailProvider>(context, listen: false)
454-
.setToken('');
458+
.setUserDetails('', '');
459+
Provider.of<UserDetailProvider>(context, listen: false)
460+
.setUsersList(<CurrentUserDetailModel>[]);
455461
Navigator.of(context).pushNamedAndRemoveUntil(
456462
Routes.loginScreenRoute,
457463
(Route<dynamic> route) => false);

lib/Pages/settings_screen.dart

Lines changed: 71 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,13 @@ import 'package:flood_mobile/Api/client_api.dart';
44
import 'package:flood_mobile/Components/flood_snackbar.dart';
55
import 'package:flood_mobile/Components/settings_text_field.dart';
66
import 'package:flood_mobile/Components/text_size.dart';
7+
import 'package:flood_mobile/Components/user_list.dart';
78
import 'package:flood_mobile/Constants/theme_provider.dart';
89
import 'package:flood_mobile/Model/client_settings_model.dart';
10+
import 'package:flood_mobile/Model/current_user_detail_model.dart';
911
import 'package:flood_mobile/Model/register_user_model.dart';
1012
import 'package:flood_mobile/Provider/client_provider.dart';
13+
import 'package:flood_mobile/Provider/user_detail_provider.dart';
1114
import 'package:flood_mobile/Services/transfer_speed_manager.dart';
1215
import 'package:flutter/material.dart';
1316
import 'package:flutter_keyboard_visibility/flutter_keyboard_visibility.dart';
@@ -64,6 +67,8 @@ class _SettingsScreenState extends State<SettingsScreen> {
6467
String downSpeed = '1 kB/s';
6568

6669
// *Authentication
70+
List<CurrentUserDetailModel> usersList = [];
71+
String currentUsername = '';
6772
TextEditingController usernameController = new TextEditingController();
6873
TextEditingController passwordController = new TextEditingController();
6974
TextEditingController pathController = new TextEditingController();
@@ -135,6 +140,11 @@ class _SettingsScreenState extends State<SettingsScreen> {
135140
upSpeed =
136141
TransferSpeedManager.valToSpeedMap[model.throttleGlobalUpSpeed] ??
137142
'Unlimited';
143+
144+
// Authentication Initialization
145+
usersList = Provider.of<UserDetailProvider>(context).usersList;
146+
currentUsername =
147+
Provider.of<UserDetailProvider>(context, listen: false).username;
138148
});
139149
super.didChangeDependencies();
140150
}
@@ -295,6 +305,8 @@ class _SettingsScreenState extends State<SettingsScreen> {
295305
),
296306
// *Authentication Section
297307
AuthenticationSection(
308+
usersList: usersList,
309+
currentUsername: currentUsername,
298310
setTCP: (value) {
299311
setState(() {
300312
socket = !value!;
@@ -521,8 +533,10 @@ class SpeedLimitSection extends StatelessWidget {
521533
}
522534

523535
class AuthenticationSection extends StatelessWidget {
524-
const AuthenticationSection({
536+
AuthenticationSection({
525537
Key? key,
538+
required this.usersList,
539+
required this.currentUsername,
526540
required this.usernameController,
527541
required this.passwordController,
528542
required this.isAdmin,
@@ -542,11 +556,13 @@ class AuthenticationSection extends StatelessWidget {
542556
required this.authenticationformKey,
543557
}) : super(key: key);
544558

559+
final List<CurrentUserDetailModel> usersList;
560+
final String currentUsername;
545561
final TextEditingController usernameController;
546562
final TextEditingController passwordController;
547-
final bool isAdmin;
548-
final String client;
549-
final bool socket;
563+
bool isAdmin;
564+
String client;
565+
bool socket;
550566
final TextEditingController pathController;
551567
final TextEditingController hostController;
552568
final TextEditingController portController;
@@ -562,6 +578,36 @@ class AuthenticationSection extends StatelessWidget {
562578

563579
@override
564580
Widget build(BuildContext context) {
581+
if (usersList.length == 0) {
582+
// User is not Admin
583+
return ExpansionTileCard(
584+
key: Key('Authentication Expansion Card'),
585+
onExpansionChanged: (value) {},
586+
elevation: 0,
587+
expandedColor: ThemeProvider.theme.primaryColor,
588+
baseColor: ThemeProvider.theme.primaryColor,
589+
title: MText(text: 'Authentication'),
590+
leading: Icon(Icons.security),
591+
contentPadding: EdgeInsets.all(0),
592+
children: [
593+
Container(
594+
width: double.infinity,
595+
decoration: BoxDecoration(
596+
color: ThemeProvider.theme.errorColor,
597+
borderRadius: BorderRadius.circular(8),
598+
border: Border.all(
599+
color: ThemeProvider.theme.primaryColor,
600+
width: 1.0,
601+
),
602+
),
603+
child: Padding(
604+
padding: const EdgeInsets.all(8.0),
605+
child: Text("User is not Admin"),
606+
),
607+
),
608+
],
609+
);
610+
}
565611
return ExpansionTileCard(
566612
key: Key('Authentication Expansion Card'),
567613
onExpansionChanged: (value) {},
@@ -578,6 +624,13 @@ class AuthenticationSection extends StatelessWidget {
578624
key: Key('Authentication option display column'),
579625
crossAxisAlignment: CrossAxisAlignment.start,
580626
children: [
627+
SText(text: 'User Accounts'),
628+
SizedBox(height: 25),
629+
UsersListView(
630+
usersList: usersList,
631+
currentUsername: currentUsername,
632+
),
633+
SizedBox(height: 25),
581634
SText(text: 'Add User'),
582635
SizedBox(height: 25),
583636
SettingsTextField(
@@ -643,7 +696,7 @@ class AuthenticationSection extends StatelessWidget {
643696
isExpanded: true,
644697
value: client,
645698
icon: const Icon(Icons.keyboard_arrow_down_rounded),
646-
dropdownColor: ThemeProvider.theme.backgroundColor,
699+
dropdownColor: ThemeProvider.theme.primaryColorLight,
647700
elevation: 16,
648701
onChanged: setClient,
649702
underline: Container(),
@@ -831,6 +884,19 @@ class AuthenticationSection extends StatelessWidget {
831884
),
832885
),
833886
);
887+
AuthApi.getUsersList(context);
888+
usernameController.clear();
889+
passwordController.clear();
890+
pathController.clear();
891+
clientUsernameController.clear();
892+
clientPasswordController.clear();
893+
urlController.clear();
894+
hostController.clear();
895+
portController.clear();
896+
setIsAdmin(false);
897+
setSocket(true);
898+
setClient('rTorrent');
899+
834900
final addNewUserSnackBar = addFloodSnackBar(
835901
SnackbarType.success,
836902
'New user added',

0 commit comments

Comments
 (0)