From 04ca285311ce415e3b46065ffb3f1a0eeba20717 Mon Sep 17 00:00:00 2001 From: Soby Chacko Date: Wed, 11 Dec 2024 15:14:56 -0500 Subject: [PATCH] Pinecone vector store builder refactoring --- .../PineconeVectorStoreAutoConfiguration.java | 30 +- .../PineconeVectorStoreProperties.java | 2 +- ...ineconeVectorStoreAutoConfigurationIT.java | 2 +- .../PineconeVectorStorePropertiesTests.java | 2 +- .../{ => pinecone}/PineconeVectorStore.java | 301 +++++++++++++++--- .../PineconeVectorStoreHints.java | 2 +- .../resources/META-INF/spring/aot.factories | 2 +- .../{ => pinecone}/PineconeVectorStoreIT.java | 31 +- .../PineconeVectorStoreObservationIT.java | 34 +- 9 files changed, 305 insertions(+), 101 deletions(-) rename vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/{ => pinecone}/PineconeVectorStore.java (57%) rename vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/{ => pinecone}/PineconeVectorStoreHints.java (95%) rename vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/{ => pinecone}/PineconeVectorStoreIT.java (93%) rename vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/{ => pinecone}/PineconeVectorStoreObservationIT.java (90%) diff --git a/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfiguration.java b/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfiguration.java index edb7cfb4aea..ba39ecec79b 100644 --- a/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfiguration.java +++ b/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfiguration.java @@ -21,8 +21,8 @@ import org.springframework.ai.embedding.BatchingStrategy; import org.springframework.ai.embedding.EmbeddingModel; import org.springframework.ai.embedding.TokenCountBatchingStrategy; -import org.springframework.ai.vectorstore.PineconeVectorStore; -import org.springframework.ai.vectorstore.PineconeVectorStore.PineconeVectorStoreConfig; +import org.springframework.ai.vectorstore.pinecone.PineconeVectorStore; +import org.springframework.ai.vectorstore.pinecone.PineconeVectorStore.PineconeVectorStoreConfig; import org.springframework.ai.vectorstore.observation.VectorStoreObservationConvention; import org.springframework.beans.factory.ObjectProvider; import org.springframework.boot.autoconfigure.AutoConfiguration; @@ -55,20 +55,20 @@ public PineconeVectorStore vectorStore(EmbeddingModel embeddingModel, PineconeVe ObjectProvider customObservationConvention, BatchingStrategy batchingStrategy) { - var config = PineconeVectorStoreConfig.builder() - .withApiKey(properties.getApiKey()) - .withEnvironment(properties.getEnvironment()) - .withProjectId(properties.getProjectId()) - .withIndexName(properties.getIndexName()) - .withNamespace(properties.getNamespace()) - .withContentFieldName(properties.getContentFieldName()) - .withDistanceMetadataFieldName(properties.getDistanceMetadataFieldName()) - .withServerSideTimeout(properties.getServerSideTimeout()) + return PineconeVectorStore.builder() + .embeddingModel(embeddingModel) + .apiKey(properties.getApiKey()) + .environment(properties.getEnvironment()) + .projectId(properties.getProjectId()) + .indexName(properties.getIndexName()) + .namespace(properties.getNamespace()) + .contentFieldName(properties.getContentFieldName()) + .distanceMetadataFieldName(properties.getDistanceMetadataFieldName()) + .serverSideTimeout(properties.getServerSideTimeout()) + .observationRegistry(observationRegistry.getIfUnique(() -> ObservationRegistry.NOOP)) + .customObservationConvention(customObservationConvention.getIfAvailable(() -> null)) + .batchingStrategy(batchingStrategy) .build(); - - return new PineconeVectorStore(config, embeddingModel, - observationRegistry.getIfUnique(() -> ObservationRegistry.NOOP), - customObservationConvention.getIfAvailable(() -> null), batchingStrategy); } } diff --git a/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreProperties.java b/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreProperties.java index bf9f2e9cfd0..c6d96d00391 100644 --- a/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreProperties.java +++ b/spring-ai-spring-boot-autoconfigure/src/main/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreProperties.java @@ -19,7 +19,7 @@ import java.time.Duration; import org.springframework.ai.document.DocumentMetadata; -import org.springframework.ai.vectorstore.PineconeVectorStore; +import org.springframework.ai.vectorstore.pinecone.PineconeVectorStore; import org.springframework.boot.context.properties.ConfigurationProperties; /** diff --git a/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfigurationIT.java b/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfigurationIT.java index 95ea2339e6b..b44c528056c 100644 --- a/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfigurationIT.java +++ b/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStoreAutoConfigurationIT.java @@ -33,7 +33,7 @@ import org.springframework.ai.embedding.EmbeddingModel; import org.springframework.ai.observation.conventions.VectorStoreProvider; import org.springframework.ai.transformers.TransformersEmbeddingModel; -import org.springframework.ai.vectorstore.PineconeVectorStore; +import org.springframework.ai.vectorstore.pinecone.PineconeVectorStore; import org.springframework.ai.vectorstore.SearchRequest; import org.springframework.ai.vectorstore.observation.VectorStoreObservationContext; import org.springframework.boot.autoconfigure.AutoConfigurations; diff --git a/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStorePropertiesTests.java b/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStorePropertiesTests.java index 3083442f87c..42d0eb74647 100644 --- a/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStorePropertiesTests.java +++ b/spring-ai-spring-boot-autoconfigure/src/test/java/org/springframework/ai/autoconfigure/vectorstore/pinecone/PineconeVectorStorePropertiesTests.java @@ -21,7 +21,7 @@ import org.junit.jupiter.api.Test; import org.springframework.ai.document.DocumentMetadata; -import org.springframework.ai.vectorstore.PineconeVectorStore; +import org.springframework.ai.vectorstore.pinecone.PineconeVectorStore; import static org.assertj.core.api.Assertions.assertThat; diff --git a/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/PineconeVectorStore.java b/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStore.java similarity index 57% rename from vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/PineconeVectorStore.java rename to vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStore.java index dbd312f5740..9d0ce87842f 100644 --- a/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/PineconeVectorStore.java +++ b/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStore.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package org.springframework.ai.vectorstore; +package org.springframework.ai.vectorstore.pinecone; import java.time.Duration; import java.util.List; @@ -45,6 +45,8 @@ import org.springframework.ai.embedding.TokenCountBatchingStrategy; import org.springframework.ai.model.EmbeddingUtils; import org.springframework.ai.observation.conventions.VectorStoreProvider; +import org.springframework.ai.vectorstore.AbstractVectorStoreBuilder; +import org.springframework.ai.vectorstore.SearchRequest; import org.springframework.ai.vectorstore.filter.FilterExpressionConverter; import org.springframework.ai.vectorstore.filter.converter.PineconeFilterExpressionConverter; import org.springframework.ai.vectorstore.observation.AbstractObservationVectorStore; @@ -69,8 +71,6 @@ public class PineconeVectorStore extends AbstractObservationVectorStore { public final FilterExpressionConverter filterExpressionConverter = new PineconeFilterExpressionConverter(); - private final EmbeddingModel embeddingModel; - private final PineconeConnection pineconeConnection; private final String pineconeNamespace; @@ -87,35 +87,77 @@ public class PineconeVectorStore extends AbstractObservationVectorStore { /** * Constructs a new PineconeVectorStore. - * @param config The configuration for the store. - * @param embeddingModel The client for embedding operations. + * @deprecated Use {@link #builder()} instead + * @param config The configuration for the store + * @param embeddingModel The client for embedding operations */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public PineconeVectorStore(PineconeVectorStoreConfig config, EmbeddingModel embeddingModel) { this(config, embeddingModel, ObservationRegistry.NOOP, null, new TokenCountBatchingStrategy()); } /** * Constructs a new PineconeVectorStore. - * @param config The configuration for the store. - * @param embeddingModel The client for embedding operations. - * @param observationRegistry The registry for observations. - * @param customObservationConvention The custom observation convention. + * @deprecated Use {@link #builder()} instead + * @param config The configuration for the store + * @param embeddingModel The client for embedding operations + * @param observationRegistry The registry for observations + * @param customObservationConvention The custom observation convention + * @param batchingStrategy The strategy for batching operations */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public PineconeVectorStore(PineconeVectorStoreConfig config, EmbeddingModel embeddingModel, ObservationRegistry observationRegistry, VectorStoreObservationConvention customObservationConvention, BatchingStrategy batchingStrategy) { - super(observationRegistry, customObservationConvention); - Assert.notNull(config, "PineconeVectorStoreConfig must not be null"); - Assert.notNull(embeddingModel, "EmbeddingModel must not be null"); - - this.embeddingModel = embeddingModel; - this.pineconeNamespace = config.namespace; - this.pineconeIndexName = config.connectionConfig.getIndexName(); - this.pineconeContentFieldName = config.contentFieldName; - this.pineconeDistanceMetadataFieldName = config.distanceMetadataFieldName; - this.pineconeConnection = new PineconeClient(config.clientConfig).connect(config.connectionConfig); + this(builder().embeddingModel(embeddingModel) + .apiKey(config.clientConfig.getApiKey()) + .projectId(config.clientConfig.getProjectName()) + .environment(config.clientConfig.getEnvironment()) + .indexName(config.connectionConfig.getIndexName()) + .namespace(config.namespace) + .contentFieldName(config.contentFieldName) + .distanceMetadataFieldName(config.distanceMetadataFieldName) + .serverSideTimeout(Duration.ofSeconds(config.clientConfig.getServerSideTimeoutSec())) + .observationRegistry(observationRegistry) + .customObservationConvention(customObservationConvention) + .batchingStrategy(batchingStrategy)); + } + + /** + * Creates a new PineconeVectorStore using the builder pattern. + * @param builder The configured builder instance + */ + protected PineconeVectorStore(PineconeBuilder builder) { + super(builder); + + Assert.hasText(builder.apiKey, "ApiKey must not be null or empty"); + Assert.hasText(builder.projectId, "ProjectId must not be null or empty"); + Assert.hasText(builder.environment, "Environment must not be null or empty"); + Assert.hasText(builder.indexName, "IndexName must not be null or empty"); + + this.pineconeNamespace = builder.namespace; + this.pineconeIndexName = builder.indexName; + this.pineconeContentFieldName = builder.contentFieldName; + this.pineconeDistanceMetadataFieldName = builder.distanceMetadataFieldName; + + PineconeClientConfig clientConfig = new PineconeClientConfig().withApiKey(builder.apiKey) + .withEnvironment(builder.environment) + .withProjectName(builder.projectId) + .withServerSideTimeoutSec((int) builder.serverSideTimeout.toSeconds()); + + PineconeConnectionConfig connectionConfig = new PineconeConnectionConfig().withIndexName(builder.indexName); + + this.pineconeConnection = new PineconeClient(clientConfig).connect(connectionConfig); this.objectMapper = new ObjectMapper(); - this.batchingStrategy = batchingStrategy; + this.batchingStrategy = builder.batchingStrategy; + } + + /** + * Creates a new builder instance for configuring a PineconeVectorStore. + * @return A new PineconeBuilder instance + */ + public static PineconeBuilder builder() { + return new PineconeBuilder(); } /** @@ -294,8 +336,151 @@ public VectorStoreObservationContext.Builder createObservationContextBuilder(Str } /** - * Configuration class for the PineconeVectorStore. + * Builder class for creating PineconeVectorStore instances. + */ + public static class PineconeBuilder extends AbstractVectorStoreBuilder { + + private String apiKey; + + private String projectId; + + private String environment; + + private String indexName; + + private String namespace = ""; + + private String contentFieldName = CONTENT_FIELD_NAME; + + private String distanceMetadataFieldName = DocumentMetadata.DISTANCE.value(); + + private Duration serverSideTimeout = Duration.ofSeconds(20); + + private BatchingStrategy batchingStrategy = new TokenCountBatchingStrategy(); + + /** + * Sets the Pinecone API key. + * @param apiKey The API key to use + * @return The builder instance + * @throws IllegalArgumentException if apiKey is null or empty + */ + public PineconeBuilder apiKey(String apiKey) { + Assert.hasText(apiKey, "ApiKey must not be null or empty"); + this.apiKey = apiKey; + return this; + } + + /** + * Sets the Pinecone project ID. + * @param projectId The project ID to use + * @return The builder instance + * @throws IllegalArgumentException if projectId is null or empty + */ + public PineconeBuilder projectId(String projectId) { + Assert.hasText(projectId, "ProjectId must not be null or empty"); + this.projectId = projectId; + return this; + } + + /** + * Sets the Pinecone environment. + * @param environment The environment to use (e.g. gcp-starter) + * @return The builder instance + * @throws IllegalArgumentException if environment is null or empty + */ + public PineconeBuilder environment(String environment) { + Assert.hasText(environment, "Environment must not be null or empty"); + this.environment = environment; + return this; + } + + /** + * Sets the Pinecone index name. + * @param indexName The index name to use + * @return The builder instance + * @throws IllegalArgumentException if indexName is null or empty + */ + public PineconeBuilder indexName(String indexName) { + Assert.hasText(indexName, "IndexName must not be null or empty"); + this.indexName = indexName; + return this; + } + + /** + * Sets the Pinecone namespace. Note: The free-tier (gcp-starter) doesn't support + * Namespaces. + * @param namespace The namespace to use (leave empty for free tier) + * @return The builder instance + */ + public PineconeBuilder namespace(String namespace) { + this.namespace = namespace != null ? namespace : ""; + return this; + } + + /** + * Sets the content field name. + * @param contentFieldName The content field name to use + * @return The builder instance + */ + public PineconeBuilder contentFieldName(String contentFieldName) { + this.contentFieldName = contentFieldName != null ? contentFieldName : CONTENT_FIELD_NAME; + return this; + } + + /** + * Sets the distance metadata field name. + * @param distanceMetadataFieldName The distance metadata field name to use + * @return The builder instance + */ + public PineconeBuilder distanceMetadataFieldName(String distanceMetadataFieldName) { + this.distanceMetadataFieldName = distanceMetadataFieldName != null ? distanceMetadataFieldName + : DocumentMetadata.DISTANCE.value(); + return this; + } + + /** + * Sets the server-side timeout. + * @param serverSideTimeout The timeout duration to use + * @return The builder instance + */ + public PineconeBuilder serverSideTimeout(Duration serverSideTimeout) { + this.serverSideTimeout = serverSideTimeout != null ? serverSideTimeout : Duration.ofSeconds(20); + return this; + } + + /** + * Sets the batching strategy. + * @param batchingStrategy The batching strategy to use + * @return The builder instance + * @throws IllegalArgumentException if batchingStrategy is null + */ + public PineconeBuilder batchingStrategy(BatchingStrategy batchingStrategy) { + Assert.notNull(batchingStrategy, "BatchingStrategy must not be null"); + this.batchingStrategy = batchingStrategy; + return this; + } + + /** + * Builds a new PineconeVectorStore instance with the configured properties. + * @return A new PineconeVectorStore instance + * @throws IllegalStateException if the builder is in an invalid state + */ + @Override + public PineconeVectorStore build() { + validate(); + return new PineconeVectorStore(this); + } + + } + + /** + * Configuration for PineconeVectorStore. + * + * @deprecated Use {@link PineconeVectorStore#builder()} instead. This class will be + * removed in a future release as part of the migration to the builder pattern. + * @since 1.0.0 */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public static final class PineconeVectorStoreConfig { // The free tier (gcp-starter) doesn't support Namespaces. @@ -312,22 +497,17 @@ public static final class PineconeVectorStoreConfig { private final PineconeClientConfig clientConfig; - // private final int defaultSimilarityTopK; - /** * Constructor using the builder. - * @param builder The configuration builder. - */ - /** - * Constructor using the builder. - * @param builder The configuration builder. + * @param builder The configuration builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public PineconeVectorStoreConfig(Builder builder) { this.namespace = builder.namespace; this.contentFieldName = builder.contentFieldName; this.distanceMetadataFieldName = builder.distanceMetadataFieldName; - // this.defaultSimilarityTopK = builder.defaultSimilarityTopK; this.connectionConfig = new PineconeConnectionConfig().withIndexName(builder.indexName); this.clientConfig = new PineconeClientConfig().withApiKey(builder.apiKey) .withEnvironment(builder.environment) @@ -337,19 +517,30 @@ public PineconeVectorStoreConfig(Builder builder) { /** * Start building a new configuration. - * @return The entry point for creating a new configuration. + * @return The entry point for creating a new configuration + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public static Builder builder() { return new Builder(); } /** * {@return the default config} + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public static PineconeVectorStoreConfig defaultConfig() { return builder().build(); } + /** + * Builder for PineconeVectorStoreConfig. + * + * @deprecated Use {@link PineconeVectorStore#builder()} instead. This class will + * be removed in a future release as part of the migration to the builder pattern. + */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public static final class Builder { private String apiKey; @@ -378,9 +569,11 @@ private Builder() { /** * Pinecone api key. - * @param apiKey key to use. - * @return this builder. + * @param apiKey key to use + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withApiKey(String apiKey) { this.apiKey = apiKey; return this; @@ -388,9 +581,11 @@ public Builder withApiKey(String apiKey) { /** * Pinecone project id. - * @param projectId Project id to use. - * @return this builder. + * @param projectId Project id to use + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withProjectId(String projectId) { this.projectId = projectId; return this; @@ -398,9 +593,11 @@ public Builder withProjectId(String projectId) { /** * Pinecone environment name. - * @param environment Environment name (e.g. gcp-starter). - * @return this builder. + * @param environment Environment name (e.g. gcp-starter) + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withEnvironment(String environment) { this.environment = environment; return this; @@ -408,9 +605,11 @@ public Builder withEnvironment(String environment) { /** * Pinecone index name. - * @param indexName Pinecone index name to use. - * @return this builder. + * @param indexName Pinecone index name to use + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withIndexName(String indexName) { this.indexName = indexName; return this; @@ -419,9 +618,11 @@ public Builder withIndexName(String indexName) { /** * Pinecone Namespace. The free-tier (gcp-starter) doesn't support Namespaces. * For free-tier leave the namespace empty. - * @param namespace Pinecone namespace to use. - * @return this builder. + * @param namespace Pinecone namespace to use + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withNamespace(String namespace) { this.namespace = namespace; return this; @@ -429,9 +630,11 @@ public Builder withNamespace(String namespace) { /** * Content field name. - * @param contentFieldName content field name to use. - * @return this builder. + * @param contentFieldName content field name to use + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withContentFieldName(String contentFieldName) { this.contentFieldName = contentFieldName; return this; @@ -439,9 +642,11 @@ public Builder withContentFieldName(String contentFieldName) { /** * Distance metadata field name. - * @param distanceMetadataFieldName distance metadata field name to use. - * @return this builder. + * @param distanceMetadataFieldName distance metadata field name to use + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withDistanceMetadataFieldName(String distanceMetadataFieldName) { this.distanceMetadataFieldName = distanceMetadataFieldName; return this; @@ -449,9 +654,11 @@ public Builder withDistanceMetadataFieldName(String distanceMetadataFieldName) { /** * Pinecone server side timeout. - * @param serverSideTimeout server timeout to use. - * @return this builder. + * @param serverSideTimeout server timeout to use + * @return this builder + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public Builder withServerSideTimeout(Duration serverSideTimeout) { this.serverSideTimeout = serverSideTimeout; return this; @@ -459,7 +666,9 @@ public Builder withServerSideTimeout(Duration serverSideTimeout) { /** * {@return the immutable configuration} + * @deprecated Use {@link PineconeVectorStore#builder()} instead */ + @Deprecated(since = "1.0.0-M5", forRemoval = true) public PineconeVectorStoreConfig build() { return new PineconeVectorStoreConfig(this); } diff --git a/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/PineconeVectorStoreHints.java b/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreHints.java similarity index 95% rename from vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/PineconeVectorStoreHints.java rename to vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreHints.java index 20c0dd75df5..744b06c429e 100644 --- a/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/PineconeVectorStoreHints.java +++ b/vector-stores/spring-ai-pinecone-store/src/main/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreHints.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package org.springframework.ai.vectorstore; +package org.springframework.ai.vectorstore.pinecone; import java.util.Set; diff --git a/vector-stores/spring-ai-pinecone-store/src/main/resources/META-INF/spring/aot.factories b/vector-stores/spring-ai-pinecone-store/src/main/resources/META-INF/spring/aot.factories index 0127c04f003..804f320c8eb 100644 --- a/vector-stores/spring-ai-pinecone-store/src/main/resources/META-INF/spring/aot.factories +++ b/vector-stores/spring-ai-pinecone-store/src/main/resources/META-INF/spring/aot.factories @@ -1 +1 @@ -org.springframework.aot.hint.RuntimeHintsRegistrar=org.springframework.ai.vectorstore.PineconeVectorStoreHints \ No newline at end of file +org.springframework.aot.hint.RuntimeHintsRegistrar=org.springframework.ai.vectorstore.pinecone.PineconeVectorStoreHints diff --git a/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/PineconeVectorStoreIT.java b/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreIT.java similarity index 93% rename from vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/PineconeVectorStoreIT.java rename to vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreIT.java index 712efa19a69..70837be8849 100644 --- a/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/PineconeVectorStoreIT.java +++ b/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreIT.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package org.springframework.ai.vectorstore; +package org.springframework.ai.vectorstore.pinecone; import java.io.IOException; import java.nio.charset.StandardCharsets; @@ -34,7 +34,9 @@ import org.springframework.ai.document.DocumentMetadata; import org.springframework.ai.embedding.EmbeddingModel; import org.springframework.ai.transformers.TransformersEmbeddingModel; -import org.springframework.ai.vectorstore.PineconeVectorStore.PineconeVectorStoreConfig; +import org.springframework.ai.vectorstore.SearchRequest; +import org.springframework.ai.vectorstore.VectorStore; +import org.springframework.ai.vectorstore.pinecone.PineconeVectorStore.PineconeVectorStoreConfig; import org.springframework.boot.SpringBootConfiguration; import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.test.context.runner.ApplicationContextRunner; @@ -271,21 +273,16 @@ public void searchThresholdTest() { public static class TestApplication { @Bean - public PineconeVectorStoreConfig pineconeVectorStoreConfig() { - - return PineconeVectorStoreConfig.builder() - .withApiKey(System.getenv("PINECONE_API_KEY")) - .withEnvironment(PINECONE_ENVIRONMENT) - .withProjectId(PINECONE_PROJECT_ID) - .withIndexName(PINECONE_INDEX_NAME) - .withNamespace(PINECONE_NAMESPACE) - .withContentFieldName(CUSTOM_CONTENT_FIELD_NAME) - .build(); - } - - @Bean - public VectorStore vectorStore(PineconeVectorStoreConfig config, EmbeddingModel embeddingModel) { - return new PineconeVectorStore(config, embeddingModel); + public VectorStore vectorStore(EmbeddingModel embeddingModel) { + return PineconeVectorStore.builder() + .embeddingModel(embeddingModel) + .apiKey(System.getenv("PINECONE_API_KEY")) + .environment(PINECONE_ENVIRONMENT) + .projectId(PINECONE_PROJECT_ID) + .indexName(PINECONE_INDEX_NAME) + .namespace(PINECONE_NAMESPACE) + .contentFieldName(CUSTOM_CONTENT_FIELD_NAME) + .build(); } @Bean diff --git a/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/PineconeVectorStoreObservationIT.java b/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreObservationIT.java similarity index 90% rename from vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/PineconeVectorStoreObservationIT.java rename to vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreObservationIT.java index 53ced5aa0b1..02c61157624 100644 --- a/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/PineconeVectorStoreObservationIT.java +++ b/vector-stores/spring-ai-pinecone-store/src/test/java/org/springframework/ai/vectorstore/pinecone/PineconeVectorStoreObservationIT.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package org.springframework.ai.vectorstore; +package org.springframework.ai.vectorstore.pinecone; import java.io.IOException; import java.nio.charset.StandardCharsets; @@ -37,7 +37,9 @@ import org.springframework.ai.observation.conventions.SpringAiKind; import org.springframework.ai.observation.conventions.VectorStoreProvider; import org.springframework.ai.transformers.TransformersEmbeddingModel; -import org.springframework.ai.vectorstore.PineconeVectorStore.PineconeVectorStoreConfig; +import org.springframework.ai.vectorstore.SearchRequest; +import org.springframework.ai.vectorstore.VectorStore; +import org.springframework.ai.vectorstore.pinecone.PineconeVectorStore.PineconeVectorStoreConfig; import org.springframework.ai.vectorstore.observation.DefaultVectorStoreObservationConvention; import org.springframework.ai.vectorstore.observation.VectorStoreObservationDocumentation.HighCardinalityKeyNames; import org.springframework.ai.vectorstore.observation.VectorStoreObservationDocumentation.LowCardinalityKeyNames; @@ -184,25 +186,21 @@ public TestObservationRegistry observationRegistry() { } @Bean - public PineconeVectorStoreConfig pineconeVectorStoreConfig() { - - return PineconeVectorStoreConfig.builder() - .withApiKey(System.getenv("PINECONE_API_KEY")) - .withEnvironment(PINECONE_ENVIRONMENT) - .withProjectId(PINECONE_PROJECT_ID) - .withIndexName(PINECONE_INDEX_NAME) - .withNamespace(PINECONE_NAMESPACE) - .withContentFieldName(CUSTOM_CONTENT_FIELD_NAME) + public VectorStore vectorStore(EmbeddingModel embeddingModel, ObservationRegistry observationRegistry) { + return PineconeVectorStore.builder() + .embeddingModel(embeddingModel) + .apiKey(System.getenv("PINECONE_API_KEY")) + .environment(PINECONE_ENVIRONMENT) + .projectId(PINECONE_PROJECT_ID) + .indexName(PINECONE_INDEX_NAME) + .namespace(PINECONE_NAMESPACE) + .contentFieldName(CUSTOM_CONTENT_FIELD_NAME) + .observationRegistry(observationRegistry) + .customObservationConvention(null) + .batchingStrategy(new TokenCountBatchingStrategy()) .build(); } - @Bean - public VectorStore vectorStore(PineconeVectorStoreConfig config, EmbeddingModel embeddingModel, - ObservationRegistry observationRegistry) { - return new PineconeVectorStore(config, embeddingModel, observationRegistry, null, - new TokenCountBatchingStrategy()); - } - @Bean public EmbeddingModel embeddingModel() { return new TransformersEmbeddingModel();