2014-02-26 49 views
2

我试图在Dart中使用sqljocky代码sql访问数据库。由于我想用我的数据库处理程序返回的结果进行一些计算,该方法返回一个Future。sqljocky查询没有方法'然后'(飞镖数据库访问)

但是当我尝试运行它,我得到了以下错误:

Uncaught Error: The null object does not have a method 'then'` 

我已经跑了调试,发现这个错误提高对:

db.query('select * from user where email="$email"').then(...) 

但catchError子句不会触发。

我的处理方法是:

// db is a ConnectionPool 
Future<Map<String,String>> queryUser(String email){ 
    print(email); 
    db.query('select * from user where email="${email}"').then((result) { // here raise the error 
     Map<String,String> results = new Map<String,String>(); 
     result.forEach((row){ 
      results['status'] = '200'; 
      results['ID'] = row[0]; 
      results['Image'] = row[1]; 
      results['Name'] = row[2]; 
      results['Email'] = row[3]; 
      results['Password'] = row[4]; 
     }); 
     return results; 
    }).catchError((error){ 
     Map<String,String> results = new Map<String,String>(); 
     results['status'] = '500'; 
     return results; 
    }); 
} 

并调用此处理程序是方法:

List getUser(String email) { 
    Future<Map<String,String>> result = dbhandler.queryUser(email); 
    result.then((Map<String,String> result) { 
    String statuscode = result['status']; 
    result.remove('status'); 
    String json = JSON.encode(result); 
    List pair = new List(); 
    pair.add(statuscode); 
    pair.add(json); 
    return pair; 
}); 

如果我直接在phpMyAdmin运行查询,它返回正确的数据,所以它是正确的。

有人可以给我一个关于如何解决它的提示吗?

回答

1

queryUser()方法将始终返回null,因为没有返回语句。在Dart的下一个版本中,会有一个静态的提示警告,但目前没有。

也许下面的代码是你的意思。请注意db.query()之前的初始返回语句以及额外的result.toList()调用。我没有测试过,所以可能有一两个错字。

Future<Map<String,String>> queryUser(String email){ 
    print(email); 
    return db.query('select * from user where email="${email}"') 
     .then((result) => result.toList()) 
     .then((rows) { 
     var row = rows.single; 
     Map<String,String> results = new Map<String,String>(); 
     results['status'] = '200'; 
     results['ID'] = row[0]; 
     results['Image'] = row[1]; 
     results['Name'] = row[2]; 
     results['Email'] = row[3]; 
     results['Password'] = row[4]; 
     return results; 
     }).catchError((error){ 
     Map<String,String> results = new Map<String,String>(); 
     results['status'] = '500'; 
     return results; 
     }); 
} 

您也可以让这个有点可爱使用地图文字:

Future<Map<String,String>> queryUser(String email){ 
    return db.query('select * from user where email="${email}"') 
     .then((result) => result.toList()) 
     .then((rows) => <String, String> { 
     'status': '200', 
     'ID': rows.single[0], 
     'Image': rows.single[1], 
     'Name': rows.single[2], 
     'Email': rows.single[3], 
     'Password': rows.single[4] }) 
     .catchError((error) => <String, String> {'status': '500'}); 
} 
+0

由于格雷格,我刚刚解决了它,我会写我的答案,也可能是别人有帮助的。 –

0

最后我发现用完成者控制未来对象的答案,但真正的问题是正如Greg Lowe所说,我的方法不会返回任何结果,因为它们在条款之前结束。

使用完成者,我做了我的查询方法为:

Future<Map<String,String>> queryUser(String email){ 
    Completer c = new Completer(); 
    db.query('select * from user where email="$email"').then((result) { 
     Map<String,String> results = new Map<String,String>(); 
     result.forEach((row){ 
      results['status'] = '200'; 
      results['ID'] = row[0].toString(); 
      results['Image'] = row[1]; 
      results['Name'] = row[2]; 
      results['Email'] = row[3]; 
      results['Password'] = row[4]; 
     }).then((onValue){ 
      c.complete(results); 
     }); 
    }).catchError((error){ 
     Map<String,String> results = new Map<String,String>(); 
     results['status'] = '500'; 
     c.completeError((e) => print("error en queryUser")); 
    }); 
return c.future; 
} 

使用的foreach方法时,我也解决了一个错误,起初我以为它返回任何结果,但在那之后,我注意到它返回一个Future,所以我添加了一个then子句。

而且我的getUser方法:

Future<List> getUser(String email) { 
    Completer c = new Completer(); 
    Future<Map<String,String>> result = dbhandler.queryUser(email); 
    result.then((Map<String,String> result) { 
     String statuscode = result['status']; 
     result.remove('status'); 
     String json = JSON.encode(result); 
     List pair = new List(); 
     pair.add(statuscode); 
     pair.add(json); 
     c.complete(pair); 
    }); 
    return c.future; 
} 

这些变化后,一切正常,右

+0

该解决方案看起来比@GregLowe更糟糕。你为什么不按照他所建议的方式行事?您认为您的解决方案的优势是什么?添加'return'(如建议)与添加'Completer'代码具有相同的效果。 –

+0

没有什么重要的理由可以走我的路,但是,因为我是Dart的新成员,来自Java,所以我的方式看起来比@GregLowe提供的方式更容易阅读,所以我想也写在这里所以它可以在将来帮助任何人。 –

+0

没有问题,我只是想知道。 –