cmem-plugin-pgvector 0.7.1__tar.gz → 0.9.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/PKG-INFO +6 -6
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/commons.py +38 -4
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/search_task.py +27 -3
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/store_task.py +26 -2
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/pyproject.toml +10 -10
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/LICENSE +0 -0
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/README-public.md +0 -0
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/__init__.py +0 -0
- {cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/postgresql.svg +0 -0
|
@@ -1,22 +1,22 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
2
|
Name: cmem-plugin-pgvector
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.9.0
|
|
4
4
|
Summary: Store and search for embedding vectors in a Postgres vector store.
|
|
5
5
|
License: Apache-2.0
|
|
6
|
+
License-File: LICENSE
|
|
6
7
|
Keywords: eccenca Corporate Memory,plugin
|
|
7
8
|
Author: eccenca GmbH
|
|
8
9
|
Author-email: cmempy-developer@eccenca.com
|
|
9
10
|
Maintainer: Edgard Marx
|
|
10
11
|
Maintainer-email: edgard.marx@eccenca.com
|
|
11
|
-
Requires-Python: >=3.
|
|
12
|
+
Requires-Python: >=3.13,<4.0
|
|
12
13
|
Classifier: Development Status :: 4 - Beta
|
|
13
14
|
Classifier: Environment :: Plugins
|
|
14
15
|
Classifier: License :: OSI Approved :: Apache Software License
|
|
15
16
|
Classifier: Programming Language :: Python :: 3
|
|
16
|
-
Classifier: Programming Language :: Python :: 3.11
|
|
17
|
-
Classifier: Programming Language :: Python :: 3.12
|
|
18
17
|
Classifier: Programming Language :: Python :: 3.13
|
|
19
|
-
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
19
|
+
Requires-Dist: cmem-plugin-base (>=4.15.0,<5.0.0)
|
|
20
20
|
Requires-Dist: langchain-core (>=0.3.71,<0.4.0)
|
|
21
21
|
Requires-Dist: langchain-postgres (>=0.0.15,<0.0.16)
|
|
22
22
|
Requires-Dist: psycopg[binary] (>=3.2.9,<4.0.0)
|
|
@@ -15,6 +15,37 @@ from cmem_plugin_base.dataintegration.types import (
|
|
|
15
15
|
)
|
|
16
16
|
|
|
17
17
|
|
|
18
|
+
class DatabaseConnectionError(Exception):
|
|
19
|
+
"""Custom exception for database connection issues"""
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def check_database_connection(dbname: str, user: str, password: str, host: str, port: int) -> str:
|
|
23
|
+
"""Test database connection and return success message or raise exception on failure"""
|
|
24
|
+
try:
|
|
25
|
+
with (
|
|
26
|
+
psycopg.connect(
|
|
27
|
+
dbname=dbname,
|
|
28
|
+
user=user,
|
|
29
|
+
password=password,
|
|
30
|
+
host=host,
|
|
31
|
+
port=port,
|
|
32
|
+
connect_timeout=10,
|
|
33
|
+
) as conn,
|
|
34
|
+
conn.cursor() as cursor,
|
|
35
|
+
):
|
|
36
|
+
# Test basic connectivity
|
|
37
|
+
cursor.execute("SELECT version();")
|
|
38
|
+
version = cursor.fetchone()[0] # type: ignore[index]
|
|
39
|
+
return f"Connection successful. PostgreSQL version: {version[:50]}..."
|
|
40
|
+
|
|
41
|
+
except psycopg.OperationalError as e:
|
|
42
|
+
raise DatabaseConnectionError(f"Connection failed: {e!s}") from e
|
|
43
|
+
except psycopg.Error as e:
|
|
44
|
+
raise DatabaseConnectionError(f"Database error: {e!s}") from e
|
|
45
|
+
except Exception as e:
|
|
46
|
+
raise DatabaseConnectionError(f"Unexpected error: {e!s}") from e
|
|
47
|
+
|
|
48
|
+
|
|
18
49
|
def get_collection_names(
|
|
19
50
|
dbname: str, user: str, password: str, host: str = "localhost", port: int = 5432
|
|
20
51
|
) -> list[str]:
|
|
@@ -59,10 +90,13 @@ class PGVectorCollection(StringParameterType):
|
|
|
59
90
|
user = depend_on_parameter_values[3]
|
|
60
91
|
password = depend_on_parameter_values[4]
|
|
61
92
|
password = password if isinstance(password, str) else password.decrypt()
|
|
62
|
-
result = []
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
93
|
+
result: list[Autocompletion] = []
|
|
94
|
+
try:
|
|
95
|
+
collections = get_collection_names(
|
|
96
|
+
host=host, port=port, dbname=dbname, user=user, password=password
|
|
97
|
+
)
|
|
98
|
+
except psycopg.Error:
|
|
99
|
+
return result
|
|
66
100
|
filtered_collections = set()
|
|
67
101
|
for term in query_terms:
|
|
68
102
|
for collection in collections:
|
{cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/search_task.py
RENAMED
|
@@ -5,7 +5,7 @@ from ast import literal_eval
|
|
|
5
5
|
from collections.abc import Generator, Sequence
|
|
6
6
|
|
|
7
7
|
from cmem_plugin_base.dataintegration.context import ExecutionContext, ExecutionReport
|
|
8
|
-
from cmem_plugin_base.dataintegration.description import Icon, Plugin, PluginParameter
|
|
8
|
+
from cmem_plugin_base.dataintegration.description import Icon, Plugin, PluginAction, PluginParameter
|
|
9
9
|
from cmem_plugin_base.dataintegration.entity import Entities, Entity, EntityPath, EntitySchema
|
|
10
10
|
from cmem_plugin_base.dataintegration.parameter.password import Password
|
|
11
11
|
from cmem_plugin_base.dataintegration.plugins import WorkflowPlugin
|
|
@@ -19,7 +19,11 @@ from langchain_core.embeddings import Embeddings
|
|
|
19
19
|
from langchain_postgres import PGVector
|
|
20
20
|
from langchain_postgres.vectorstores import DistanceStrategy
|
|
21
21
|
|
|
22
|
-
from cmem_plugin_pgvector.commons import
|
|
22
|
+
from cmem_plugin_pgvector.commons import (
|
|
23
|
+
DatabaseConnectionError,
|
|
24
|
+
DatabaseParams,
|
|
25
|
+
check_database_connection,
|
|
26
|
+
)
|
|
23
27
|
|
|
24
28
|
|
|
25
29
|
class DummyEmbeddings(Embeddings):
|
|
@@ -66,6 +70,13 @@ The results in this output are structured like this:
|
|
|
66
70
|
""",
|
|
67
71
|
icon=Icon(package=__package__, file_name="postgresql.svg"),
|
|
68
72
|
plugin_id="cmem_plugin_pgvector-Search",
|
|
73
|
+
actions=[
|
|
74
|
+
PluginAction(
|
|
75
|
+
name="test_connection",
|
|
76
|
+
label="Test Connection",
|
|
77
|
+
description="Test database connectivity",
|
|
78
|
+
)
|
|
79
|
+
],
|
|
69
80
|
parameters=[
|
|
70
81
|
*DatabaseParams().as_list(),
|
|
71
82
|
PluginParameter(
|
|
@@ -149,6 +160,19 @@ class PGVectorSearchPlugin(WorkflowPlugin):
|
|
|
149
160
|
self.report.operation_desc = "searches"
|
|
150
161
|
self._setup_ports()
|
|
151
162
|
|
|
163
|
+
def test_connection(self) -> str:
|
|
164
|
+
"""Plugin Action to test database connection"""
|
|
165
|
+
try:
|
|
166
|
+
return check_database_connection(
|
|
167
|
+
dbname=self.database,
|
|
168
|
+
user=self.user,
|
|
169
|
+
password=self.password,
|
|
170
|
+
host=self.host,
|
|
171
|
+
port=self.port,
|
|
172
|
+
)
|
|
173
|
+
except DatabaseConnectionError as e:
|
|
174
|
+
raise ValueError(f"Connection test failed: {e!s}") from e
|
|
175
|
+
|
|
152
176
|
def _setup_ports(self) -> None:
|
|
153
177
|
"""Configure input and output ports depending on the configuration"""
|
|
154
178
|
input_paths = [EntityPath(path=self.embedding_query_path)]
|
|
@@ -194,7 +218,7 @@ class PGVectorSearchPlugin(WorkflowPlugin):
|
|
|
194
218
|
for doc_tuple in docs:
|
|
195
219
|
json_entity = {
|
|
196
220
|
"id": doc_tuple[0].id,
|
|
197
|
-
"metadata":
|
|
221
|
+
"metadata": doc_tuple[0].metadata,
|
|
198
222
|
"_embedding_source": doc_tuple[0].page_content,
|
|
199
223
|
"distance": str(doc_tuple[1]),
|
|
200
224
|
}
|
{cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/store_task.py
RENAMED
|
@@ -5,7 +5,7 @@ from collections.abc import Sequence
|
|
|
5
5
|
from typing import Any
|
|
6
6
|
|
|
7
7
|
from cmem_plugin_base.dataintegration.context import ExecutionContext, ExecutionReport
|
|
8
|
-
from cmem_plugin_base.dataintegration.description import Icon, Plugin, PluginParameter
|
|
8
|
+
from cmem_plugin_base.dataintegration.description import Icon, Plugin, PluginAction, PluginParameter
|
|
9
9
|
from cmem_plugin_base.dataintegration.entity import Entities, Entity, EntityPath
|
|
10
10
|
from cmem_plugin_base.dataintegration.parameter.password import Password
|
|
11
11
|
from cmem_plugin_base.dataintegration.plugins import WorkflowPlugin
|
|
@@ -15,7 +15,11 @@ from cmem_plugin_base.dataintegration.ports import (
|
|
|
15
15
|
)
|
|
16
16
|
from langchain_postgres import PGVector
|
|
17
17
|
|
|
18
|
-
from cmem_plugin_pgvector.commons import
|
|
18
|
+
from cmem_plugin_pgvector.commons import (
|
|
19
|
+
DatabaseConnectionError,
|
|
20
|
+
DatabaseParams,
|
|
21
|
+
check_database_connection,
|
|
22
|
+
)
|
|
19
23
|
|
|
20
24
|
|
|
21
25
|
class DataContainer:
|
|
@@ -56,6 +60,13 @@ metadata.
|
|
|
56
60
|
""",
|
|
57
61
|
icon=Icon(package=__package__, file_name="postgresql.svg"),
|
|
58
62
|
plugin_id="cmem_plugin_pgvector-Store",
|
|
63
|
+
actions=[
|
|
64
|
+
PluginAction(
|
|
65
|
+
name="test_connection",
|
|
66
|
+
label="Test Connection",
|
|
67
|
+
description="Test database connectivity",
|
|
68
|
+
)
|
|
69
|
+
],
|
|
59
70
|
parameters=[
|
|
60
71
|
*DatabaseParams().as_list(),
|
|
61
72
|
PluginParameter(
|
|
@@ -150,6 +161,19 @@ class PGVectorStorePlugin(WorkflowPlugin):
|
|
|
150
161
|
self.report.operation = "store"
|
|
151
162
|
self.report.operation_desc = "vectors stored"
|
|
152
163
|
|
|
164
|
+
def test_connection(self) -> str:
|
|
165
|
+
"""Plugin Action to test database connection"""
|
|
166
|
+
try:
|
|
167
|
+
return check_database_connection(
|
|
168
|
+
dbname=self.database,
|
|
169
|
+
user=self.user,
|
|
170
|
+
password=self.password,
|
|
171
|
+
host=self.host,
|
|
172
|
+
port=self.port,
|
|
173
|
+
)
|
|
174
|
+
except DatabaseConnectionError as e:
|
|
175
|
+
raise ValueError(f"Connection test failed: {e!s}") from e
|
|
176
|
+
|
|
153
177
|
def _update_report(self, count: int) -> None:
|
|
154
178
|
self.report.entity_count = count
|
|
155
179
|
self.execution_context.report.update(self.report)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[tool.poetry]
|
|
2
2
|
name = "cmem-plugin-pgvector"
|
|
3
|
-
version = "0.
|
|
3
|
+
version = "0.9.0"
|
|
4
4
|
license = "Apache-2.0"
|
|
5
5
|
description = "Store and search for embedding vectors in a Postgres vector store."
|
|
6
6
|
authors = ["eccenca GmbH <cmempy-developer@eccenca.com>"]
|
|
@@ -15,29 +15,29 @@ keywords = [
|
|
|
15
15
|
|
|
16
16
|
|
|
17
17
|
[tool.poetry.dependencies]# if you need to change python version here, change it also in .python-version
|
|
18
|
-
python = "^3.
|
|
18
|
+
python = "^3.13"
|
|
19
19
|
langchain-postgres = "^0.0.15"
|
|
20
20
|
psycopg = {extras = ["binary"], version = "^3.2.9"}
|
|
21
21
|
langchain-core = "^0.3.71"
|
|
22
22
|
|
|
23
23
|
[tool.poetry.dependencies.cmem-plugin-base]
|
|
24
|
-
version = "^4.
|
|
24
|
+
version = "^4.15.0"
|
|
25
25
|
allow-prereleases = false
|
|
26
26
|
|
|
27
27
|
[tool.poetry.group.dev.dependencies.cmem-cmemc]
|
|
28
28
|
version = ">=24.2.0"
|
|
29
29
|
|
|
30
30
|
[tool.poetry.group.dev.dependencies]
|
|
31
|
-
deptry = "^0.23.
|
|
31
|
+
deptry = "^0.23.1"
|
|
32
32
|
genbadge = {extras = ["coverage"], version = "^1.1.2"}
|
|
33
|
-
mypy = "^1.
|
|
34
|
-
pip = "^25.
|
|
35
|
-
pytest = "^8.4.
|
|
36
|
-
pytest-cov = "^
|
|
33
|
+
mypy = "^1.18.2"
|
|
34
|
+
pip = "^25.2"
|
|
35
|
+
pytest = "^8.4.2"
|
|
36
|
+
pytest-cov = "^7.0.0"
|
|
37
37
|
pytest-dotenv = "^0.5.2"
|
|
38
38
|
pytest-html = "^4.1.1"
|
|
39
|
-
pytest-memray = { version = "^1.
|
|
40
|
-
ruff = "^0.
|
|
39
|
+
pytest-memray = { version = "^1.8.0", markers = "platform_system != 'Windows'" }
|
|
40
|
+
ruff = "^0.13.3"
|
|
41
41
|
safety = "^1.10.3"
|
|
42
42
|
aiohttp = "^3.10.11"
|
|
43
43
|
testcontainers = "^4.12.0"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cmem_plugin_pgvector-0.7.1 → cmem_plugin_pgvector-0.9.0}/cmem_plugin_pgvector/postgresql.svg
RENAMED
|
File without changes
|