Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Protocol Selector Dropdown #321

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions lib/consts.dart
Original file line number Diff line number Diff line change
Expand Up @@ -245,6 +245,8 @@ final kColorHttpMethodDelete = Colors.red.shade800;

enum RequestItemMenuOption { edit, delete, duplicate }

enum ProtocolType { http }

enum HTTPVerb { get, head, post, put, patch, delete }

enum FormDataType { text, file }
Expand All @@ -258,6 +260,7 @@ const kMethodsWithBody = [
HTTPVerb.delete,
];

const kDefaultProtocolType = ProtocolType.http;
const kDefaultHttpMethod = HTTPVerb.get;
const kDefaultContentType = ContentType.json;

Expand Down
16 changes: 16 additions & 0 deletions lib/models/request_model.dart
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import 'models.dart';
class RequestModel {
const RequestModel({
required this.id,
this.protocol = kDefaultProtocolType,
this.method = HTTPVerb.get,
this.url = "",
this.name = "",
Expand All @@ -34,6 +35,7 @@ class RequestModel {
});

final String id;
final ProtocolType protocol;
final HTTPVerb method;
final String url;
final String name;
Expand Down Expand Up @@ -98,6 +100,7 @@ class RequestModel {
}) {
return RequestModel(
id: id,
protocol: protocol,
method: method,
url: url,
name: name ?? "${this.name} (copy)",
Expand All @@ -117,6 +120,7 @@ class RequestModel {

RequestModel copyWith({
String? id,
ProtocolType? protocol,
HTTPVerb? method,
String? url,
String? name,
Expand All @@ -141,6 +145,7 @@ class RequestModel {
var formDataList = requestFormDataList ?? this.requestFormDataList;
return RequestModel(
id: id ?? this.id,
protocol: protocol ?? this.protocol,
method: method ?? this.method,
url: url ?? this.url,
name: name ?? this.name,
Expand All @@ -162,11 +167,17 @@ class RequestModel {
}

factory RequestModel.fromJson(Map<String, dynamic> data) {
ProtocolType protocol;
HTTPVerb method;
ContentType requestBodyContentType;
ResponseModel? responseModel;

final id = data["id"] as String;
try {
protocol = ProtocolType.values.byName(data["protocol"] as String);
} catch (e) {
protocol = kDefaultProtocolType;
}
try {
method = HTTPVerb.values.byName(data["method"] as String);
} catch (e) {
Expand Down Expand Up @@ -200,6 +211,7 @@ class RequestModel {

return RequestModel(
id: id,
protocol: protocol,
method: method,
url: url,
name: name ?? "",
Expand Down Expand Up @@ -227,6 +239,7 @@ class RequestModel {
Map<String, dynamic> toJson({bool includeResponse = true}) {
return {
"id": id,
"protocol": protocol.name,
"method": method.name,
"url": url,
"name": name,
Expand All @@ -248,6 +261,7 @@ class RequestModel {
String toString() {
return [
"Request Id: $id",
"Request Protocol: ${protocol.name}",
"Request Method: ${method.name}",
"Request URL: $url",
"Request Name: $name",
Expand All @@ -271,6 +285,7 @@ class RequestModel {
return other is RequestModel &&
other.runtimeType == runtimeType &&
other.id == id &&
other.protocol == protocol &&
other.method == method &&
other.url == url &&
other.name == name &&
Expand All @@ -293,6 +308,7 @@ class RequestModel {
return Object.hash(
runtimeType,
id,
protocol,
method,
url,
name,
Expand Down
2 changes: 2 additions & 0 deletions lib/providers/collection_providers.dart
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,7 @@ class CollectionStateNotifier

void update(
String id, {
ProtocolType? protocol,
HTTPVerb? method,
String? url,
String? name,
Expand All @@ -146,6 +147,7 @@ class CollectionStateNotifier
ResponseModel? responseModel,
}) {
final newModel = state![id]!.copyWith(
protocol: protocol,
method: method,
url: url,
name: name,
Expand Down
2 changes: 2 additions & 0 deletions lib/screens/home_page/editor_pane/editor_request.dart
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,8 @@ class RequestEditorTopBar extends ConsumerWidget {
),
child: Row(
children: [
const DropdownButtonProtocol(),
kHSpacer20,
Expanded(
child: Text(
name ?? "",
Expand Down
22 changes: 22 additions & 0 deletions lib/screens/home_page/editor_pane/url_card.dart
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,28 @@ class EditorPaneRequestURLCard extends StatelessWidget {
}
}

class DropdownButtonProtocol extends ConsumerWidget {
const DropdownButtonProtocol({
super.key,
});

@override
Widget build(BuildContext context, WidgetRef ref) {
final protocol = ref
.watch(selectedRequestModelProvider.select((value) => value?.protocol));
return DropdownButtonProtocolType(
protocolType: protocol,
onChanged: (ProtocolType? value) {
final selectedId = ref.read(selectedRequestModelProvider)!.id;
ref
.read(collectionStateNotifierProvider.notifier)
.update(selectedId, protocol: protocol);
print('protocol: $value');
},
);
}
}

class DropdownButtonHTTPMethod extends ConsumerWidget {
const DropdownButtonHTTPMethod({
super.key,
Expand Down
50 changes: 50 additions & 0 deletions lib/widgets/dropdowns.dart
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,56 @@ class DropdownButtonHttpMethod extends StatelessWidget {
}
}

class DropdownButtonProtocolType extends StatelessWidget {
const DropdownButtonProtocolType({
super.key,
this.protocolType,
this.onChanged,
});

final ProtocolType? protocolType;
final void Function(ProtocolType? value)? onChanged;

@override
Widget build(BuildContext context) {
final surfaceColor = Theme.of(context).colorScheme.surface;
return DropdownButton<ProtocolType>(
isDense: true,
focusColor: surfaceColor,
value: protocolType,
icon: const Icon(
Icons.unfold_more_rounded,
size: 16,
),
elevation: 4,
underline: Container(
height: 0,
),
borderRadius: kBorderRadius12,
onChanged: onChanged,
items: ProtocolType.values
.map<DropdownMenuItem<ProtocolType>>((ProtocolType value) {
return DropdownMenuItem<ProtocolType>(
value: value,
child: Padding(
padding: const EdgeInsets.only(left: 16),
child: Text(
value.name.toUpperCase(),
style: kCodeStyle.copyWith(
fontWeight: FontWeight.bold,
color: Theme.of(context).brightness == Brightness.dark
? getDarkModeColor(Colors.white)
: Colors.black,
fontSize: 14,
),
),
),
);
}).toList(),
);
}
}

class DropdownButtonContentType extends StatelessWidget {
const DropdownButtonContentType({
super.key,
Expand Down
2 changes: 2 additions & 0 deletions test/models/request_model_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,7 @@ void main() {

Map<String, dynamic> requestModelAsJson = {
"id": '1',
"protocol": 'http',
"method": 'post',
"url": 'api.apidash.dev/case/lower',
"name": 'foss42 api',
Expand Down Expand Up @@ -137,6 +138,7 @@ void main() {

final requestModeDupString = [
"Request Id: 1",
"Request Protocol: http",
"Request Method: post",
"Request URL: api.apidash.dev/case/lower",
"Request Name: foss42 api",
Expand Down
44 changes: 44 additions & 0 deletions test/widgets/dropdowns_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -171,4 +171,48 @@ void main() {

expect(changedValue, CodegenLanguage.dartDio);
});
testWidgets('Testing Dropdown for ProtocolType', (tester) async {
ProtocolType? changedValue;
await tester.pumpWidget(
MaterialApp(
title: 'Dropdown ProtocolType testing',
theme: ThemeData.light(),
home: Scaffold(
body: Center(
child: Column(
children: [
DropdownButtonProtocolType(
protocolType: ProtocolType.values.first,
onChanged: (value) {
changedValue = value;
},
),
],
),
),
),
),
);

expect(find.byIcon(Icons.unfold_more_rounded), findsOneWidget);
expect(find.byType(DropdownButton<ProtocolType>), findsOneWidget);
expect(
(tester.widget(find.byType(DropdownButton<ProtocolType>))
as DropdownButton)
.value,
equals(ProtocolType.values.first));

if (ProtocolType.values.length > 1) {
await tester.tap(find.text(ProtocolType.values.first.name.toUpperCase()));
await tester.pump();
await tester.pump(const Duration(seconds: 1));

await tester
.tap(find.text(ProtocolType.values[1].name.toUpperCase()).last);
await tester.pump();
await tester.pump(const Duration(seconds: 1));

expect(changedValue, ProtocolType.values[1]);
}
});
}