Python bindings for Enki's Rust agent runtime.
Project description
enki-py
Python bindings for Enki's Rust agent runtime.
enki-py exposes two layers:
- A high-level Python API built around
AgentandMultiAgentRuntime - The lower-level native bindings generated from the Rust runtime, including workflow APIs
The package is designed for Python-first usage without giving up the native runtime features that already exist in the Rust core.
Requirements
- Python
>=3.8 - A supported model string such as
openai::gpt-4o,anthropic::claude-sonnet-4-6, orollama::qwen3.5:latest
Install
Published package:
pip install enki-py
With the built-in LiteLLM adapter:
pip install "enki-py[litellm]"
Using uv:
uv add enki-py
uv add "enki-py[litellm]"
What It Exports
High-level Python API
The main Python-facing exports are:
AgentAgentLoopRequestAgentLoopResultAgentRunResultExecutionStepToolToolRegistryRunContextMemoryBackendMemoryModuleMemoryEntryMemoryKindMultiAgentRuntimeMultiAgentMemberAgentCardLiteLlmProviderLlmProviderBackend
Low-level native bindings
The generated module is also re-exported, so lower-level runtime types remain available when you want to work closer to the Rust layer. Commonly used native types include:
EnkiAgentEnkiWorkflowRuntimeEnkiToolandEnkiToolSpecEnkiMemoryEntryEnkiMemoryModule
Agent API
Agent is the main Python entrypoint. Its constructor supports:
model: required provider and model stringdeps_type: optional dependency type used withRunContextinstructions: system guidance / prompt preambleagentic_loop: optional prompt-level loop instructionsagent_loop_handler: optional Python callback that overrides the runtime loopname: display name for the agentmax_iterations: iteration cap for the runtime loopworkspace_home: optional workspace root for persisted runtime statetools: optional list of pre-registeredToolobjectstool_registry: optional reusableToolRegistrymemories: optional list ofMemoryModuleobjectsllm: optional Python-side LLM backend or callback
Main methods:
run(...): async single-agent executionrun_sync(...): sync wrapper aroundrun(...)set_agent_loop_handler(...)clear_agent_loop_handler(...)tool_plain(...): decorator for plain Python toolstool(...): decorator for tools that receiveRunContextregister_tool(...)connect_tool_registry(...)register_memory(...)as_workflow_agent(...): converts the wrapper into a workflow-configured low-level agent
The result of run(...) or run_sync(...) is AgentRunResult, which contains:
output: final model response textsteps:ExecutionStepentries describing runtime progress
Both run(...) and run_sync(...) accept:
session_id: optional explicit session iddeps: optional dependency object passed intoRunContexton_step: optional callback for streaming step visibility
Basic Agent
Synchronous example:
import uuid
from enki_py import Agent
agent = Agent(
"anthropic::claude-sonnet-4-6",
name="Simple Agent",
instructions="Answer clearly and keep responses short.",
)
result = agent.run_sync(
"Explain what this Enki Python example demonstrates.",
session_id=f"simple-agent-{uuid.uuid4()}",
)
print(result.output)
for step in result.steps:
print(f"{step.index}. [{step.phase}] {step.kind}: {step.detail}")
Async version:
import asyncio
from enki_py import Agent
async def main() -> None:
agent = Agent(
"ollama::qwen3.5:latest",
name="Async Agent",
instructions="Answer clearly and keep responses short.",
)
result = await agent.run("What does enki-py provide?")
print(result.output)
asyncio.run(main())
Tools
The high-level wrapper lets you register Python functions directly as tools.
@agent.tool_plain
Use this when the tool only needs its declared arguments:
from enki_py import Agent
agent = Agent(
"ollama::qwen3.5:latest",
name="Researcher",
instructions="Use tools when they help answer factual questions.",
)
@agent.tool_plain
def lookup_example_topics(topic: str) -> str:
"""Return a canned fact for an example topic."""
facts = {
"memory": "Memory lets the agent persist and recall useful session context.",
"tools": "Tools let the agent call Python functions to fetch or compute structured results.",
"multi-agent": "Multi-agent runtimes let a coordinator route work to specialized agents.",
}
return facts.get(topic.lower(), f"No prepared fact exists for '{topic}'.")
@agent.tool
Use this when the tool should receive a RunContext with typed dependencies:
from dataclasses import dataclass
from enki_py import Agent, RunContext
@dataclass
class AppDeps:
project_name: str
agent = Agent(
"ollama::qwen3.5:latest",
deps_type=AppDeps,
name="Context Agent",
instructions="Use the provided context when it helps answer.",
)
@agent.tool
def project_name(ctx: RunContext[AppDeps]) -> str:
"""Return the active project name from runtime dependencies."""
return ctx.deps.project_name
Tool schemas are inferred from Python signatures and type annotations. Required parameters come from arguments without defaults, and optional parameters come from arguments with defaults.
If you need lower-level control, you can also build Tool(...) values directly and register them with register_tool(...).
Reusable ToolRegistry
If you want to manage a shared set of tools separately from a single agent, build a ToolRegistry and connect it when needed:
from enki_py import Agent, ToolRegistry
registry = ToolRegistry()
@registry.tool_plain
def lookup_release(version: str) -> str:
"""Return a canned release note."""
return f"Release {version} is ready."
agent = Agent(
"ollama::qwen3.5:latest",
name="Registry Agent",
instructions="Use connected tools when they help.",
)
agent.connect_tool_registry(registry)
You can also pass tool_registry=registry to Agent(...) during construction.
This is the cleanest path when multiple agents should share the same tool catalog or when you want to prepare tools separately from agent creation.
Memory
enki-py supports Python-defined memory modules through MemoryBackend and MemoryModule.
Implement MemoryBackend when you want custom record and recall behavior:
from dataclasses import dataclass, field
from time import time_ns
from enki_py import MemoryBackend, MemoryEntry, MemoryKind
@dataclass
class SessionMemory(MemoryBackend):
name: str = "session_memory"
_entries: dict[str, list[MemoryEntry]] = field(default_factory=dict)
def record(self, session_id: str, user_msg: str, assistant_msg: str) -> None:
entries = self._entries.setdefault(session_id, [])
entries.append(
MemoryEntry(
key=f"{session_id}-{len(entries)}",
content=f"User: {user_msg}\nAssistant: {assistant_msg}",
kind=MemoryKind.RECENT_MESSAGE,
relevance=1.0,
timestamp_ns=time_ns(),
)
)
def recall(self, session_id: str, query: str, max_entries: int) -> list[MemoryEntry]:
entries = self._entries.get(session_id, [])
return entries[-max_entries:]
def flush(self, session_id: str) -> None:
return None
Register it like this:
memory = SessionMemory()
agent = Agent(
"ollama::qwen3.5:latest",
memories=[memory.as_memory_module()],
)
Supported memory kinds:
MemoryKind.RECENT_MESSAGEMemoryKind.SUMMARYMemoryKind.ENTITYMemoryKind.PREFERENCE
Memory callbacks may be synchronous or async def coroutines.
Multi-Agent Runtime
MultiAgentRuntime wires multiple Agent instances together and installs the coordination tools used for agent discovery and delegation.
Available methods:
registry()discover(...)process(...)process_sync(...)
The runtime automatically installs two reserved tools on member agents:
discover_agentsdelegate_task
Minimal example:
from enki_py import Agent, MultiAgentMember, MultiAgentRuntime
coordinator = Agent(
"ollama::qwen3.5:latest",
name="Coordinator",
instructions=(
"Use discover_agents first. "
"Delegate research work to the researcher with delegate_task."
),
)
researcher = Agent(
"ollama::qwen3.5:latest",
name="Researcher",
instructions="Answer delegated questions clearly and briefly.",
)
runtime = MultiAgentRuntime(
[
MultiAgentMember(
agent_id="coordinator",
agent=coordinator,
capabilities=["planning", "orchestration"],
),
MultiAgentMember(
agent_id="researcher",
agent=researcher,
capabilities=["research"],
),
]
)
result = runtime.process_sync(
"coordinator",
"Use discover_agents first, then delegate to the researcher.",
session_id="simple-multi-agent-example",
)
print(result.output)
Repository examples:
Workflow Runtime
For workflow execution, the lower-level EnkiWorkflowRuntime is the main entrypoint. A common pattern is:
- Create Python
Agentwrappers - Convert them with
as_workflow_agent(agent_id=..., capabilities=[...]) - Provide JSON task definitions and JSON workflow definitions
- Start and inspect runs through the workflow runtime
Methods used in the checked-in Python examples include:
list_workflows_json()list_runs_json()inspect_json(run_id)start_json(payload_json)resume_json(run_id)submit_intervention_json(run_id, intervention_id, response)
Workflow example:
import asyncio
import json
from pathlib import Path
import enki_py
WORKSPACE_HOME = Path("./example/enki-py/.enki-workflow")
MODEL = "ollama::qwen3.5:latest"
async def main() -> None:
researcher = enki_py.Agent(
MODEL,
name="Researcher",
instructions="Return short factual notes.",
workspace_home=str(WORKSPACE_HOME),
)
writer = enki_py.Agent(
MODEL,
name="Writer",
instructions="Turn notes into a concise summary.",
workspace_home=str(WORKSPACE_HOME),
)
runtime = enki_py.EnkiWorkflowRuntime(
agents=[
researcher.as_workflow_agent(agent_id="researcher", capabilities=["research"]),
writer.as_workflow_agent(agent_id="writer", capabilities=["writing"]),
],
tasks_json=[],
workflows_json=[],
workspace_home=str(WORKSPACE_HOME),
)
print(json.loads(await runtime.list_workflows_json()))
asyncio.run(main())
For a complete runnable version with task and edge definitions, see example/enki-py/agent_workflow.py.
Human Intervention
Workflow runs can pause for human input and then resume from persisted state.
Two built-in patterns are demonstrated in the repository examples:
human_gateworkflow nodes that pause and wait for a human response- task nodes with
failure_policy: "pause_for_intervention"that convert a failure into a human resolution step
The runtime interaction loop is:
start_json(...)starts the workflow and may return a paused responseinspect_json(run_id)exposespending_interventionssubmit_intervention_json(run_id, intervention_id, response)resolves the interventionresume_json(run_id)continues the persisted run
See example/enki-py/human_intervention_workflow.py.
Custom LLM Providers
You can keep model execution on the Python side by passing either:
- an instance of
LlmProviderBackend - a compatible Python callable matching the LLM completion shape
The built-in LiteLlmProvider is the default adapter for LiteLLM-backed usage. It is useful when you want:
- provider-specific configuration in Python
- LiteLLM-managed credentials or routing
- a Python extension point without changing Rust code
Notes from the current implementation:
LiteLlmProviderraises a clear error iflitellmis not installed- for Ollama, the default base URL comes from
OLLAMA_URLor falls back tohttp://127.0.0.1:11434 ENKI_LITELLM_TIMEOUTcontrols the request timeout used by the adapter- Ollama tool calling is only forwarded when
ENKI_OLLAMA_TOOLSis truthy
The repository workflow example also includes a custom OllamaProvider implementation in example/enki-py/agent_workflow.py.
Custom Agentic Loop
There are two different customization levels.
Use agentic_loop= when you want to keep the normal Rust runtime loop but replace the default loop instructions that the model sees:
from enki_py import Agent
agent = Agent(
"anthropic::claude-sonnet-4-6",
name="Custom Agentic Loop",
instructions="Answer clearly and keep responses short.",
agentic_loop=(
"1. Understand the user request.\n"
"2. Decide whether a tool is necessary before acting.\n"
"3. If you use a tool, summarize what you learned.\n"
"4. Verify that the answer is complete.\n"
"5. Return the final response."
),
)
Use agent_loop_handler= when you want Python to own the turn-by-turn control flow:
from enki_py import Agent, AgentLoopRequest, AgentLoopResult, ExecutionStep
def custom_loop(request: AgentLoopRequest[None]) -> AgentLoopResult:
return AgentLoopResult(
output=f"Handled in Python for: {request.user_message}",
steps=[
ExecutionStep(
index=1,
phase="Custom",
kind="final",
detail="Returned a final answer from Python",
)
],
)
agent = Agent(
"ollama::qwen3.5:latest",
instructions="Answer clearly and keep responses short.",
agent_loop_handler=custom_loop,
)
The loop request includes:
session_iduser_messagesystem_promptmessagestoolsagent_dirworkspace_dirsessions_dirmodelmax_iterationsdeps
You can also update the loop handler after construction with:
agent.set_agent_loop_handler(handler)agent.clear_agent_loop_handler()
Repository examples:
example/enki-py/custom_agentic_loop.pyexample/enki-py/react_custom_agentic_loop.pyexample/enki-py/compare_agent_loops.py
Running The Examples
After building the local package with maturin develop, you can run the checked-in examples from the repository root:
python example\enki-py\simple_agent.py
python example\enki-py\simple_agent_ollama.py
python example\enki-py\tool_registry.py
python example\enki-py\simple_multi_agent.py
python example\enki-py\multi_agent_with_memory_and_tools.py
python example\enki-py\agent_workflow.py
python example\enki-py\human_intervention_workflow.py
python example\enki-py\custom_agentic_loop.py
python example\enki-py\react_custom_agentic_loop.py
python example\enki-py\compare_agent_loops.py
Model notes:
simple_agent.pyusesanthropic::claude-sonnet-4-6simple_agent_ollama.pyusesollama::qwen3.5- several other checked-in examples use
ollama::qwen3.5:latest agent_workflow.pyreadsENKI_MODELand falls back toollama::qwen3.5:latest
Make sure the selected provider and model are available in your local environment before running the examples.
Development
From crates/bindings/enki-py:
pip install maturin
maturin develop
pytest python/tests
Useful commands:
maturin develop: build the Rust extension and install the package in editable formpytest python/tests: run the Python-side tests and examples under test coverage
Project Layout
crates/bindings/enki-py/
|-- Cargo.toml
|-- pyproject.toml
|-- python/enki_py/
|-- python/tests/
`-- src/
src/: Rust UniFFI binding implementationpython/enki_py/: Python wrapper and generated native modulepython/tests/: Python-side tests and usage coverage
Related Docs
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 Distributions
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 enki_py-0.5.81.tar.gz.
File metadata
- Download URL: enki_py-0.5.81.tar.gz
- Upload date:
- Size: 426.8 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
13873d1cb26ef60d972e157af416daed7552832595fc2d734b8a8bf4aefb9fbb
|
|
| MD5 |
e39e2f13b44188a58e940ff460ed3787
|
|
| BLAKE2b-256 |
521753a354d084a63fdd292ea04b57617f58dd27a9f9f44bebeae3842115b2e5
|
File details
Details for the file enki_py-0.5.81-py3-none-win_arm64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-win_arm64.whl
- Upload date:
- Size: 1.5 MB
- Tags: Python 3, Windows ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
9f698ac593c2549b507c7657f847240aa60155acdfa3699091a9b507c19ac466
|
|
| MD5 |
5c9da6b4f7c467eb656b10d61607f084
|
|
| BLAKE2b-256 |
981cf6284a3fc079a270d8b3f5f1da331c75d3ed374b223154c64b5995b84064
|
File details
Details for the file enki_py-0.5.81-py3-none-win_amd64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-win_amd64.whl
- Upload date:
- Size: 1.5 MB
- Tags: Python 3, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
8a7a29aec7780b9bead6f131e7e7c3fb4ba0937af347c04d56f6dbf31f4fe73f
|
|
| MD5 |
ef01aaa7efe80463f8bf1d32391b44c5
|
|
| BLAKE2b-256 |
a568016a270c796fac096d382f9f29875344499428b4a9c97bfa7a8554f5b99b
|
File details
Details for the file enki_py-0.5.81-py3-none-win32.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-win32.whl
- Upload date:
- Size: 1.4 MB
- Tags: Python 3, Windows x86
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
9e14464faf82789d3baee028eb7940560ca42ec6553ebb1b9753f924e21dd4a9
|
|
| MD5 |
3d4fc8cddba82ee42d0b8987e1ac69b0
|
|
| BLAKE2b-256 |
d2f078e3c8bf6115d84e2d66469a4e1621a0af1c57717d26e572af4b1806a625
|
File details
Details for the file enki_py-0.5.81-py3-none-musllinux_1_2_x86_64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-musllinux_1_2_x86_64.whl
- Upload date:
- Size: 1.7 MB
- Tags: Python 3, musllinux: musl 1.2+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a7d77cf2d271be8eecbd4008e4bf506017d2fa340dda8837f8bc958d4f12b3b6
|
|
| MD5 |
874ebc7ec3a8202dcd217944dcb76bab
|
|
| BLAKE2b-256 |
ba9be4826fcf9700b1b24d11fbd7aa2f2a7d7630154ead8271760505989e44a2
|
File details
Details for the file enki_py-0.5.81-py3-none-musllinux_1_2_i686.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-musllinux_1_2_i686.whl
- Upload date:
- Size: 1.7 MB
- Tags: Python 3, musllinux: musl 1.2+ i686
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e6f179e32615ec9e3065f8c68e7772c7d7d90d2f58bde2e6103fdbff45fdf015
|
|
| MD5 |
c1ad57d227ee98b69503f60fa7b245a8
|
|
| BLAKE2b-256 |
5f5b022326355dd1f51ecf63c2f58676b6be3750104c11d968b939579be73af1
|
File details
Details for the file enki_py-0.5.81-py3-none-musllinux_1_2_armv7l.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-musllinux_1_2_armv7l.whl
- Upload date:
- Size: 1.7 MB
- Tags: Python 3, musllinux: musl 1.2+ ARMv7l
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
71b301188ed019c8a082321e1731c38bb4efcaa570305a7da85e82c86855097b
|
|
| MD5 |
9fbd5e7304c470ac1ea70864d69dfdd6
|
|
| BLAKE2b-256 |
5f388cf929657a355ab251792b7401a8c590f84cbf3a8dd9a1a6a1aca63c9386
|
File details
Details for the file enki_py-0.5.81-py3-none-musllinux_1_2_aarch64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-musllinux_1_2_aarch64.whl
- Upload date:
- Size: 1.6 MB
- Tags: Python 3, musllinux: musl 1.2+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
5c938daf69a66fe19590bcaf9195038f07d364b1c9bc3747832dc1f66b8485c5
|
|
| MD5 |
c7deaa5e77e6d06fb4909fe01233dd98
|
|
| BLAKE2b-256 |
64374365847e0591c006556aee866407c7e154f91ece39698532996eb40c4f8d
|
File details
Details for the file enki_py-0.5.81-py3-none-manylinux_2_28_x86_64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-manylinux_2_28_x86_64.whl
- Upload date:
- Size: 1.5 MB
- Tags: Python 3, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
f118546908b6b2dd75448e26a9bf3e995fbcc9c6ffd3d0f5f695256c084aa844
|
|
| MD5 |
9ad35469e134c7efed13cbd505195414
|
|
| BLAKE2b-256 |
6258731aef7bf8a62581365c722f2886a238cd1e7cbafef3705c757ad9c9b141
|
File details
Details for the file enki_py-0.5.81-py3-none-manylinux_2_28_s390x.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-manylinux_2_28_s390x.whl
- Upload date:
- Size: 1.6 MB
- Tags: Python 3, manylinux: glibc 2.28+ s390x
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
580134137e1a68b2830011fd012b50dc14fe40dae0927077d785bd1b7be8c237
|
|
| MD5 |
f73904cb72bd558aa40c6a91d5421114
|
|
| BLAKE2b-256 |
98f16e43bcf19b0e671020c041cf7f8a42cee3d8903a2a3331343bc089ec685e
|
File details
Details for the file enki_py-0.5.81-py3-none-manylinux_2_28_ppc64le.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-manylinux_2_28_ppc64le.whl
- Upload date:
- Size: 1.6 MB
- Tags: Python 3, manylinux: glibc 2.28+ ppc64le
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0ea30872bed767e951b4874cc51f652d588cfdd236d843d9b757cc432cfc0f18
|
|
| MD5 |
a9b59f924879c6c2f67286746e7e9a80
|
|
| BLAKE2b-256 |
2366b68ebab0478a05679fbe9ed11d15b949172c7eb41f1a7440339477bd4b92
|
File details
Details for the file enki_py-0.5.81-py3-none-manylinux_2_28_i686.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-manylinux_2_28_i686.whl
- Upload date:
- Size: 1.5 MB
- Tags: Python 3, manylinux: glibc 2.28+ i686
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
26bc12051b36bac56bab6da093fbbe4ba1c5e5503486b28183c856f2e8341629
|
|
| MD5 |
fd7b7365898c633ea2e5879cd20f08ad
|
|
| BLAKE2b-256 |
2446a8ef4266eb436c8ef8fd7d55bbaf732316b4016897debd1dfd126193a159
|
File details
Details for the file enki_py-0.5.81-py3-none-manylinux_2_28_armv7l.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-manylinux_2_28_armv7l.whl
- Upload date:
- Size: 1.4 MB
- Tags: Python 3, manylinux: glibc 2.28+ ARMv7l
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
c819d3ef0bf10f7dabb36025d77066866b37c5c0a868a44c354cfc2cbe2efb50
|
|
| MD5 |
12f6bd395d3b9007e424f791bcca3f85
|
|
| BLAKE2b-256 |
bcc54f2863a9a2fc1c5b94ea8bd63137a811e2affe3f129779ba1902bfc95795
|
File details
Details for the file enki_py-0.5.81-py3-none-manylinux_2_28_aarch64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-manylinux_2_28_aarch64.whl
- Upload date:
- Size: 1.4 MB
- Tags: Python 3, manylinux: glibc 2.28+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
8a0eb37e4caa02a92a5d7ec66c3705d59e300c1db3803db7b82a90f74dbf3e75
|
|
| MD5 |
2faa168f8ae083ff603b08816c009271
|
|
| BLAKE2b-256 |
4c6a60ede2340079c21b3e6c32f3f134997137cd9ede1d7e19cea402bf5d26fc
|
File details
Details for the file enki_py-0.5.81-py3-none-macosx_11_0_arm64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-macosx_11_0_arm64.whl
- Upload date:
- Size: 1.3 MB
- Tags: Python 3, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
5e1e78d3244b8f01c43226f049f3593b6d204f5d788c6461cdcdd4430c415662
|
|
| MD5 |
59b33a9e26021e6288b51d1e85d6048f
|
|
| BLAKE2b-256 |
be3b2d4f932a49e8dbe139e5a233212deebf5855be402fca7dbd5f6296bf326a
|
File details
Details for the file enki_py-0.5.81-py3-none-macosx_10_12_x86_64.whl.
File metadata
- Download URL: enki_py-0.5.81-py3-none-macosx_10_12_x86_64.whl
- Upload date:
- Size: 1.4 MB
- Tags: Python 3, macOS 10.12+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
29176e5b5e0a79724d5308e74931ef61bff5e2c3c0b03d2066c598308117ac6a
|
|
| MD5 |
54beec6de7c20cd4cf55b987af5c3dd8
|
|
| BLAKE2b-256 |
f55b08c97f1f21be8d8d41a4a58741ca3f3247be6ffcc0ab120d64db3aceed0f
|