diff --git a/swoole_postgresql_coro.cc b/swoole_postgresql_coro.cc
index 8395055..5d1f54c 100644
--- a/swoole_postgresql_coro.cc
+++ b/swoole_postgresql_coro.cc
@@ -228,12 +228,36 @@ void swoole_postgresql_init(int module_number)
 
     le_result = zend_register_list_destructors_ex(_free_result, NULL, "pgsql result", module_number);
     zend_declare_property_null(swoole_postgresql_coro_ce, ZEND_STRL("error"), ZEND_ACC_PUBLIC);
+    zend_declare_property_null(swoole_postgresql_coro_ce, ZEND_STRL("errorInfo"), ZEND_ACC_PUBLIC);
 
     SW_REGISTER_LONG_CONSTANT("SW_PGSQL_ASSOC", PGSQL_ASSOC);
     SW_REGISTER_LONG_CONSTANT("SW_PGSQL_NUM", PGSQL_NUM);
     SW_REGISTER_LONG_CONSTANT("SW_PGSQL_BOTH", PGSQL_BOTH);
 }
 
+static void resetError(pg_object *object)
+{
+    zend_update_property_null(swoole_postgresql_coro_ce, object->object, ZEND_STRL("error"));
+    zend_update_property_null(swoole_postgresql_coro_ce, object->object, ZEND_STRL("errorInfo"));
+}
+
+static void setErrorFromResult(pg_object *object, PGresult *pgsql_result)
+{
+    ExecStatusType status = PQresultStatus(pgsql_result);
+    char *err_msg = PQerrorMessage(object->conn);
+    char *err_code = PQresultErrorField(pgsql_result, PG_DIAG_SQLSTATE);
+
+    zval errorInfo;
+    array_init_size(&errorInfo, 3);
+
+    add_index_string(&errorInfo, 0, err_code);
+    add_index_long(&errorInfo, 1, status);
+    add_index_string(&errorInfo, 2, err_msg);
+
+    zend_update_property_string(swoole_postgresql_coro_ce, object->object, "error", 5, err_msg);
+    zend_update_property(swoole_postgresql_coro_ce, object->object, "errorInfo", 9, &errorInfo);
+}
+
 static PHP_METHOD(swoole_postgresql_coro, __construct) { }
 
 static PHP_METHOD(swoole_postgresql_coro, connect)
@@ -427,7 +451,7 @@ static void connect_callback(pg_object *object, swReactor *reactor, swEvent *eve
 
     if (object->connected == 1)
     {
-        zend_update_property_null(swoole_postgresql_coro_ce, object->object, ZEND_STRL("error"));
+        resetError(object);
     }
 
     int ret = PHPCoroutine::resume_m(context, &return_value, retval);
@@ -537,7 +561,9 @@ static int meta_data_result_parse(pg_object *object)
 
     }
     php_coro_context *context = php_swoole_postgresql_coro_get_context(object->object);
-    zend_update_property_null(swoole_postgresql_coro_ce, object->object, "error", 5);
+
+    setErrorFromResult(object, pg_result);
+
     int ret = PHPCoroutine::resume_m(context, &return_value, retval);
     if (ret == SW_CORO_ERR_END && retval)
     {
@@ -554,7 +580,6 @@ static int query_result_parse(pg_object *object)
     ExecStatusType status;
 
     int error = 0;
-    char *err_msg;
     int ret, res;
     zval *retval = NULL;
     zval return_value;
@@ -569,11 +594,12 @@ static int query_result_parse(pg_object *object)
     case PGRES_BAD_RESPONSE:
     case PGRES_NONFATAL_ERROR:
     case PGRES_FATAL_ERROR:
-        err_msg = PQerrorMessage(object->conn);
         PQclear(pgsql_result);
         ZVAL_FALSE(&return_value);
         swoole_event_del(object->fd);
-        zend_update_property_string(swoole_postgresql_coro_ce, object->object, "error", 5, err_msg);
+
+        setErrorFromResult(object, pgsql_result);
+
         ret = PHPCoroutine::resume_m(context, &return_value, retval);
         if (ret == SW_CORO_ERR_END && retval)
         {
@@ -588,7 +614,9 @@ static int query_result_parse(pg_object *object)
         res = PQflush(object->conn);
         swoole_event_del(object->fd);
         ZVAL_RES(&return_value, zend_register_resource(object, le_result));
-        zend_update_property_null(swoole_postgresql_coro_ce, object->object, "error", 5);
+
+        resetError(object);
+
         ret = PHPCoroutine::resume_m(context, &return_value, retval);
         if (ret == SW_CORO_ERR_END && retval)
         {
@@ -615,10 +643,25 @@ static  int prepare_result_parse(pg_object *object)
     zval return_value;
     php_coro_context *context = php_swoole_postgresql_coro_get_context(object->object);
 
+    PGresult *pgsql_result = PQgetResult(object->conn);
+    ExecStatusType status = PQresultStatus(pgsql_result);
+
+    if (status != PGRES_COMMAND_OK) {
+        setErrorFromResult(object, pgsql_result);
+
+        ZVAL_FALSE(&return_value);
+    } else {
+        resetError(object);
+
+        ZVAL_TRUE(&return_value);
+    }
+
+    PQclear(pgsql_result);
+
     /* Wait to finish sending buffer */
     //res = PQflush(object->conn);
-    ZVAL_TRUE(&return_value);
     swoole_event_del(object->fd);
+
     ret = PHPCoroutine::resume_m(context, &return_value, retval);
 
     if (ret == SW_CORO_END && retval)
@@ -1338,6 +1381,7 @@ static int swoole_pgsql_coro_onError(swReactor *reactor, swEvent *event)
     ZVAL_FALSE(result);
 
     php_coro_context *context = php_swoole_postgresql_coro_get_context(zobject);
+
     zend_update_property_string(swoole_postgresql_coro_ce, zobject, "error", 5, "onerror");
     int ret = PHPCoroutine::resume_m(context, result, retval);
     zval_ptr_dtor(result);