Adapter¶
In-memory conversion between MolPy objects and an external library's representation — the in-memory half of MolPy's two bridging patterns. The other half is the wrapper, which shells out to a binary instead.
An adapter is a pair of pure functions, to_<lib> / from_<lib>: each builds
a new object and leaves its input untouched. MolPy keeps one worked example:
to_rdkit / from_rdkit. Packing is not an adapter — use
molpack (pip install molcrafts-molpack).
An example is not a dependency — RDKit is an optional extra
(pip install "molcrafts-molpy[rdkit]"), importing molpy never requires it,
and no molpy code path routes through it.
Quick reference¶
| Symbol | Summary | Preferred for |
|---|---|---|
to_rdkit(atomistic) |
New sanitized RDKit Mol from an Atomistic |
Handing a structure to RDKit's own algorithms |
from_rdkit(mol, conf_id=-1) |
New Atomistic from an RDKit Mol |
Bringing RDKit's result back |
generate_3d(atomistic) |
RDKit ETKDGv3 embedding (+ UFF), as a round trip | Comparing against RDKit's embedder |
PROP_PREFIX |
"molpy:", the namespace of carried RDKit properties |
Reading carried components on the RDKit side |
Canonical example¶
The examples below share this setup:
# docs: skip — RDKit optional adapter example; not unit-tested
import molpy as mp
from molpy.adapter import from_rdkit, to_rdkit
from rdkit import Chem
from rdkit.Chem import AllChem
mol = mp.io.smiles.read_smiles("CCO").to_atomistic()
rd_mol = Chem.AddHs(to_rdkit(mol))
AllChem.EmbedMolecule(rd_mol) # RDKit's algorithm, on RDKit's object
AllChem.MMFFOptimizeMolecule(rd_mol)
optimized = from_rdkit(rd_mol) # a new molpy Atomistic; `mol` is unchanged
What crosses the boundary¶
| To RDKit | Back to MolPy | |
|---|---|---|
| Element, formal charge, bond type, coordinates | RDKit's own fields (one conformer) | RDKit's values win |
Bracket hydrogen count (h_count, SMILES [nH]) |
Sets RDKit's H count on that atom | Carried back unchanged |
Every other atom / bond component (name, res_name, res_id, type, charge, mass, bond_number, a bond's type, …) |
RDKit property molpy:<key> |
Restored on the atoms and bonds RDKit kept |
Scalar Atomistic.props |
Mol property molpy:<key> |
Restored |
What does not survive the round trip:
- Atoms or bonds RDKit removes (
RemoveHs, fragment stripping) are absent from the result. Atoms or bonds RDKit creates (AddHs) carry RDKit-owned fields only. - Angles, dihedrals, impropers and ports: only atoms and bonds cross.
Regenerate the rest with
generate_topology. - Stereo is not translated. molpy's
stereocomponent does not become RDKit chiral tags or bond stereo, and RDKit's chiral tags, bond stereo and CIP labels do not come back. Thestereocomponent itself rides along untouched, so it is stale if RDKit changed that atom's neighbours. - Recomputed facts: when RDKit changes a bond's type, the carried
bond_numberis replaced by the number the new type implies (none for aromatic). Nothing else is recomputed — an atom whose element RDKit changes keeps its oldmassandtype. - Extra conformers:
from_rdkitreads one (conf_id). - A graph prop that is not a bool, int, float or str makes
to_rdkitraiseTypeErrorrather than drop it silently.
Do not use it for what MolPy already does¶
The adapter exists to reach algorithms MolPy does not implement. For anything below, the native path is the supported one and needs no third-party install:
| Task | Native |
|---|---|
| 3D embedding | Conformer — ETKDGv3 → torsion refinement → MMFF94 cleanup |
| Hydrogens / aromaticity / stereo | mp.perceive.add_hydrogens(...) / mp.perceive.assign_aromaticity(...) |
| SMILES / SMARTS | mp.io.smiles.read_smiles(...).to_atomistic(), mp.perceive.SmartsPattern — see Notation |
| Ring queries | mp.perceive.perceive_rings(mol) → RingSet |
| GAFF types | AmberTools wrapper — antechamber delegation |
Key behavior¶
- every function returns a new object and never mutates its input
import molpy.adapterworks without RDKit; readingto_rdkit,from_rdkitorgenerate_3dthen raisesImportErrornaming the extra to install- an adapter does in-memory conversion only — executing an external binary belongs in a wrapper
Related¶
- Concepts: Wrapper and Adapter
- Conformer — the native embedder
Full API¶
to_rdkit ¶
Build a sanitized RDKit Mol from atomistic; the input is not touched.
RDKit atom i is atomistic's atom i and RDKit bond k its
bond k. A conformer is added when every atom has coordinates. See the
module docstring for what is carried and what is lost.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
atomistic
|
Atomistic
|
The structure to convert. Every atom needs an |
required |
Returns:
| Type | Description |
|---|---|
Mol
|
A new, sanitized |
Raises:
| Type | Description |
|---|---|
KeyError
|
If an atom has no |
ValueError
|
If a bond type has no RDKit counterpart. |
TypeError
|
If a graph-level prop is not a bool, int, float or str. |
RuntimeError
|
If RDKit cannot sanitize the result. |
from_rdkit ¶
Build a new :class:~molpy.Atomistic from mol; the input is not touched.
Atom i of the result is RDKit atom i. Components carried by
:func:to_rdkit come back on the atoms and bonds RDKit kept; RDKit's own
fields (element, formal charge, bond type, coordinates) override them.
See the module docstring for what is lost.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
mol
|
Mol
|
Any RDKit molecule — one from :func: |
required |
conf_id
|
int
|
The conformer to read coordinates from; |
-1
|
Returns:
| Type | Description |
|---|---|
Atomistic
|
A new |
Raises:
| Type | Description |
|---|---|
ValueError
|
If a bond type has no molpy counterpart (dative, …). |
generate_3d ¶
Embed 3D coordinates with RDKit's ETKDGv3, optionally UFF-relaxed.
A round trip through :func:to_rdkit and :func:from_rdkit: the result is
a new Atomistic and atomistic is not touched. Hydrogens RDKit adds
carry RDKit-owned fields only. For molpy's native embedder, use
:class:molpy.conformer.Conformer instead.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
atomistic
|
Atomistic
|
The structure to embed. |
required |
add_hydrogens
|
bool
|
Add explicit hydrogens before embedding. |
True
|
optimize
|
bool
|
Relax the embedded geometry with UFF. |
True
|
Returns:
| Type | Description |
|---|---|
Atomistic
|
A new |
Raises:
| Type | Description |
|---|---|
ValueError
|
If |
RuntimeError
|
If RDKit cannot sanitize or embed the molecule. |