Add columnNames to LimboResultSet

This commit is contained in:
김선우
2025-02-02 21:14:30 +09:00
parent 098da0794f
commit f6919f028e
4 changed files with 74 additions and 2 deletions

View File

@@ -2,7 +2,7 @@ use crate::errors::Result;
use crate::errors::{LimboError, LIMBO_ETC};
use crate::limbo_connection::LimboConnection;
use crate::utils::set_err_msg_and_throw_exception;
use jni::objects::{JObject, JValue};
use jni::objects::{JObject, JObjectArray, JValue};
use jni::sys::jlong;
use jni::JNIEnv;
use limbo_core::{Statement, StepResult};
@@ -125,6 +125,27 @@ fn row_to_obj_array<'local>(
Ok(obj_array.into())
}
#[no_mangle]
pub extern "system" fn Java_org_github_tursodatabase_core_LimboStatement_columnNames<'local>(
mut env: JNIEnv<'local>,
_obj: JObject<'local>,
stmt_ptr: jlong,
) -> JObject<'local> {
let stmt = to_limbo_statement(stmt_ptr).unwrap();
let columns = stmt.stmt.columns();
let obj_arr: JObjectArray = env
.new_object_array(columns.len() as i32, "java/lang/String", JObject::null())
.unwrap();
for (i, value) in columns.iter().enumerate() {
let str = env.new_string(value).unwrap();
env.set_object_array_element(&obj_arr, i as i32, str)
.unwrap();
}
obj_arr.into()
}
/// Converts an optional `JObject` into Java's `LimboStepResult`.
///
/// This function takes an optional `JObject` and converts it into a Java object

View File

@@ -19,6 +19,8 @@ public class LimboResultSet {
private final LimboStatement statement;
// Name of the columns
private String[] columnNames = new String[0];
// Whether the result set does not have any rows.
private boolean isEmptyResultSet = false;
// If the result set is open. Doesn't mean it has results.
@@ -136,6 +138,14 @@ public class LimboResultSet {
return resultSet[columnIndex - 1];
}
public String[] getColumnNames() {
return this.columnNames;
}
public void setColumnNames(String[] columnNames) {
this.columnNames = columnNames;
}
@Override
public String toString() {
return "LimboResultSet{"

View File

@@ -89,6 +89,23 @@ public class LimboStatement {
private native void _close(long statementPointer);
/**
* Initializes the column metadata, such as the names of the columns. Since {@link LimboStatement}
* can only have a single {@link LimboResultSet}, it is appropriate to place the initialization of
* column metadata here.
*
* @throws SQLException if a database access error occurs while retrieving column names
*/
public void initializeColumnMetadata() throws SQLException {
final String[] columnNames = this.columnNames(statementPointer);
if (columnNames != null) {
this.resultSet.setColumnNames(columnNames);
}
}
@Nullable
private native String[] columnNames(long statementPointer) throws SQLException;
/**
* Checks if the statement is closed.
*

View File

@@ -1,6 +1,8 @@
package org.github.tursodatabase.core;
import static org.junit.jupiter.api.Assertions.*;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import java.util.Properties;
import org.github.tursodatabase.TestUtils;
@@ -28,4 +30,26 @@ class LimboStatementTest {
assertTrue(stmt.isClosed());
assertFalse(stmt.getResultSet().isOpen());
}
@Test
void test_initializeColumnMetadata() throws Exception {
runSql("CREATE TABLE users (name TEXT, age INT, country TEXT);");
runSql("INSERT INTO users VALUES ('seonwoo', 30, 'KR');");
final LimboStatement stmt = connection.prepare("SELECT * FROM users");
stmt.initializeColumnMetadata();
final LimboResultSet rs = stmt.getResultSet();
final String[] columnNames = rs.getColumnNames();
assertEquals(columnNames[0], "name");
assertEquals(columnNames[1], "age");
assertEquals(columnNames[2], "country");
}
private void runSql(String sql) throws Exception {
LimboStatement stmt = connection.prepare(sql);
while (stmt.execute()) {
stmt.execute();
}
}
}