How to display different different data form in Json response? - json

I'm successfully got responded from my API , also able to display Status and Message in my App.
But How to display Name & EncUserId as it is inside UserData
Here is my JSON response in Postman
{
"Status": "1",
"Message": "You are Logged in successfully",
"UserData": {
"Name": "qwerty#gmail.com",
"EncUserId": "GO9gj3aSUKCpxE3AMSbh/A=="
}
}
Im Displaying my Json response in my App in this format
Text("Status: ${widget.response.status}"),
Text("Message: ${widget.response.message}"),
Here is API model
class ApiResponse {
ApiResponse({
required this.status,
required this.message,
required this.userData,
});
String status;
String message;
UserData? userData;
factory ApiResponse.fromJson(Map<String, dynamic> json) => ApiResponse(
status: json["Status"],
message: json["Message"],
userData: json["UserData"] == null? null:UserData.fromJson(json["UserData"] as Map<String, dynamic>),
);
}
class UserData {
UserData({
required this.name,
required this.encUserId,
});
String name;
String encUserId;
factory UserData.fromJson(Map<String, dynamic> json) => UserData(
name: json["Name"],
encUserId: json["EncUserId"],
);
}

This will work
Text("name: ${widget.response.userData.name}"),
Text("encUserId: ${widget.response.userData.encUserId}")

Related

How can I fetch data in API without giving this error

I want to retrieve some data in API, but that's giving an error . How can i get List of all posts
This is my DataModel class:
class DataModel {
DataModel({
required this.id,
required this.title,
required this.body,
});
int id;
String title;
String body;
factory DataModel.fromJson(Map<String, dynamic> json) => DataModel(
id: json["id"],
title: json["title"],
body: json["body"],
);
Map<String, dynamic> toJson() => {
"id": id,
"title": title,
"body": body,
};
}
And this is my get future data function:
Future<DataModel?> getData(context) async {
DataModel? result;
try {
final response = await http.get(
Uri.parse("https://someapi.com/posts"),); // this is example api for security
if (response.statusCode == 200) {
final data = json.decode(response.body);
result = DataModel.fromJson(data);
} else {
// ignore: avoid_print
print("error");
}
} catch (e) {
log(e.toString());
}
return result;
}
That's giving me an error like that:
type 'List<dynamic>' is not a subtype of type 'Map<String, dynamic>'
I think in the reponse you are getting a list of items which has to be used like the following
var list = json.decode(response.body);
List<DataModel> result = list.map((i) => DataModel.fromJSON(i)).toList();
return result;
And the method will return
Future<List<DataModel>>?

Json Status=0 not displaying

I'm trying to show my json response after user login. It successfully displaying response in my app when user put correct info. But the app getting crashed when user putting wrong credentials
Here is my json response when user put wrong info. It should displaying Status=0 in my app display(or whatever response I want to display
I/flutter (16426): {"Status":"0","Message":"Wrong Password provided","UserData":null}
Here is my API call when user press the login button
Future<void> login() async{
var jsonResponse = null;
if (passwordontroller.text.isNotEmpty && emailController.text.isNotEmpty) {
var response = await http.post(Uri.parse("http://jhhjhjhjhjhjhj"),
body: ({
'LoginId': emailController.text,
'Password': passwordontroller.text
}));
if (response.statusCode == 200) {
print("Correct");
print(response.body);
jsonResponse = json.decode(response.body.toString());
print(jsonResponse);
Navigator.push(context, MaterialPageRoute(builder: (context)=>AfterLoginResPage(response: ApiResponse.fromJson(jsonResponse))));
}
else {
print("Wronggooooooooooooooooooooooooooo");
print(response.body);
ScaffoldMessenger.of(context)
.showSnackBar(SnackBar(content: Text("Invalid credentials")));
}
} else {
ScaffoldMessenger.of(context)
.showSnackBar(SnackBar(content: Text("Blank field is not allowed")));
}
}
My Model class
class ApiResponse {
ApiResponse({
required this.status,
required this.message,
required this.userData,
});
String status;
String message;
UserData userData;
factory ApiResponse.fromJson(Map<String, dynamic> json) => ApiResponse(
status: json["Status"],
message: json["Message"],
//userData: UserData.fromJson(json["UserData"]),
userData: json["UserData"] == null? null:UserData.fromJson(json["UserData"]), //======== Updated
);
}
class UserData {
UserData({
required this.name,
required this.encUserId,
});
String name;
String encUserId;
factory UserData.fromJson(Map<String, dynamic> json) => UserData(
name: json["Name"],
encUserId: json["EncUserId"],
);
}
And then here I'm displaying my response which is successfully getting executed when User putting correct credentials. but got crashed when putting wrong credentials
children: [
Text("Status: ${widget.response.status}"),
Text("Message: ${widget.response.message}"),
one more problem I'm facing ,here im able to display status and message What If I want to display Name & EncUserId also?.
here is my json response in postman after putting right info
{
"Status": "1",
"Message": "You are Logged in successfully",
"UserData": {
"Name": "tuhinroy881#gmail.com",
"EncUserId": "bbA/HajfPdswT0fhhiMvEg=="
}
}
.
Since null safety is enabled, you need to change UserData userData to UserData? userData; and userData: json["UserData"] == null? null:UserData.fromJson(json["UserData"] as Map<String, dynamic>)
Your problem is that you are trying to parse UserData while your error response doesn't have any UserData related information.
class ApiResponse {
ApiResponse({
required this.status,
required this.message,
required this.userData,
});
String status;
String message;
UserData? userData;
factory ApiResponse.fromJson(Map<String, dynamic> json) => ApiResponse(
status: json["Status"],
message: json["Message"],
userData: json["UserData"] == null? null:UserData.fromJson(json["UserData"]),
);
}

Dart - error doing deserialization of FCM Json notification

I have an app made in flutter 1.22.2, and I'm putting together a "Notification Center" view. When the notification arrives at the device, it arrives in json format, and I'm trying to make a decode, to display it in this view.
fcm.configure(
onMessage: (message) async {
try {
print("onMessage: $message");
PushDecode.fromJson(message);
print(PushDecode().notification.title);
} catch (e) {
print(e);
}
return message;
},
onLaunch: (message) async {
print("onLaunch: $message");
},
onResume: (message) async {
print("onResume: $message");
},
);
My decode class:
// final pushDecode = pushDecodeFromJson(jsonString);
import 'dart:convert';
PushDecode pushDecodeFromJson(String str) => PushDecode.fromJson(json.decode(str));
String pushDecodeToJson(PushDecode data) => json.encode(data.toJson());
class PushDecode {
PushDecode({
this.data,
this.notification,
});
Data data;
PushNotification notification;
factory PushDecode.fromJson(Map<dynamic, dynamic> json) => PushDecode(
data: Data.fromJson(json["data"]),
notification: PushNotification.fromJson(json["notification"]),
);
Map<dynamic, dynamic> toJson() => {
"data": data.toJson(),
"notification": notification.toJson(),
};
}
class Data {
Data({
this.title,
this.message,
});
String title;
String message;
factory Data.fromJson(Map<dynamic, dynamic> json) => Data(
title: json["title"],
message: json["message"],
);
Map<dynamic, dynamic> toJson() => {
"title": title,
"message": message,
};
}
class PushNotification {
PushNotification({
this.body,
this.title,
});
String body;
String title;
factory PushNotification.fromJson(Map<dynamic, dynamic> json) =>
PushNotification(
body: json["body"],
title: json["title"],
);
Map<dynamic, dynamic> toJson() => {
"body": body,
"title": title,
};
}
I have received this error when I run the code.
I/flutter (xx): onMessage: {notification: {title: Test one, body: Test one body}, data: {title: number 1, message: number too}}
I/flutter (xx): NoSuchMethodError: The getter 'title' was called on null.
I/flutter (xx): Receiver: null
I/flutter (xx): Tried calling: title
What happens is that the onMessage () try goes straight through the decode class, and the error pops up, returning null, what should I do?
Try using PushDecode.fromJson(jsonDecode(message.data));
You might be getting it as a string.

How to Map Model Class from JSON Response Flutter/MongoDB

I have used Node/MongoDB for my back end and everything works fine wrt requests and responses.
For my front end, I am building a mobile app with flutter and therefore have to create model classes to represent my response.
Sample response:
{success: true, message: Logged in Successfully, user: {_id: 6028965c16056b37eca50076, username: spideyr, email: peterparker#gmail.com, password: $2b$10$R4kYBA3Ezk7z2EBIY3dfk.6Qy.IXQuXJocKVS5PCzLf4fXYckUMju, phone: 89066060484, __v: 0}, accessToken: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpYXQiOjE2MTM1NDg3ODIsImV4cCI6MTYxNjE0MDc4MiwiYXVkIjoiNjAyODk2NWMxNjA1NmIzN2VjYTUwMDc2IiwiaXNzIjoicGlja3VycGFnZS5jb20ifQ.DX8-WGRkCQ9geAaQASOIzoPGpvpjdI7aV0C5o1i5Thw, refreshToken: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpYXQiOjE2MTM1NDg3ODIsImV4cCI6MTY0NTEwNjM4MiwiYXVkIjoiNjAyODk2NWMxNjA1NmIzN2VjYTUwMDc2IiwiaXNzIjoicGlja3VycGFnZS5jb20ifQ.RkVCGK9FfU0rxs2qf5QtJsyFaGShsL05CI320GsmAwg}
In this response body, I am only interested in the user field and therefore have created my POJO/PODO class like below:
class UserModel {
final String id;
final String username;
final String email;
final String phone;
const UserModel({
this.id,
#required this.email,
#required this.username,
#required this.phone,
});
UserModel copyWith({String id, String username, String email, String phone}){
if (
(id == null) || identical(id, this.id) &&
(username == null) || identical(id, this.username) &&
(email == null || identical(email, this.email)) &&
(phone == null || identical(phone, this.phone))) {
return this;
}
return new UserModel(
id: id ?? this.id,
username: username ?? this.username,
email: email ?? this.email,
phone: phone ?? this.phone,
);
}
static const empty = UserModel(email: '', username: null, phone: null, id: '');
#override
String toString() {
return 'User{id: $id, username: $username, email: $email, phone: $phone}';
}
factory UserModel.fromMap(Map<String, dynamic> map){
return new UserModel(
id:map['_id'], // unable to understand why it shows error here
username:map['username'],
email:map['email'],
phone:map['phone'],
);
}
Map<String, dynamic> toMap(){
return {
'id': id,
'username': username,
'email': email,
'phone': phone,
};
}
}
I am able to login and register a user but this error keeps appearing regarding my mapping from mongo db's _id to id in my model class UserModel.fromJSON() method. Here's the error:
I/flutter (19353): NoSuchMethodError: The method '[]' was called on null.
I/flutter (19353): Receiver: null
I/flutter (19353): Tried calling: []("_id")
Does anyone know what changes I need to make in my UserModel class? Thanks.
I converted your JSON to class
class Model {
Model({
this.success,
this.message,
this.user,
this.accessToken,
this.refreshToken,
});
bool success;
String message;
User user;
String accessToken;
String refreshToken;
factory Model.fromJson(Map<String, dynamic> json) => Model(
success: json["success"],
message: json["message"],
user: User.fromJson(json["user"]),
accessToken: json["accessToken"],
refreshToken: json["refreshToken"],
);
Map<String, dynamic> toJson() => {
"success": success,
"message": message,
"user": user.toJson(),
"accessToken": accessToken,
"refreshToken": refreshToken,
};
}
class User {
User({
this.id,
this.username,
this.email,
this.password,
this.phone,
this.v,
});
String id;
String username;
String email;
String password;
String phone;
int v;
factory User.fromJson(Map<String, dynamic> json) => User(
id: json["_id"],
username: json["username"],
email: json["email"],
password: json["password"],
phone: json["phone"],
v: json["__v"],
);
Map<String, dynamic> toJson() => {
"_id": id,
"username": username,
"email": email,
"password": password,
"phone": phone,
"__v": v,
};
}
thanks to everyone that tried to help me understand the issue. I was missing a return statement in my APIClient class and that ensured that all the values in my map in fromJSON method were null.
Here's the correction:
class APIClient {
dynamic post(String pathSegment, Map<String, dynamic> body) async {
Dio dio = Dio();
Response response = await dio.post(
'${APIConstants.BASE_URL}${APIConstants.AUTH_URL}/$pathSegment',
data: body
);
if(response.statusCode == 200) {
print(response.data);
return response.data; // here's the change
} else {
print(response.statusMessage);
throw Exception(response.statusMessage);
}
}
}
The problem is in the UserResponseModel class. You are assigning Map to user.
Try this:
factory UserResponseModel.fromJSON(Map<String, dynamic> json) {
return UserResponseModel(
user: UserModel.fromJSON(json['user']),
success: json['success'],
message: json['message'],
accessToken: json['accessToken'],
refreshToken: json['refreshToken'],
);
}

JSON Parse not parsing in Flutter if some object is empty

I have a signup form and the backend is PHP. PHP returning success, error data as JSON.
Below is my JSONParse file.
import 'dart:convert';
Signup signupFromJson(String str) => Signup.fromJson(json.decode(str));
String signupToJson(Signup data) => json.encode(data.toJson());
class Signup {
Errors errors;
bool success;
Signup({
this.errors,
this.success,
});
factory Signup.fromJson(Map<String, dynamic> json) => Signup(
errors: Errors.fromJson(json["errors"]),
success: json["success"],
);
Map<String, dynamic> toJson() => {
"errors": errors.toJson(),
"success": success,
};
}
class Errors {
String password1;
String email1;
String name;
Errors({
this.password1,
this.email1,
this.name,
});
factory Errors.fromJson(Map<String, dynamic> json) => Errors(
password1: json["Password1"],
email1: json["Email1"],
name: json["Name"],
);
Map<String, dynamic> toJson() => {
"Password1": password1,
"Email1": email1,
"Name": name,
};
}
Here is sample JSON Data.
If login is failed due to some condition not met.
{"errors":{"Email1":"Email could not be empty",
"Password1":"Password could not be empty",
"Name":"Your name must be between 3 to 30 characters!"},
"success":false}
If login successful
{"success":false}
My JSONParse is working properly if condition not met. I mean it retuning all the errors and Success false.
But if login is successful then it is not working, by checking more I found data is coming fine from PHP.
Signup signupFromJson(String str) => Signup.fromJson(json.decode(str)); - Data is coming in str variable.
factory Signup.fromJson(Map<String, dynamic> json) => Signup(
errors: Errors.fromJson(json["errors"]), -- If error is nulll then it is not checking the success.
success: json["success"],
);
The issue coming here when errors are null then it moved out didn't goto the success section.
What am I doing wrong here?
If you get success then you will not get errors, so you have to check null aware where you are passing to error class too.
In Signup.fromJson :
errors: Errors.fromJson(json["errors"] ?? {}),
In Error Class
factory Errors.fromJson(Map<String, dynamic> json) => Errors(
password1: json["Password1"] ?? '',
email1: json["Email1"] ?? '',
name: json["Name"] ?? '',
);