rdf4j-python 0.1.3__py3-none-any.whl → 0.1.5__py3-none-any.whl
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.
- rdf4j_python/_client/_client.py +24 -2
- rdf4j_python/_driver/_async_rdf4j_db.py +1 -0
- rdf4j_python/_driver/_async_repository.py +44 -12
- rdf4j_python/model/repository_config.py +15 -928
- rdf4j_python-0.1.5.dist-info/METADATA +259 -0
- {rdf4j_python-0.1.3.dist-info → rdf4j_python-0.1.5.dist-info}/RECORD +9 -9
- {rdf4j_python-0.1.3.dist-info → rdf4j_python-0.1.5.dist-info}/WHEEL +1 -1
- rdf4j_python-0.1.3.dist-info/METADATA +0 -77
- {rdf4j_python-0.1.3.dist-info → rdf4j_python-0.1.5.dist-info}/licenses/LICENSE +0 -0
- {rdf4j_python-0.1.3.dist-info → rdf4j_python-0.1.5.dist-info}/top_level.txt +0 -0
|
@@ -0,0 +1,259 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: rdf4j-python
|
|
3
|
+
Version: 0.1.5
|
|
4
|
+
Summary: The Python client for RDF4J
|
|
5
|
+
Author-email: Chengxu Bian <cbian564@gmail.com>
|
|
6
|
+
Requires-Python: >=3.10
|
|
7
|
+
Description-Content-Type: text/markdown
|
|
8
|
+
License-File: LICENSE
|
|
9
|
+
Requires-Dist: httpx>=0.28.1
|
|
10
|
+
Requires-Dist: pyoxigraph>=0.4.10
|
|
11
|
+
Provides-Extra: sparqlwrapper
|
|
12
|
+
Requires-Dist: sparqlwrapper>=2.0.0; extra == "sparqlwrapper"
|
|
13
|
+
Dynamic: license-file
|
|
14
|
+
|
|
15
|
+
# rdf4j-python
|
|
16
|
+
|
|
17
|
+
**A modern Python client for the Eclipse RDF4J framework, enabling seamless RDF data management and SPARQL operations from Python applications.**
|
|
18
|
+
|
|
19
|
+
rdf4j-python bridges the gap between Python and the robust [Eclipse RDF4J](https://rdf4j.org/) ecosystem, providing a clean, async-first API for managing RDF repositories, executing SPARQL queries, and handling semantic data with ease.
|
|
20
|
+
|
|
21
|
+
> ⚠️ **Note:** This project is currently under active development and considered **experimental**. Interfaces may change. Use with caution in production environments—and feel free to help shape its future!
|
|
22
|
+
|
|
23
|
+
## Features
|
|
24
|
+
|
|
25
|
+
- **🚀 Async-First Design**: Native support for async/await with synchronous fallback
|
|
26
|
+
- **🔄 Repository Management**: Create, access, and manage RDF4J repositories programmatically
|
|
27
|
+
- **⚡ SPARQL Support**: Execute SELECT, ASK, CONSTRUCT, and UPDATE queries effortlessly
|
|
28
|
+
- **📊 Flexible Data Handling**: Add, retrieve, and manipulate RDF triples and quads
|
|
29
|
+
- **🎯 Multiple Formats**: Support for various RDF serialization formats (Turtle, N-Triples, JSON-LD, etc.)
|
|
30
|
+
- **🛠️ Repository Types**: Memory stores, native stores, HTTP repositories, and more
|
|
31
|
+
- **🔗 Named Graph Support**: Work with multiple graphs within repositories
|
|
32
|
+
- **⚙️ Inferencing**: Built-in support for RDFS and custom inferencing rules
|
|
33
|
+
|
|
34
|
+
## Installation
|
|
35
|
+
|
|
36
|
+
### Prerequisites
|
|
37
|
+
|
|
38
|
+
- Python 3.10 or higher
|
|
39
|
+
- RDF4J Server (for remote repositories) or embedded usage
|
|
40
|
+
|
|
41
|
+
### Install from PyPI
|
|
42
|
+
|
|
43
|
+
```bash
|
|
44
|
+
pip install rdf4j-python
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
### Install with Optional Dependencies
|
|
48
|
+
|
|
49
|
+
```bash
|
|
50
|
+
# Include SPARQLWrapper integration
|
|
51
|
+
pip install rdf4j-python[sparqlwrapper]
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
### Development Installation
|
|
55
|
+
|
|
56
|
+
```bash
|
|
57
|
+
git clone https://github.com/odysa/rdf4j-python.git
|
|
58
|
+
cd rdf4j-python
|
|
59
|
+
uv sync --group dev
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
## Usage
|
|
63
|
+
|
|
64
|
+
### Quick Start
|
|
65
|
+
|
|
66
|
+
```python
|
|
67
|
+
import asyncio
|
|
68
|
+
from rdf4j_python import AsyncRdf4j
|
|
69
|
+
from rdf4j_python.model.repository_config import RepositoryConfig, MemoryStoreConfig, SailRepositoryConfig
|
|
70
|
+
from rdf4j_python.model.term import IRI, Literal
|
|
71
|
+
|
|
72
|
+
async def main():
|
|
73
|
+
# Connect to RDF4J server
|
|
74
|
+
async with AsyncRdf4j("http://localhost:19780/rdf4j-server") as db:
|
|
75
|
+
# Create an in-memory repository
|
|
76
|
+
config = RepositoryConfig(
|
|
77
|
+
repo_id="my-repo",
|
|
78
|
+
title="My Repository",
|
|
79
|
+
impl=SailRepositoryConfig(sail_impl=MemoryStoreConfig(persist=False))
|
|
80
|
+
)
|
|
81
|
+
repo = await db.create_repository(config=config)
|
|
82
|
+
|
|
83
|
+
# Add some data
|
|
84
|
+
await repo.add_statement(
|
|
85
|
+
IRI("http://example.com/person/alice"),
|
|
86
|
+
IRI("http://xmlns.com/foaf/0.1/name"),
|
|
87
|
+
Literal("Alice")
|
|
88
|
+
)
|
|
89
|
+
|
|
90
|
+
# Query the data
|
|
91
|
+
results = await repo.query("SELECT * WHERE { ?s ?p ?o }")
|
|
92
|
+
for result in results:
|
|
93
|
+
print(f"Subject: {result['s']}, Predicate: {result['p']}, Object: {result['o']}")
|
|
94
|
+
|
|
95
|
+
if __name__ == "__main__":
|
|
96
|
+
asyncio.run(main())
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
### Working with Multiple Graphs
|
|
100
|
+
|
|
101
|
+
```python
|
|
102
|
+
from rdf4j_python.model.term import Quad
|
|
103
|
+
|
|
104
|
+
async def multi_graph_example():
|
|
105
|
+
async with AsyncRdf4j("http://localhost:19780/rdf4j-server") as db:
|
|
106
|
+
repo = await db.get_repository("my-repo")
|
|
107
|
+
|
|
108
|
+
# Add data to specific graphs
|
|
109
|
+
statements = [
|
|
110
|
+
Quad(
|
|
111
|
+
IRI("http://example.com/person/bob"),
|
|
112
|
+
IRI("http://xmlns.com/foaf/0.1/name"),
|
|
113
|
+
Literal("Bob"),
|
|
114
|
+
IRI("http://example.com/graph/people")
|
|
115
|
+
),
|
|
116
|
+
Quad(
|
|
117
|
+
IRI("http://example.com/person/bob"),
|
|
118
|
+
IRI("http://xmlns.com/foaf/0.1/age"),
|
|
119
|
+
Literal("30", datatype=IRI("http://www.w3.org/2001/XMLSchema#integer")),
|
|
120
|
+
IRI("http://example.com/graph/demographics")
|
|
121
|
+
)
|
|
122
|
+
]
|
|
123
|
+
await repo.add_statements(statements)
|
|
124
|
+
|
|
125
|
+
# Query specific graph
|
|
126
|
+
graph_query = """
|
|
127
|
+
SELECT * WHERE {
|
|
128
|
+
GRAPH <http://example.com/graph/people> {
|
|
129
|
+
?person ?property ?value
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
"""
|
|
133
|
+
results = await repo.query(graph_query)
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
### Advanced Repository Configuration
|
|
137
|
+
|
|
138
|
+
Here's a more comprehensive example showing repository creation with different configurations:
|
|
139
|
+
|
|
140
|
+
```python
|
|
141
|
+
async def advanced_example():
|
|
142
|
+
async with AsyncRdf4j("http://localhost:19780/rdf4j-server") as db:
|
|
143
|
+
# Memory store with persistence
|
|
144
|
+
persistent_config = RepositoryConfig(
|
|
145
|
+
repo_id="persistent-repo",
|
|
146
|
+
title="Persistent Memory Store",
|
|
147
|
+
impl=SailRepositoryConfig(sail_impl=MemoryStoreConfig(persist=True))
|
|
148
|
+
)
|
|
149
|
+
|
|
150
|
+
# Create and populate repository
|
|
151
|
+
repo = await db.create_repository(config=persistent_config)
|
|
152
|
+
|
|
153
|
+
# Bulk data operations
|
|
154
|
+
data = [
|
|
155
|
+
(IRI("http://example.com/alice"), IRI("http://xmlns.com/foaf/0.1/name"), Literal("Alice")),
|
|
156
|
+
(IRI("http://example.com/alice"), IRI("http://xmlns.com/foaf/0.1/email"), Literal("alice@example.com")),
|
|
157
|
+
(IRI("http://example.com/bob"), IRI("http://xmlns.com/foaf/0.1/name"), Literal("Bob")),
|
|
158
|
+
]
|
|
159
|
+
|
|
160
|
+
statements = [
|
|
161
|
+
Quad(subj, pred, obj, IRI("http://example.com/default"))
|
|
162
|
+
for subj, pred, obj in data
|
|
163
|
+
]
|
|
164
|
+
await repo.add_statements(statements)
|
|
165
|
+
|
|
166
|
+
# Complex SPARQL query
|
|
167
|
+
query = """
|
|
168
|
+
PREFIX foaf: <http://xmlns.com/foaf/0.1/>
|
|
169
|
+
SELECT ?name ?email WHERE {
|
|
170
|
+
?person foaf:name ?name .
|
|
171
|
+
OPTIONAL { ?person foaf:email ?email }
|
|
172
|
+
}
|
|
173
|
+
ORDER BY ?name
|
|
174
|
+
"""
|
|
175
|
+
results = await repo.query(query)
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
For more detailed examples, see the [examples](examples/) directory.
|
|
179
|
+
|
|
180
|
+
## Development
|
|
181
|
+
|
|
182
|
+
### Setting up Development Environment
|
|
183
|
+
|
|
184
|
+
1. **Clone the repository**:
|
|
185
|
+
```bash
|
|
186
|
+
git clone https://github.com/odysa/rdf4j-python.git
|
|
187
|
+
cd rdf4j-python
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
2. **Install development dependencies**:
|
|
191
|
+
```bash
|
|
192
|
+
uv sync --group dev
|
|
193
|
+
```
|
|
194
|
+
|
|
195
|
+
3. **Start RDF4J Server** (for integration tests):
|
|
196
|
+
```bash
|
|
197
|
+
# Using Docker
|
|
198
|
+
docker run -p 19780:8080 eclipse/rdf4j:latest
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
4. **Run tests**:
|
|
202
|
+
```bash
|
|
203
|
+
pytest tests/
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
5. **Run linting**:
|
|
207
|
+
```bash
|
|
208
|
+
ruff check .
|
|
209
|
+
ruff format .
|
|
210
|
+
```
|
|
211
|
+
|
|
212
|
+
### Project Structure
|
|
213
|
+
|
|
214
|
+
```
|
|
215
|
+
rdf4j_python/
|
|
216
|
+
├── _driver/ # Core async driver implementation
|
|
217
|
+
├── model/ # Data models and configurations
|
|
218
|
+
├── exception/ # Custom exceptions
|
|
219
|
+
└── utils/ # Utility functions
|
|
220
|
+
|
|
221
|
+
examples/ # Usage examples
|
|
222
|
+
tests/ # Test suite
|
|
223
|
+
docs/ # Documentation
|
|
224
|
+
```
|
|
225
|
+
|
|
226
|
+
### Contributing
|
|
227
|
+
|
|
228
|
+
We welcome contributions! Here's how to get involved:
|
|
229
|
+
|
|
230
|
+
1. **Fork** the repository on GitHub
|
|
231
|
+
2. **Create** a feature branch (`git checkout -b feature/amazing-feature`)
|
|
232
|
+
3. **Make** your changes and add tests
|
|
233
|
+
4. **Run** the test suite to ensure everything works
|
|
234
|
+
5. **Commit** your changes (`git commit -m 'Add amazing feature'`)
|
|
235
|
+
6. **Push** to your branch (`git push origin feature/amazing-feature`)
|
|
236
|
+
7. **Open** a Pull Request
|
|
237
|
+
|
|
238
|
+
### Running Examples
|
|
239
|
+
|
|
240
|
+
```bash
|
|
241
|
+
# Make sure RDF4J server is running on localhost:19780
|
|
242
|
+
python examples/complete_workflow.py
|
|
243
|
+
python examples/query.py
|
|
244
|
+
```
|
|
245
|
+
|
|
246
|
+
## License
|
|
247
|
+
|
|
248
|
+
This project is licensed under the **BSD 3-Clause License**. See the [LICENSE](LICENSE) file for the full license text.
|
|
249
|
+
|
|
250
|
+
```
|
|
251
|
+
Copyright (c) 2025, Chengxu Bian
|
|
252
|
+
All rights reserved.
|
|
253
|
+
```
|
|
254
|
+
|
|
255
|
+
---
|
|
256
|
+
|
|
257
|
+
**Questions or Issues?** Please feel free to [open an issue](https://github.com/odysa/rdf4j-python/issues) on GitHub.
|
|
258
|
+
|
|
259
|
+
**⭐ Star this repo** if you find it useful!
|
|
@@ -1,23 +1,23 @@
|
|
|
1
1
|
rdf4j_python/__init__.py,sha256=E8gojaWuLHo2AfNn5HBc5cF7K8_dK2jOBcZaH_qoZs4,347
|
|
2
2
|
rdf4j_python/_client/__init__.py,sha256=L5q5RTHXCNyHp2WNP4xTemGXNntUW4RF_QJPoCWciUQ,98
|
|
3
|
-
rdf4j_python/_client/_client.py,sha256=
|
|
3
|
+
rdf4j_python/_client/_client.py,sha256=0jlxEdmg9uwoUYhaLJQq0zD21ZlqyoaAL4vkTa5dz3o,8083
|
|
4
4
|
rdf4j_python/_driver/__init__.py,sha256=au0r15mQBVaJkqBknw9CoVswe7_rPPFs1wFWI_ttdy4,224
|
|
5
5
|
rdf4j_python/_driver/_async_named_graph.py,sha256=BqJRpN-JzGpvlSnWY2RrM5TrnIHg6W4PortZ0y-4mgw,2685
|
|
6
|
-
rdf4j_python/_driver/_async_rdf4j_db.py,sha256=
|
|
7
|
-
rdf4j_python/_driver/_async_repository.py,sha256=
|
|
6
|
+
rdf4j_python/_driver/_async_rdf4j_db.py,sha256=POJ2-5EiyFOjX6ykjxbm0RH7yjtU6mXCY2PlVYidLDI,4497
|
|
7
|
+
rdf4j_python/_driver/_async_repository.py,sha256=bNO4m_0u0uNjz14vXlsyzkVYLUy5cpCSNnvEZg4fG3o,15364
|
|
8
8
|
rdf4j_python/exception/__init__.py,sha256=PFdUyIMsHIL5e2P2z33Qr2pwlUAJVI0G5T8114W4-1A,83
|
|
9
9
|
rdf4j_python/exception/repo_exception.py,sha256=WXlfIYzOYfNU8LpwtOct9fAZADR-P3cZx4jAX9v_HaA,704
|
|
10
10
|
rdf4j_python/model/__init__.py,sha256=wHboqZX2bN3AubXvWRwKOWwnrefpeiiB_nnry2Ba_a4,176
|
|
11
11
|
rdf4j_python/model/_namespace.py,sha256=6iOvPc2Z6XFY44wmVucQCrjZbFuxdBtoTfDq_bSHJS0,3854
|
|
12
12
|
rdf4j_python/model/_repository_info.py,sha256=fdKwjoQz6_D95Q8uZEuEYhXEUeqElsdBkHRCRRNxjzM,2010
|
|
13
|
-
rdf4j_python/model/repository_config.py,sha256=
|
|
13
|
+
rdf4j_python/model/repository_config.py,sha256=USaWQ_C8UlnKSnL3coiXFly0TjOvapS6OMy3Nt9eVlg,22482
|
|
14
14
|
rdf4j_python/model/term.py,sha256=JBxndQESR2KEY6y9s6TqoELUQaegKcIUO0ctR818QaA,508
|
|
15
15
|
rdf4j_python/model/vocabulary.py,sha256=Yam0F_YNlO-7wDi2fc0DkAqIKB4ZqCpqq56wKRrFAcw,307
|
|
16
16
|
rdf4j_python/utils/__init__.py,sha256=LAyzkmO5QOIjJogQE1m4Eszwb2cCU8ytKRfhjAGoraw,34
|
|
17
17
|
rdf4j_python/utils/const.py,sha256=HKH9ZGe7m_dvMx1RwT6zhu2HUkvwOX2Y4e8vQFs3uE8,849
|
|
18
18
|
rdf4j_python/utils/helpers.py,sha256=4ubvrx3OV_0Y2_YECNIJhkJUB-JthdCJA8d6Hz_G_kE,506
|
|
19
|
-
rdf4j_python-0.1.
|
|
20
|
-
rdf4j_python-0.1.
|
|
21
|
-
rdf4j_python-0.1.
|
|
22
|
-
rdf4j_python-0.1.
|
|
23
|
-
rdf4j_python-0.1.
|
|
19
|
+
rdf4j_python-0.1.5.dist-info/licenses/LICENSE,sha256=sGjA7CzoCG1LVlkh0ZB76ZdgWHVpUFegLU41YYDkGIA,1499
|
|
20
|
+
rdf4j_python-0.1.5.dist-info/METADATA,sha256=cMzk7E91qtPK_l_8EQJbkDYOsN5twDUotZWcIHNyiIo,7968
|
|
21
|
+
rdf4j_python-0.1.5.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
|
|
22
|
+
rdf4j_python-0.1.5.dist-info/top_level.txt,sha256=Lf2K8d8WcEkmvo5giLGuZ3gl20rNEwMssyAFBeVzbCs,13
|
|
23
|
+
rdf4j_python-0.1.5.dist-info/RECORD,,
|
|
@@ -1,77 +0,0 @@
|
|
|
1
|
-
Metadata-Version: 2.4
|
|
2
|
-
Name: rdf4j-python
|
|
3
|
-
Version: 0.1.3
|
|
4
|
-
Summary: The Python client for RDF4J
|
|
5
|
-
Author-email: Chengxu Bian <cbian564@gmail.com>
|
|
6
|
-
Requires-Python: >=3.10
|
|
7
|
-
Description-Content-Type: text/markdown
|
|
8
|
-
License-File: LICENSE
|
|
9
|
-
Requires-Dist: httpx>=0.28.1
|
|
10
|
-
Requires-Dist: pyoxigraph>=0.4.10
|
|
11
|
-
Dynamic: license-file
|
|
12
|
-
|
|
13
|
-
# 🐍 rdf4j-python
|
|
14
|
-
|
|
15
|
-
**A Pythonic interface to the powerful Java-based [Eclipse RDF4J](https://rdf4j.org/) framework.**
|
|
16
|
-
|
|
17
|
-
> ⚠️ **Note:** This project is currently under active development and considered **experimental**. Interfaces may change. Use with caution in production environments—and feel free to help shape its future!
|
|
18
|
-
|
|
19
|
-
✅ **Supports both asynchronous (`async/await`) and synchronous programming styles.**
|
|
20
|
-
|
|
21
|
-
## 🌐 Overview
|
|
22
|
-
|
|
23
|
-
`rdf4j-python` bridges the gap between Python applications and the [Eclipse RDF4J](https://rdf4j.org/) framework, enabling seamless interaction with RDF4J repositories directly from Python. This integration allows developers to leverage RDF4J's robust capabilities for managing RDF data and executing SPARQL queries without leaving the Python ecosystem.
|
|
24
|
-
|
|
25
|
-
## 🚀 Features
|
|
26
|
-
|
|
27
|
-
- **Seamless Integration**: Interact with RDF4J repositories using Pythonic constructs.
|
|
28
|
-
- **SPARQL Support**: Execute SPARQL queries and updates effortlessly.
|
|
29
|
-
- **Repository Management**: Create, access, and manage RDF4J repositories programmatically.
|
|
30
|
-
- **Data Handling**: Add and retrieve RDF triples with ease.
|
|
31
|
-
- **Format Flexibility**: Support for various RDF serialization formats.
|
|
32
|
-
|
|
33
|
-
## 📦 Installation
|
|
34
|
-
|
|
35
|
-
Install via pip:
|
|
36
|
-
|
|
37
|
-
```bash
|
|
38
|
-
pip install rdf4j-python
|
|
39
|
-
```
|
|
40
|
-
|
|
41
|
-
## 🧪 Usage (Async)
|
|
42
|
-
|
|
43
|
-
Here's a basic example of how to use `rdf4j-python` to create an in-memory sail repository
|
|
44
|
-
|
|
45
|
-
```python
|
|
46
|
-
async with AsyncRdf4j("http://localhost:19780/rdf4j-server") as db:
|
|
47
|
-
repo_config = (
|
|
48
|
-
RepositoryConfig.Builder()
|
|
49
|
-
.repo_id("example-repo")
|
|
50
|
-
.title("Example Repository")
|
|
51
|
-
.sail_repository_impl(
|
|
52
|
-
MemoryStoreConfig.Builder().persist(False).build(),
|
|
53
|
-
)
|
|
54
|
-
.build()
|
|
55
|
-
)
|
|
56
|
-
repo = await db.create_repository(config=repo_config)
|
|
57
|
-
await repo.add_statement(
|
|
58
|
-
IRI("http://example.com/subject"),
|
|
59
|
-
IRI("http://example.com/predicate"),
|
|
60
|
-
Literal("test_object"),
|
|
61
|
-
)
|
|
62
|
-
await repo.get_statements(subject=IRI("http://example.com/subject"))
|
|
63
|
-
```
|
|
64
|
-
|
|
65
|
-
For more detailed examples, refer to the [examples](https://github.com/odysa/rdf4j-python/tree/main/examples) directory.
|
|
66
|
-
|
|
67
|
-
## 🤝 Contributing
|
|
68
|
-
|
|
69
|
-
We welcome contributions and feedback! If you'd like to help improve this project:
|
|
70
|
-
|
|
71
|
-
- Fork the repo and submit a pull request
|
|
72
|
-
- Open an issue for bugs, feature ideas, or discussions
|
|
73
|
-
- ⭐ Star the repo if you find it useful!
|
|
74
|
-
|
|
75
|
-
## 📄 License
|
|
76
|
-
|
|
77
|
-
This project is licensed under the MIT License. See the [LICENSE](https://github.com/odysa/rdf4j-python/blob/main/LICENSE) file for details.
|
|
File without changes
|
|
File without changes
|