OpenDMA REST client to access OpenDMA repositories via REST
Project description
OpenDMA REST client for Python
Please see OpenDMA API for Python for an introduction to OpenDMA and it's Python API.
Provides an OpenDMA Adaptor consuming the OpenDMA REST API.
Installation
This project is available on PyPI. You can simply install it with pip:
pip install opendma-remote
Usage
Import this module and use the connect function to establish an OdmaSession
with a REST-ful OpenDMA service:
import opendma.remote
session = opendma.remote.connect(endpoint="http://127.0.0.1:8080/opendma/",
username="user",
password="secret")
Example
Run the tutorial REST service docker container:
docker run -p 8080:8080 ghcr.io/opendma/tutorial-xmlrepo:0.8
It will provide the tutorial xml repository. Make sure that this service is available
by opening
http://localhost:8080/opendma
in a web browser.
Troubleshooting
If the GitHub Container Registry (ghcr.io) is blocked in your environment, you can use our mirror on Docker Hub:
docker run -p 8080:8080 opendma/tutorial-xmlrepo:latest
If the local port 8080 is already in use, you can map to a different port, e.g. 8090:
docker run -p 8090:8080 ghcr.io/opendma/tutorial-xmlrepo:latest
To run in deamon mode in the background:
docker run -d --name opendma-tutorial-xmlrepo -p 8080:8080 ghcr.io/opendma/tutorial-xmlrepo:latest
The following python application will establish a connection to this service and print out the entire repository:
from typing import Optional
from opendma.api import OdmaType, OdmaQName, OdmaId, OdmaObject, OdmaClass, OdmaPropertyInfo, OdmaFolder, OdmaAssociation, OdmaDocument, OdmaContentElement, OdmaDataContentElement, OdmaContent, OdmaVersionCollection, OdmaServiceException
import opendma.remote
def printClassTree(clazz: OdmaClass, indent: int = 0) -> None:
print(f"{' ' * indent}{clazz.get_qname()}")
aspects = clazz.get_aspects()
if aspects is not None:
for aspect in aspects:
print(f"{' ' * indent} @{aspect.get_qname()}")
subclasses = clazz.get_sub_classes()
if subclasses is not None:
for subclass in subclasses:
printClassTree(subclass, indent + 1)
def printObjectInfo(obj: OdmaObject, indent: int, include_props: bool, expand_special: bool):
print(f"{' ' * indent}{obj.get_id()} {obj.get_odma_class().get_qname()}")
if not include_props:
return
properties = obj.get_odma_class().get_properties()
indent = indent + 1
for propinfo in properties:
pi: OdmaPropertyInfo = propinfo
prop = obj.get_property(pi.get_qname())
type = prop.get_type()
value = prop.get_value()
if prop.is_multi_value():
if type == OdmaType.REFERENCE:
print(f"{' ' * indent}{pi.get_qname()}=")
for pos, item in enumerate(value):
id = item.get_id()
if '/' in str(id):
printObjectInfo(item, indent+1, True, False)
else:
print(f"{' ' * (indent+3)}* Object<{id}>")
else:
print(f"{' ' * indent}{pi.get_qname()}=")
for pos, item in enumerate(value):
print(f"{' ' * (indent+3)}[{pos}] {item}")
else:
if value == None:
print(f"{' ' * indent}{pi.get_qname()}=None")
else:
if type == OdmaType.REFERENCE:
if expand_special and (isinstance(value, OdmaVersionCollection) or isinstance(value, OdmaContentElement)):
print(f"{' ' * indent}{pi.get_qname()}=")
printObjectInfo(value, indent+1, True, False)
else:
print(f"{' ' * indent}{pi.get_qname()}=Object<{value.get_id()}>")
elif type == OdmaType.CONTENT:
cnt: OdmaContent = value
stream = cnt.get_stream()
data = stream.read(25)
hex_bytes = ' '.join(f'{b:02x}' for b in data)
print(f"{' ' * indent}{pi.get_qname()}= {cnt.get_size()} bytes; first 25 bytes: {hex_bytes}")
else:
print(f"{' ' * indent}{pi.get_qname()}={value}")
def printFolderTree(folder: OdmaFolder, indent: int = 0) -> None:
print(f"{' ' * indent}{folder.get_title()}")
associations = folder.get_associations()
if associations is not None:
for association in associations:
assoc: OdmaAssociation = association
print(f"{' ' * indent} -{assoc.get_name()}")
printObjectInfo(assoc.get_containable(), indent + 2, True, True)
subfolders = folder.get_sub_folders()
if subfolders is not None:
for subfolder in subfolders:
printFolderTree(subfolder, indent + 1)
def printRepo(endpoint: str, username: Optional[str] = None, password: Optional[str] = None, includeClassTree: bool = True, includeFolderTree: bool = True) -> None:
print(f"Trying to connect...")
session = opendma.remote.connect(endpoint=endpoint, username=username, password=password, requestTraceLevel = 0)
print(f"Connected.")
print(f"Repositories: {session.get_repository_ids()}")
repoId = session.get_repository_ids()[0]
print(f"Trying to get repository {repoId}...")
repo = session.get_repository(repoId)
print(f"Got repository.")
print(f" Id: {repo.get_id()}")
print(f" Display Name: {repo.get_display_name()}")
if includeClassTree:
print(f"")
print(f"Class tree:")
rootClass = repo.get_root_class()
printClassTree(rootClass)
if includeFolderTree:
print(f"")
print(f"Folder tree:")
rootFolder = repo.get_root_folder()
if rootFolder is None:
print(f"No root folder is in this repository")
else:
printFolderTree(rootFolder)
if __name__ == "__main__":
printRepo(endpoint="http://127.0.0.1:8080/opendma/")
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file opendma_remote-0.8.0.tar.gz.
File metadata
- Download URL: opendma_remote-0.8.0.tar.gz
- Upload date:
- Size: 11.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.2
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
351008a5439792d43a18c37a6b5234fb363a2f80752970d81b8b4bf6567bf0ed
|
|
| MD5 |
427d71780c89ab84e671de2be69ecbfb
|
|
| BLAKE2b-256 |
c0d26786b209084785afa22e10e5503c2c9b5ff25c9e8d1a491f74ef11736103
|
File details
Details for the file opendma_remote-0.8.0-py3-none-any.whl.
File metadata
- Download URL: opendma_remote-0.8.0-py3-none-any.whl
- Upload date:
- Size: 9.6 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.2
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
4a19deeb744636c6f45c605691f594569e02f6f5fee0073f84fa30e4ed008129
|
|
| MD5 |
284ed63f439ee2c8f7788d3be94e5122
|
|
| BLAKE2b-256 |
6841e3b85bc9ff532d922ce88ca1089fee611944f8694b8900a741d0d9eebf2b
|