0

I am trying to parse this API response below and saving the response in a sqlite database. But getting this error message in the saving process.. And I think it happens because I cant properly create this model file. Can't figure it out how to implement 2 class within the "Map<String, Object?> toJson()" section.

Error:

 Invalid argument [{id: 1, name: İstanbul Ayasofya Müzesi, session_time: 12, distId: AYS, photo: https://api.thevoiceofmuseums.com/storage/contents/museums/1.jpeg, address: null, lat: null, long: null, sectionId: AYS01, email: null, updated_at: 2019-07-20T13:42:53.000, created_at: 2019-06-20T02:27:21.000}, {id: 2, name: İstanbul Topkapı Sarayı Müzesi, session_time: 12, distId: TPK01, photo: https://api.thevoiceofmuseums.com/storage/contents/museums/2.jpeg, address: null, lat: null, long: null, sectionId: TPK01, email: null, updated_at: 2019-07-20T13:44:12.000, created_at: 2019-06-21T14:11:43.000}, {id: 3, name: İstanbul Topkapı Sarayı - Harem Dairesi, session_time: 12, distId: TPK02, photo: https://api.thevoiceofmuseums.com/storage/contents/museums/3.jpeg, address: null, lat: null, long: null, sectionId: TPK02, email: null, updated_at: 2019-07-20T13:44:22.000, created_at: 2019-06-21T14:12:48.000}, {id: 4, name: İstanbul Topkapı Sarayı Müzesi ve Harem Dairesi, session_time: 12, di
E/flutter ( 7093): [ERROR:flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: DatabaseException(java.util.HashMap cannot be cast to java.lang.Integer) sql 'INSERT INTO museums_list.db (data) VALUES (?)' args

Table View screenshot: enter image description here

Here is my endpoint response:

{
    "data": [
        {
            "id": 1,
            "name": "İstanbul Ayasofya Müzesi",
            "session_time": 12,
            "distId": "AYS",
            "photo": "https://api.thevoiceofmuseums.com/storage/contents/museums/1.jpeg",
            "address": "null",
            "lat": "null",
            "long": "null",
            "sectionId": "AYS01",
            "email": "null",
            "updated_at": "2019-07-20 13:42:53",
            "created_at": "2019-06-20 02:27:21"
        },
        {
            "id": 2,
            "name": "İstanbul Topkapı Sarayı Müzesi",
            "session_time": 12,
            "distId": "TPK01",
            "photo": "https://api.thevoiceofmuseums.com/storage/contents/museums/2.jpeg",
            "address": "null",
            "lat": "null",
            "long": "null",
            "sectionId": "TPK01",
            "email": "null",
            "updated_at": "2019-07-20 13:44:12",
            "created_at": "2019-06-21 14:11:43"
        },
        {
            "id": 3,
            "name": "İstanbul Topkapı Sarayı - Harem Dairesi",
            "session_time": 12,
            "distId": "TPK02",
            "photo": "https://api.thevoiceofmuseums.com/storage/contents/museums/3.jpeg",
            "address": "null",
            "lat": "null",
            "long": "null",
            "sectionId": "TPK02",
            "email": "null",
            "updated_at": "2019-07-20 13:44:22",
            "created_at": "2019-06-21 14:12:48"
        }
    ]
}

model file:

final String tableMuseums = 'MuseumsListTable';

// column names for database
class MuseumsFields {
  static const String MUSEUM_ID = 'id';
  static const String MUSEUM_NAME = 'name';
  static const String SESSION_TIME = 'session_time';
  static const String MUSEUM_DIST_ID = 'distId';
  static const String MUSEUM_PHOTO = 'photo';
  static const String MUSEUM_ADDRESS = 'address';
  static const String LAT = 'lat';
  static const String LONG = 'long';
  static const String MUSEUM_SECTION_ID = 'sectionId';
  static const String EMAIL = 'email';
  static const String UPDATED_AT = 'updated_at';
  static const String CREATED_AT = 'created_at';
}

class MuseumsList {
  List<Data>? data;

  MuseumsList({this.data});

  MuseumsList.fromJson(Map<String, dynamic> json) {
    if (json['data'] != null) {
      data = <Data>[];
      json['data'].forEach((v) {
        data!.add(new Data.fromJson(v));
      });
    }
  }

  Map<String, dynamic> toJson() {
    print("TOJSON");
    final Map<String, dynamic> data = new Map<String, dynamic>();
    if (this.data != null) {
      data['data'] = this.data!.map((v) => v.toJson()).toList();
    }
    return data;
  }
}

class Data {
  int? id;
  String? name;
  int? sessionTime;
  String? distId;
  String? photo;
  String? address;
  String? lat;
  String? long;
  String? sectionId;
  String? email;
  DateTime? updatedAt;
  DateTime? createdAt;

  Data({
    this.id,
    this.name,
    this.sessionTime,
    this.distId,
    this.photo,
    this.address,
    this.lat,
    this.long,
    this.sectionId,
    this.email,
    this.updatedAt,
    this.createdAt,
  });


  Data.fromJson(Map<String, dynamic> json) {
    id = json['id'];
    name = json['name'];
    sessionTime = json['session_time'];
    distId = json['distId'];
    photo = json['photo'];
    address = json['address'];
    lat = json['lat'];
    long = json['long'];
    sectionId = json['sectionId'];
    email = json['email'];
    updatedAt = DateTime.parse(json["updated_at"]);
    createdAt = DateTime.parse(json["created_at"]);
  }

  Map<String, Object?> toJson() => {
        MuseumsFields.MUSEUM_ID: id,
        MuseumsFields.MUSEUM_NAME: name,
        MuseumsFields.SESSION_TIME: sessionTime,
        MuseumsFields.MUSEUM_DIST_ID: distId,
        MuseumsFields.MUSEUM_PHOTO: photo,
        MuseumsFields.MUSEUM_ADDRESS: address,
        MuseumsFields.LAT: lat,
        MuseumsFields.LONG: long,
        MuseumsFields.MUSEUM_SECTION_ID: sectionId,
        MuseumsFields.EMAIL: email,
        MuseumsFields.UPDATED_AT: updatedAt!.toIso8601String(),
        MuseumsFields.CREATED_AT: createdAt!.toIso8601String(),
      };
}

database provider file:

import 'dart:io';
import 'package:path/path.dart';
import 'package:the_vom/models/museums_list_model.dart';

import 'package:path_provider/path_provider.dart';
import 'package:sqflite/sqflite.dart';

class DBProvider {
  static final DBProvider instance = DBProvider._init();
  static Database? _database;
  DBProvider._init();

  Future<Database?> get database async {
    if (_database != null) return _database!;

    _database = await _initDB('museums.db');
    return _database;
  }

  Future<Database> _initDB(String filePath) async {
    // final dbPath = await getDatabasesPath();
    Directory documentsDirectory = await getApplicationDocumentsDirectory();
    String path = join(documentsDirectory.path, filePath);
    print('database location: $path');

    return await openDatabase(path, version: 1, onCreate: _createDB);
  }

  Future _createDB(Database db, int version) async {
    final idType = 'INTEGER PRIMARY KEY';
    final textType = 'TEXT';
    final intType = 'INTEGER';

    await db.execute('''
    CREATE TABLE $tableMuseums (
    ${MuseumsFields.MUSEUM_ID} $idType,
    ${MuseumsFields.MUSEUM_NAME} $textType,
    ${MuseumsFields.SESSION_TIME} $intType,
    ${MuseumsFields.MUSEUM_DIST_ID} $textType,
    ${MuseumsFields.MUSEUM_PHOTO} $textType,
    ${MuseumsFields.MUSEUM_ADDRESS} $textType,
    ${MuseumsFields.LAT} $textType,
    ${MuseumsFields.LONG} $textType,
    ${MuseumsFields.MUSEUM_SECTION_ID} $textType,
    ${MuseumsFields.EMAIL} $textType,
    ${MuseumsFields.UPDATED_AT} $textType,
    ${MuseumsFields.CREATED_AT} $textType
    )
     ''');

    print("database table is created.");
  }

  Future<MuseumsList> create(MuseumsList museum) async {
    print("inside of create function in db_provider.dart");
    final db = await instance.database;

    final json = museum.toJson();
    print("+++++++++++");
    print(json.values);
    print("+++++++++++");
    // // COLUMN NAMES
    // final columns =
    //     '${MuseumsFields.MUSEUM_ID}, ${MuseumsFields.MUSEUM_NAME},  ${MuseumsFields.SESSION_TIME},  ${MuseumsFields.MUSEUM_DIST_ID},  ${MuseumsFields.MUSEUM_PHOTO},  ${MuseumsFields.MUSEUM_ADDRESS},  ${MuseumsFields.LAT},  ${MuseumsFields.LONG},  ${MuseumsFields.MUSEUM_SECTION_ID},  ${MuseumsFields.EMAIL},  ${MuseumsFields.UPDATED_AT},  ${MuseumsFields.CREATED_AT}';
    // // ROWS
    // final values =
    //     '${json[MuseumsFields.MUSEUM_ID]}, ${json[MuseumsFields.MUSEUM_NAME]}, ${json[MuseumsFields.SESSION_TIME]}, ${json[MuseumsFields.MUSEUM_DIST_ID]}, ${json[MuseumsFields.MUSEUM_PHOTO]}, ${json[MuseumsFields.MUSEUM_ADDRESS]}, ${json[MuseumsFields.LAT]}, ${json[MuseumsFields.LONG]}, ${json[MuseumsFields.MUSEUM_SECTION_ID]}, ${json[MuseumsFields.EMAIL]}, ${json[MuseumsFields.UPDATED_AT]}, ${json[MuseumsFields.CREATED_AT]}';
    //
    // final y = await db!
    //     .rawInsert('INSERT INTO $tableMuseums ($columns) VALUES ($values)');

    final x =
        await db!.insert(tableMuseums, museum.toJson()); //convert to a map.

    print("museums are saved in the database.");

    return museum;
  }

  Future close() async {
    final db = await instance.database;

    db!.close();
  }
}

service file: I pass my decoded response.body to db provider here as you can see below.

class MuseumsService {
  Future getMuseums() async {
    print("Future getMuseums");
    try {
      // headers of the post request
      final _headers = {
        //todo bearer token, remove the hardcoded one.
        'Authorization': _hardCodedBearerToken,
        'Content-Type': 'application/x-www-form-urlencoded',
      };

      // body of the post request
      // final _body = '';

      // sending post request
      http.Response response = await http.post(
        loginAPIURL,
        headers: _headers,
        // body: _body,
      );
      print("getMuseums Request Sent!");

      //get response from endpoint
      if (response.statusCode == 200) {
        print('$loginAPIURL Endpoint Response: response.body');
        print(response.body);

        MuseumsList museums =
            await MuseumsList.fromJson(jsonDecode(response.body));

        // print(museums.data![0].name);

        DBProvider.instance.create(museums); //-> **** 
      }
    } catch (e) {
      print(e);
      return throw Exception("MUSEUMSLIST ALINAMADI");
    }
  }
}

1 Answer 1

1

You are trying to insert the result of MuseumsList.toJson instead of Data.toJson

Try with something like this:

Future<MuseumsList> create(MuseumsList museums) async {
  print("inside of create function in db_provider.dart");
  final db = await instance.database;

  // {'data': [...]}
  final jsons = museums.toJson();
  if (jsons['data'] != null) {
    batch = db!.batch();

    jsons['data'].forEach((museum) {
      batch.insert(tableMuseums, museum);
    });

    await batch.commit();
  }

  print("museums are saved in the database.");

  return museums;
}
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.