This is an automated email from the ASF dual-hosted git repository.
JingsongLi pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/paimon-vector-index.git
The following commit(s) were added to refs/heads/main by this push:
new e97896e Expose metadata types as strings in bindings (#34)
e97896e is described below
commit e97896e25c76c2998d745db9045dc41a372ba419
Author: Jingsong Lee <[email protected]>
AuthorDate: Thu Jun 11 09:34:18 2026 +0800
Expose metadata types as strings in bindings (#34)
---
core/src/distance.rs | 15 ++++++++
.../org/apache/paimon/index/vector/IndexType.java | 44 ----------------------
.../org/apache/paimon/index/vector/Metric.java | 34 -----------------
.../paimon/index/vector/VectorIndexMetadata.java | 30 +++++++--------
.../paimon/index/vector/VectorIndexReader.java | 2 +-
.../index/vector/VectorIndexJavaApiTest.java | 23 ++---------
jni/src/lib.rs | 14 +++++--
python/src/lib.rs | 21 ++---------
8 files changed, 49 insertions(+), 134 deletions(-)
diff --git a/core/src/distance.rs b/core/src/distance.rs
index 3d2ec90..e14381c 100644
--- a/core/src/distance.rs
+++ b/core/src/distance.rs
@@ -32,6 +32,14 @@ impl MetricType {
_ => None,
}
}
+
+ pub fn as_str(self) -> &'static str {
+ match self {
+ MetricType::L2 => "l2",
+ MetricType::InnerProduct => "inner_product",
+ MetricType::Cosine => "cosine",
+ }
+ }
}
/// Squared L2 distance between two vectors.
@@ -602,6 +610,13 @@ mod tests {
assert!((fvec_distance(&a, &b, MetricType::Cosine) - 1.0).abs() <
1e-6);
}
+ #[test]
+ fn test_metric_type_as_str() {
+ assert_eq!(MetricType::L2.as_str(), "l2");
+ assert_eq!(MetricType::InnerProduct.as_str(), "inner_product");
+ assert_eq!(MetricType::Cosine.as_str(), "cosine");
+ }
+
#[test]
fn test_normalize() {
let mut v = [3.0, 4.0];
diff --git a/java/src/main/java/org/apache/paimon/index/vector/IndexType.java
b/java/src/main/java/org/apache/paimon/index/vector/IndexType.java
deleted file mode 100644
index 0c801c0..0000000
--- a/java/src/main/java/org/apache/paimon/index/vector/IndexType.java
+++ /dev/null
@@ -1,44 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements. See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership. The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License. You may obtain a copy of the License at
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied. See the License for the
-// specific language governing permissions and limitations
-// under the License.
-
-package org.apache.paimon.index.vector;
-
-public enum IndexType {
- IVF_FLAT(0),
- IVF_PQ(1),
- IVF_HNSW_FLAT(2),
- IVF_HNSW_SQ(3);
-
- private final int code;
-
- IndexType(int code) {
- this.code = code;
- }
-
- public int code() {
- return code;
- }
-
- static IndexType fromCode(int code) {
- for (IndexType type : values()) {
- if (type.code == code) {
- return type;
- }
- }
- throw new IllegalArgumentException("unknown index type code: " + code);
- }
-}
diff --git a/java/src/main/java/org/apache/paimon/index/vector/Metric.java
b/java/src/main/java/org/apache/paimon/index/vector/Metric.java
deleted file mode 100644
index f9db885..0000000
--- a/java/src/main/java/org/apache/paimon/index/vector/Metric.java
+++ /dev/null
@@ -1,34 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements. See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership. The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License. You may obtain a copy of the License at
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied. See the License for the
-// specific language governing permissions and limitations
-// under the License.
-
-package org.apache.paimon.index.vector;
-
-public enum Metric {
- L2(0),
- INNER_PRODUCT(1),
- COSINE(2);
-
- private final int code;
-
- Metric(int code) {
- this.code = code;
- }
-
- public int code() {
- return code;
- }
-}
diff --git
a/java/src/main/java/org/apache/paimon/index/vector/VectorIndexMetadata.java
b/java/src/main/java/org/apache/paimon/index/vector/VectorIndexMetadata.java
index 2154299..48c49e0 100644
--- a/java/src/main/java/org/apache/paimon/index/vector/VectorIndexMetadata.java
+++ b/java/src/main/java/org/apache/paimon/index/vector/VectorIndexMetadata.java
@@ -19,10 +19,10 @@ package org.apache.paimon.index.vector;
public final class VectorIndexMetadata {
- private final IndexType indexType;
+ private final String indexType;
private final int dimension;
private final int nlist;
- private final Metric metric;
+ private final String metric;
private final long totalVectors;
private final int pqM;
private final int hnswM;
@@ -30,19 +30,25 @@ public final class VectorIndexMetadata {
private final int hnswMaxLevel;
public VectorIndexMetadata(
- int indexType,
+ String indexType,
int dimension,
int nlist,
- int metric,
+ String metric,
long totalVectors,
int pqM,
int hnswM,
int efConstruction,
int maxLevel) {
- this.indexType = IndexType.fromCode(indexType);
+ if (indexType == null) {
+ throw new NullPointerException("indexType");
+ }
+ if (metric == null) {
+ throw new NullPointerException("metric");
+ }
+ this.indexType = indexType;
this.dimension = dimension;
this.nlist = nlist;
- this.metric = metricFromCode(metric);
+ this.metric = metric;
this.totalVectors = totalVectors;
this.pqM = pqM;
this.hnswM = hnswM;
@@ -50,7 +56,7 @@ public final class VectorIndexMetadata {
this.hnswMaxLevel = maxLevel;
}
- public IndexType indexType() {
+ public String indexType() {
return indexType;
}
@@ -62,7 +68,7 @@ public final class VectorIndexMetadata {
return nlist;
}
- public Metric metric() {
+ public String metric() {
return metric;
}
@@ -86,12 +92,4 @@ public final class VectorIndexMetadata {
return hnswMaxLevel;
}
- private static Metric metricFromCode(int code) {
- for (Metric metric : Metric.values()) {
- if (metric.code() == code) {
- return metric;
- }
- }
- throw new IllegalArgumentException("unknown metric code: " + code);
- }
}
diff --git
a/java/src/main/java/org/apache/paimon/index/vector/VectorIndexReader.java
b/java/src/main/java/org/apache/paimon/index/vector/VectorIndexReader.java
index 3a27321..34eefc7 100644
--- a/java/src/main/java/org/apache/paimon/index/vector/VectorIndexReader.java
+++ b/java/src/main/java/org/apache/paimon/index/vector/VectorIndexReader.java
@@ -54,7 +54,7 @@ public final class VectorIndexReader implements AutoCloseable
{
}
}
- public IndexType indexType() {
+ public String indexType() {
return metadata().indexType();
}
diff --git
a/java/src/test/java/org/apache/paimon/index/vector/VectorIndexJavaApiTest.java
b/java/src/test/java/org/apache/paimon/index/vector/VectorIndexJavaApiTest.java
index 4d2cc80..2cf1a05 100644
---
a/java/src/test/java/org/apache/paimon/index/vector/VectorIndexJavaApiTest.java
+++
b/java/src/test/java/org/apache/paimon/index/vector/VectorIndexJavaApiTest.java
@@ -24,8 +24,6 @@ import java.util.Map;
public class VectorIndexJavaApiTest {
public static void main(String[] args) {
- testMetricCodes();
- testIndexTypeCodes();
testSingleResultCopiesArrays();
testBatchResultCopiesArraysAndSlicesRows();
testMetadata();
@@ -34,19 +32,6 @@ public class VectorIndexJavaApiTest {
testReaderAndWriterApiCompile();
}
- private static void testMetricCodes() {
- assertEquals(0, Metric.L2.code());
- assertEquals(1, Metric.INNER_PRODUCT.code());
- assertEquals(2, Metric.COSINE.code());
- }
-
- private static void testIndexTypeCodes() {
- assertEquals(0, IndexType.IVF_FLAT.code());
- assertEquals(1, IndexType.IVF_PQ.code());
- assertEquals(2, IndexType.IVF_HNSW_FLAT.code());
- assertEquals(3, IndexType.IVF_HNSW_SQ.code());
- }
-
private static void testSingleResultCopiesArrays() {
long[] ids = new long[] {11L, 7L};
float[] distances = new float[] {0.1f, 0.3f};
@@ -95,19 +80,19 @@ public class VectorIndexJavaApiTest {
private static void testMetadata() {
VectorIndexMetadata metadata =
new VectorIndexMetadata(
- IndexType.IVF_HNSW_FLAT.code(),
+ "ivf_hnsw_flat",
16,
4,
- Metric.COSINE.code(),
+ "cosine",
123L,
0,
20,
150,
7);
- assertEquals(IndexType.IVF_HNSW_FLAT, metadata.indexType());
+ assertEquals("ivf_hnsw_flat", metadata.indexType());
assertEquals(16, metadata.dimension());
assertEquals(4, metadata.nlist());
- assertEquals(Metric.COSINE, metadata.metric());
+ assertEquals("cosine", metadata.metric());
assertEquals(123L, metadata.totalVectors());
assertEquals(20, metadata.hnswM());
assertEquals(150, metadata.hnswEfConstruction());
diff --git a/jni/src/lib.rs b/jni/src/lib.rs
index cc18f92..dd4aa8a 100644
--- a/jni/src/lib.rs
+++ b/jni/src/lib.rs
@@ -266,18 +266,26 @@ fn build_metadata(env: &mut JNIEnv, metadata:
VectorIndexMetadata) -> jobject {
Ok(c) => c,
Err(e) => return throw_and_return(env, &format!("find_class: {}", e)),
};
+ let index_type = match env.new_string(metadata.index_type.as_str()) {
+ Ok(value) => JObject::from(value),
+ Err(e) => return throw_and_return(env,
&format!("new_string(index_type): {}", e)),
+ };
+ let metric = match env.new_string(metadata.metric.as_str()) {
+ Ok(value) => JObject::from(value),
+ Err(e) => return throw_and_return(env, &format!("new_string(metric):
{}", e)),
+ };
let (hnsw_m, ef_construction, max_level) = metadata
.hnsw
.map(|h| (h.m as jint, h.ef_construction as jint, h.max_level as jint))
.unwrap_or((0, 0, 0));
let result = match env.new_object(
class,
- "(IIIIJIIII)V",
+ "(Ljava/lang/String;IILjava/lang/String;JIIII)V",
&[
- JValue::Int(metadata.index_type as jint),
+ JValue::Object(&index_type),
JValue::Int(metadata.dimension as jint),
JValue::Int(metadata.nlist as jint),
- JValue::Int(metadata.metric as jint),
+ JValue::Object(&metric),
JValue::Long(metadata.total_vectors),
JValue::Int(metadata.pq_m.unwrap_or(0) as jint),
JValue::Int(hnsw_m),
diff --git a/python/src/lib.rs b/python/src/lib.rs
index 901bcc5..8a812ab 100644
--- a/python/src/lib.rs
+++ b/python/src/lib.rs
@@ -20,9 +20,8 @@
use numpy::{
PyArray, PyArray1, PyArray2, PyReadonlyArray1, PyReadonlyArray2,
PyUntypedArrayMethods,
};
-use paimon_vindex_core::distance::MetricType;
use paimon_vindex_core::index::{
- IndexType, VectorIndexConfig, VectorIndexReader as CoreVectorIndexReader,
+ VectorIndexConfig, VectorIndexReader as CoreVectorIndexReader,
VectorIndexWriter as CoreVectorIndexWriter, VectorSearchParams,
};
use paimon_vindex_core::io::{ReadRequest, SeekRead, SeekWrite};
@@ -131,18 +130,6 @@ impl SeekWrite for PyOutputStream {
}
}
-fn metric_name(metric: MetricType) -> &'static str {
- match metric {
- MetricType::L2 => "l2",
- MetricType::InnerProduct => "inner_product",
- MetricType::Cosine => "cosine",
- }
-}
-
-fn index_type_name(index_type: IndexType) -> &'static str {
- index_type.as_str()
-}
-
fn decode_filter_bytes<'a>(
filter_bytes: Option<&'a Bound<'_, PyAny>>,
) -> PyResult<Option<&'a [u8]>> {
@@ -321,7 +308,7 @@ impl VectorIndexReader {
#[getter]
fn index_type(&self) -> String {
- index_type_name(self.inner.index_type()).to_string()
+ self.inner.index_type().as_str().to_string()
}
#[getter]
@@ -342,10 +329,10 @@ impl VectorIndexReader {
fn metadata(&self) -> VectorIndexMetadata {
let metadata = self.inner.metadata();
VectorIndexMetadata {
- index_type: index_type_name(metadata.index_type).to_string(),
+ index_type: metadata.index_type.as_str().to_string(),
dimension: metadata.dimension,
nlist: metadata.nlist,
- metric: metric_name(metadata.metric).to_string(),
+ metric: metadata.metric.as_str().to_string(),
total_vectors: metadata.total_vectors,
pq_m: metadata.pq_m,
hnsw_m: metadata.hnsw.map(|h| h.m),