You are viewing a plain text version of this content. The canonical link for it is here.
Posted to github@arrow.apache.org by "WillAyd (via GitHub)" <gi...@apache.org> on 2023/05/27 02:29:13 UTC

[GitHub] [arrow-adbc] WillAyd opened a new pull request, #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

WillAyd opened a new pull request, #714:
URL: https://github.com/apache/arrow-adbc/pull/714

   (no comment)


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] WillAyd commented on a diff in pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "WillAyd (via GitHub)" <gi...@apache.org>.
WillAyd commented on code in PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714#discussion_r1209465211


##########
c/driver/postgresql/connection.cc:
##########
@@ -146,15 +185,17 @@ class PqGetObjectsHelper {
   }
 
   AdbcStatusCode GetObjects() {
-    PqResultHelper curr_db_helper = PqResultHelper{conn_, "SELECT current_database()"};
-    if (curr_db_helper.Status() == PGRES_TUPLES_OK) {
-      assert(curr_db_helper.NumRows() == 1);
-      auto curr_iter = curr_db_helper.begin();
-      PqResultRow db_row = *curr_iter;
-      current_db_ = std::string(db_row[0].data);
-    } else {
-      return ADBC_STATUS_INTERNAL;
-    }
+    std::vector<std::string> _;

Review Comment:
   OK added the alternate constructor. The caller is still responsible for calling `Prepare` in this case even though it is overkill when there are no parameters. Could either create a separate class for statements that don't need to be prepared, or make the class more intelligent to recognize if it needs it or not. Leaving that as a follow up exercise



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] lidavidm commented on a diff in pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "lidavidm (via GitHub)" <gi...@apache.org>.
lidavidm commented on code in PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714#discussion_r1210251609


##########
c/driver/postgresql/connection.cc:
##########
@@ -72,12 +72,44 @@ class PqResultRow {
 // as expected prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,
+                 struct AdbcError* error)
+      : conn_(conn), param_values_(param_values), error_(error) {

Review Comment:
   I suppose if we need to pass integer parameters in the future or something. But it's not a worry for now.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] lidavidm merged pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "lidavidm (via GitHub)" <gi...@apache.org>.
lidavidm merged PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] WillAyd commented on a diff in pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "WillAyd (via GitHub)" <gi...@apache.org>.
WillAyd commented on code in PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714#discussion_r1207596735


##########
c/driver/postgresql/connection.cc:
##########
@@ -72,12 +72,48 @@ class PqResultRow {
 // as expected prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,
+                 struct AdbcError* error)
+      : conn_(conn), param_values_(param_values), error_(error) {
     query_ = std::string(query);
     result_ = PQexec(conn_, query_.c_str());
+    for (auto data : param_values) {
+      param_lengths_.push_back(data.length());
+    }
+  }
+
+  AdbcStatusCode Prepare() {
+    // TODO: make stmtName a unique identifier?

Review Comment:
   I noticed in the similar implementation in statement.cc that this uses an empty string. Wondering if we should generate a random string for the lifetime of the class so that there is no potential for races trying to execute prepared statements



##########
c/driver/postgresql/connection.cc:
##########
@@ -146,15 +185,17 @@ class PqGetObjectsHelper {
   }
 
   AdbcStatusCode GetObjects() {
-    PqResultHelper curr_db_helper = PqResultHelper{conn_, "SELECT current_database()"};
-    if (curr_db_helper.Status() == PGRES_TUPLES_OK) {
-      assert(curr_db_helper.NumRows() == 1);
-      auto curr_iter = curr_db_helper.begin();
-      PqResultRow db_row = *curr_iter;
-      current_db_ = std::string(db_row[0].data);
-    } else {
-      return ADBC_STATUS_INTERNAL;
-    }
+    std::vector<std::string> _;

Review Comment:
   This is pointless to add an empty vector. I'm guessing we should just add an alternate constructor, but could also go in a separate class since the Prepare/Execute interaction is overkill for something without parameters



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] lidavidm commented on a diff in pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "lidavidm (via GitHub)" <gi...@apache.org>.
lidavidm commented on code in PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714#discussion_r1210249221


##########
c/driver/postgresql/connection.cc:
##########
@@ -68,16 +69,54 @@ class PqResultRow {
 
 // Helper to manager the lifecycle of a PQResult. The query argument
 // will be evaluated as part of the constructor, with the desctructor handling cleanup
-// Caller is responsible for calling the `Status()` method to ensure results are
-// as expected prior to iterating
+// Caller must call Prepare then Execute, checking both for an OK AdbcStatusCode
+// prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  explicit PqResultHelper(PGconn* conn, const char* query, struct AdbcError* error)
+      : conn_(conn), error_(error) {
     query_ = std::string(query);
-    result_ = PQexec(conn_, query_.c_str());
+    param_values_ = {};

Review Comment:
   nit: technically unnecessary (it would get default-initialized)



##########
c/driver/postgresql/connection.cc:
##########
@@ -68,16 +69,54 @@ class PqResultRow {
 
 // Helper to manager the lifecycle of a PQResult. The query argument
 // will be evaluated as part of the constructor, with the desctructor handling cleanup
-// Caller is responsible for calling the `Status()` method to ensure results are
-// as expected prior to iterating
+// Caller must call Prepare then Execute, checking both for an OK AdbcStatusCode
+// prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  explicit PqResultHelper(PGconn* conn, const char* query, struct AdbcError* error)
+      : conn_(conn), error_(error) {
     query_ = std::string(query);
-    result_ = PQexec(conn_, query_.c_str());
+    param_values_ = {};
   }
 
-  ExecStatusType Status() { return PQresultStatus(result_); }
+  explicit PqResultHelper(PGconn* conn, const char* query,

Review Comment:
   I guess, why not just declare it as taking a `std::string` and then initializing `query_` with a move?



##########
c/driver/postgresql/connection.cc:
##########
@@ -68,16 +69,54 @@ class PqResultRow {
 
 // Helper to manager the lifecycle of a PQResult. The query argument
 // will be evaluated as part of the constructor, with the desctructor handling cleanup
-// Caller is responsible for calling the `Status()` method to ensure results are
-// as expected prior to iterating
+// Caller must call Prepare then Execute, checking both for an OK AdbcStatusCode
+// prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  explicit PqResultHelper(PGconn* conn, const char* query, struct AdbcError* error)
+      : conn_(conn), error_(error) {
     query_ = std::string(query);
-    result_ = PQexec(conn_, query_.c_str());
+    param_values_ = {};
   }
 
-  ExecStatusType Status() { return PQresultStatus(result_); }
+  explicit PqResultHelper(PGconn* conn, const char* query,
+                          std::vector<std::string> param_values, struct AdbcError* error)
+      : conn_(conn), param_values_(std::move(param_values)), error_(error) {
+    query_ = std::string(query);

Review Comment:
   nit: prefer the initializer list (so `query_(query)` above)



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] lidavidm commented on a diff in pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "lidavidm (via GitHub)" <gi...@apache.org>.
lidavidm commented on code in PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714#discussion_r1209313186


##########
c/driver/postgresql/connection.cc:
##########
@@ -72,12 +72,44 @@ class PqResultRow {
 // as expected prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,
+                 struct AdbcError* error)
+      : conn_(conn), param_values_(param_values), error_(error) {

Review Comment:
   ```suggestion
         : conn_(conn), param_values_(std::move(param_values)), error_(error) {
   ```



##########
c/driver/postgresql/connection.cc:
##########
@@ -146,15 +185,17 @@ class PqGetObjectsHelper {
   }
 
   AdbcStatusCode GetObjects() {
-    PqResultHelper curr_db_helper = PqResultHelper{conn_, "SELECT current_database()"};
-    if (curr_db_helper.Status() == PGRES_TUPLES_OK) {
-      assert(curr_db_helper.NumRows() == 1);
-      auto curr_iter = curr_db_helper.begin();
-      PqResultRow db_row = *curr_iter;
-      current_db_ = std::string(db_row[0].data);
-    } else {
-      return ADBC_STATUS_INTERNAL;
-    }
+    std::vector<std::string> _;

Review Comment:
   You can write this as `PqResultHelper helper(conn_, "QUERY", {}, error_};`



##########
c/driver/postgresql/connection.cc:
##########
@@ -72,12 +72,44 @@ class PqResultRow {
 // as expected prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,
+                 struct AdbcError* error)
+      : conn_(conn), param_values_(param_values), error_(error) {

Review Comment:
   I guess this may eventually need to be more flexible than `std::string`? We can re-evaluate when needed.
   
   (Unfortunately, R places the restriction that we can't use C++17 for the next few years. So we can't use `std::variant` to handle this, we would have to backport.)



##########
c/driver/postgresql/connection.cc:
##########
@@ -146,15 +185,17 @@ class PqGetObjectsHelper {
   }
 
   AdbcStatusCode GetObjects() {
-    PqResultHelper curr_db_helper = PqResultHelper{conn_, "SELECT current_database()"};
-    if (curr_db_helper.Status() == PGRES_TUPLES_OK) {
-      assert(curr_db_helper.NumRows() == 1);
-      auto curr_iter = curr_db_helper.begin();
-      PqResultRow db_row = *curr_iter;
-      current_db_ = std::string(db_row[0].data);
-    } else {
-      return ADBC_STATUS_INTERNAL;
-    }
+    std::vector<std::string> _;

Review Comment:
   Though yeah, just add a second constructor for `PqResultHelper`.



##########
c/driver/postgresql/connection.cc:
##########
@@ -72,12 +72,44 @@ class PqResultRow {
 // as expected prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,

Review Comment:
   ```suggestion
     explicit PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,
   ```
   
   Should've caught this earlier but might as well now



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] lidavidm commented on a diff in pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "lidavidm (via GitHub)" <gi...@apache.org>.
lidavidm commented on code in PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714#discussion_r1209311440


##########
c/driver/postgresql/connection.cc:
##########
@@ -72,12 +72,48 @@ class PqResultRow {
 // as expected prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,
+                 struct AdbcError* error)
+      : conn_(conn), param_values_(param_values), error_(error) {
     query_ = std::string(query);
     result_ = PQexec(conn_, query_.c_str());
+    for (auto data : param_values) {
+      param_lengths_.push_back(data.length());
+    }
+  }
+
+  AdbcStatusCode Prepare() {
+    // TODO: make stmtName a unique identifier?

Review Comment:
   A single connection can only handle a single query at a time anyways. Though, exposing the name may be useful if we want to somehow expose managing multiple prepared statements on a single connection. (I suppose that could be one way to allow multiple AdbcStatement instances from a single AdbcConnection, with the restriction that you can't use them concurrently, and that one result set must be completely consumed before using a different statement.)



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


[GitHub] [arrow-adbc] WillAyd commented on a diff in pull request #714: refactor(c/driver/postgresql): Use Prepared Statement in Result Helper

Posted by "WillAyd (via GitHub)" <gi...@apache.org>.
WillAyd commented on code in PR #714:
URL: https://github.com/apache/arrow-adbc/pull/714#discussion_r1209464650


##########
c/driver/postgresql/connection.cc:
##########
@@ -72,12 +72,44 @@ class PqResultRow {
 // as expected prior to iterating
 class PqResultHelper {
  public:
-  PqResultHelper(PGconn* conn, const char* query) : conn_(conn) {
+  PqResultHelper(PGconn* conn, const char* query, std::vector<std::string> param_values,
+                 struct AdbcError* error)
+      : conn_(conn), param_values_(param_values), error_(error) {

Review Comment:
   You are referring to the vector elements? What would you have in mind being contained besides string?



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@arrow.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org