Search Shortcut cmd + k | ctrl + k
ducksmiles

Cheminformatics and CPU numerical analytics for DuckDB - molecular formats, descriptors, fingerprints, similarity, regression, statistical inference, experimental design, time series, reliability and model evaluation from SQL

Maintainer(s): nkwork9999

Compatibility Matrix

This table covers all DuckDB releases that have not reached end-of-life, including LTS releases, and shows the 2 most recent patch releases of each. Older patch releases are not listed, but the extension may be available for them as well.

Platform 1.4.4 1.4.5 1.5.5 1.5.6 2.0.0
Linux AMD64
Linux ARM64
macOS AMD64
macOS ARM64
Windows AMD64
Windows ARM64
WebAssembly

Installing and Loading

INSTALL ducksmiles FROM community;
LOAD ducksmiles;

Example

-- Parse SMILES and get molecular formula
SELECT mol_formula('CCO');
-- C2H6O

-- Calculate molecular weight
SELECT round(mol_weight('c1ccccc1'), 2);
-- 78.11

-- Wildman-Crippen LogP and molar refractivity (match RDKit)
SELECT round(logp_crippen('CCO'), 4), round(mol_mr('c1ccccc1'), 3);
-- -0.0014, 26.442

-- QED drug-likeness score (RDKit Chem.QED, weights_mean)
SELECT round(qed('CC(=O)Oc1ccccc1C(=O)O'), 3);
-- 0.550   (aspirin)

-- Drug-likeness rule panels + toxicophore alerts
SELECT lipinski_violations('CC(=O)Oc1ccccc1C(=O)O'),
       druglikeness_pass('CC(=O)Oc1ccccc1C(=O)O', 'veber'),
       structural_alerts_json('O=Cc1ccccc1');
-- 0, 1, ["aldehyde","aldehyde_any"]

-- Morgan/ECFP fingerprint + similarity between two BLOBs
SELECT round(tanimoto_bit(morgan_fp_bits('CCO'), morgan_fp_bits('CCN')), 4);
-- 0.3333

-- In-silico docking: SMILES ligand vs PDB receptor -> ranked poses (JSON)
SELECT dock('CCO', :receptor_pdb, 1.7,0.2,0.5, 8,8,8, 20, 42);

-- Retrospective virtual-screening enrichment over a docked, labelled library
SELECT roc_auc(list(score), list(is_active)),
       enrichment_factor(list(score), list(is_active), 0.01),
       bedroc(list(score), list(is_active), 20.0)
FROM docked_library;

-- CPU PCA on a numeric matrix, returning versioned JSON
SELECT chem_pca([[1.0,2.0],[2.0,4.0],[3.0,6.0]], [1.0,0.0]);

-- Convert SMILES to SELFIES (ML-friendly notation)
SELECT smiles_to_selfies('CCO');

About ducksmiles

Cheminformatics toolkit for DuckDB - analyze molecular structures directly from SQL without leaving your database. Pure Rust implementation with no external chemistry library dependencies (no RDKit required).

Supported Formats:

  • SMILES: validation, formula, weight, atom/bond counts, canonicalization, aromaticity
  • InChI/InChIKey: layer extraction, stereochemistry detection, skeleton matching
  • MOL/SDF: V2000/V3000 block parsing, 3D geometry, molecule counting
  • PDB/CIF/XYZ: protein structure analysis (atom, chain, residue, model counts)
  • SELFIES: bidirectional SMILES-SELFIES conversion for ML pipelines

418 SQL overloads, including the existing 151 molecular overloads and 267 CPU analytics functions. Molecular methods cover property extraction, format conversion, structural comparison, fingerprinting, similarity search, drug-likeness / toxicophore filtering, and structure-based virtual screening.

Function descriptions, meaningful argument names, runnable examples and categories are discoverable through duckdb_functions() for every overload. Filter with list_contains(categories, 'ducksmiles') after loading the extension.

Descriptors (RDKit-faithful ports):

  • 21 structural-profile functions: fragments, formal charge, hydrogen and bond counts, ring membership, elemental counts, fractions, isotope-aware heavy-atom mass and mean heavy-atom degree. A pinned RDKit 2025.09.6 reference suite checks 4,510 inputs; this is finite-corpus validation, not a guarantee of full RDKit parser/sanitizer equivalence.
  • logp_crippen() / mol_mr() - Wildman-Crippen LogP and molar refractivity.
  • tpsa() - Ertl topological polar surface area.
  • qed() - QED drug-likeness (Bickerton 2012), a port of RDKit Chem.QED.
  • Lipinski set: num_h_donors(), num_h_acceptors(), num_rotatable_bonds(), fraction_csp3(), num_heteroatoms(), and the full ring-count descriptor family.

Mass context and native graphs:

  • formula_exact_mass() parses supported flat formulas strictly.
  • adduct_neutral_mass() and adduct_precursor_mz() perform versioned arithmetic for 29 explicit adduct labels, including signed electron corrections.
  • mol_graph_json() exports a versioned native atom/bond graph in input order with explicit hydrogen vertices, isotope, charge and raw stereo tokens. This sidecar is not pretrained-model tensors or full RDKit sanitization.
  • Unsupported or malformed inputs return NULL.

Fingerprints & similarity:

  • morgan_fp_bits() (Morgan/ECFP-style, radius 2 / 2048-bit default) and maccs_keys() (167-bit MACCS). Morgan bit positions are not claimed to be identical to RDKit's MorganGenerator.
  • Full bit-fingerprint similarity family over raw BLOBs, faithful to RDKit DataStructs/BitOps.cpp: tanimoto_bit, dice_bit, cosine_bit, kulczynski_bit, sokal_bit, mcconnaughey_bit, asymmetric_bit, braun_blanquet_bit, russel_bit, and asymmetric tversky_bit(a, b, alpha, beta).

Structure tools: SMARTS substructure search/counting, Bemis-Murcko and generic scaffolds, scaffold networks, ring-system extraction, maximum common substructure (MCS), and MolHash standardization.

Drug-likeness & toxicophore filtering:

  • admet_json() - a full report: descriptors plus six drug-likeness rule panels.
  • druglikeness_pass(smiles, rule) for Lipinski, Veber, Ghose, Egan, Muegge and Lead-likeness; lipinski_violations() for the Rule-of-Five count.
  • structural_alerts_json() / structural_alert_count() over a curated Brenk / PAINS reactive-group toxicophore catalogue.

In-silico docking pipeline (structure-based virtual screening, end-to-end in SQL):

  • smiles_to_pdbqt() - 3D conformer generation (distance geometry + an L-BFGS- minimised lite force field with aromatic-ring planarity) emitted as PDBQT.
  • prepare_receptor(pdb, ph) - pH-dependent protonation states + polar-hydrogen addition, so the receptor can donate H-bonds.
  • dock(smiles, pdb, cx, cy, cz, sx, sy, sz, n_runs, seed [, ph]) - flexible torsion-tree docking with an AutoDock-Vina-style scoring function and 3D affinity maps; returns ranked poses with coordinates as JSON.
  • Retrospective-validation harness: roc_auc, enrichment_factor(fraction), bedroc(alpha) to measure how well a docked library enriches known actives.

CPU numerical analytics:

  • 267 functions for descriptive/inferential statistics, regression, mixed/latent models, IRT/SEM, causal evaluation, experimental design, quality/reliability, time series, functional preprocessing, numeric text analysis and spatial models.
  • Numeric matrices and ordered parameter lists; versioned JSON results, reusable fitted models, and NULL for invalid or resource-limited inputs. No GPU or Python runtime is required. Existing molecular methods remain available.
  • Complete SQL examples, parameter contracts, validation evidence and remaining gaps are in the README. These are bounded partial method contracts; full JMP equivalence is not claimed.

The new bounded CPU methods include censored regression, estimated spatial covariance, static SVG histograms/box plots and ordered categorical ML with saved prediction. JMP default Lasso, sandwich inference and full plot options remain explicitly incomplete in the source README.

Architecture: Rust (core logic, zero external chemistry crates) + C++ (DuckDB integration via FFI).

Added Functions

function_name function_type description comment examples
add_hydrogens scalar NULL NULL  
admet_json scalar NULL NULL  
asymmetric_bit scalar NULL NULL  
bedroc scalar NULL NULL  
braun_blanquet_bit scalar NULL NULL  
canonical_smiles scalar NULL NULL  
cosine_bit scalar NULL NULL  
dice_bit scalar NULL NULL  
dock scalar NULL NULL  
druglikeness_pass scalar NULL NULL  
enrichment_factor scalar NULL NULL  
fraction_csp3 scalar NULL NULL  
fragment_parent scalar NULL NULL  
generic_scaffold scalar NULL NULL  
inchi_charge scalar NULL NULL  
inchi_connections scalar NULL NULL  
inchi_formula scalar NULL NULL  
inchi_has_stereo scalar NULL NULL  
inchi_hydrogens scalar NULL NULL  
inchi_is_standard scalar NULL NULL  
inchi_is_valid scalar NULL NULL  
inchi_num_stereo_centers scalar NULL NULL  
inchi_skeleton_match scalar NULL NULL  
inchi_stereo_bond scalar NULL NULL  
inchi_stereo_tetrahedral scalar NULL NULL  
inchi_version scalar NULL NULL  
inchikey_connectivity scalar NULL NULL  
inchikey_is_valid scalar NULL NULL  
inchikey_protonation scalar NULL NULL  
inchikey_stereo scalar NULL NULL  
kulczynski_bit scalar NULL NULL  
largest_fragment scalar NULL NULL  
lipinski_violations scalar NULL NULL  
logp_crippen scalar NULL NULL  
maccs_keys scalar NULL NULL  
mcconnaughey_bit scalar NULL NULL  
mcs_json scalar NULL NULL  
mcs_smarts scalar NULL NULL  
mol_aromatic_fraction scalar NULL NULL  
mol_block_atoms_json scalar NULL NULL  
mol_block_bonds_json scalar NULL NULL  
mol_block_centroid_x scalar NULL NULL  
mol_block_centroid_y scalar NULL NULL  
mol_block_centroid_z scalar NULL NULL  
mol_block_formula scalar NULL NULL  
mol_block_has_3d scalar NULL NULL  
mol_block_json scalar NULL NULL  
mol_block_max_x scalar NULL NULL  
mol_block_max_y scalar NULL NULL  
mol_block_max_z scalar NULL NULL  
mol_block_min_x scalar NULL NULL  
mol_block_min_y scalar NULL NULL  
mol_block_min_z scalar NULL NULL  
mol_block_name scalar NULL NULL  
mol_block_num_atoms scalar NULL NULL  
mol_block_num_bonds scalar NULL NULL  
mol_block_properties_json scalar NULL NULL  
mol_block_property scalar NULL NULL  
mol_block_radius_of_gyration scalar NULL NULL  
mol_block_weight scalar NULL NULL  
mol_exact_mass scalar NULL NULL  
mol_formal_charge scalar NULL NULL  
mol_formula scalar NULL NULL  
mol_has_substructure scalar NULL NULL  
mol_hash scalar NULL NULL  
mol_hash_methods scalar NULL NULL  
mol_heavy_atom_mass scalar NULL NULL  
mol_heteroatom_fraction scalar NULL NULL  
mol_is_valid scalar NULL NULL  
mol_largest_ring_size scalar NULL NULL  
mol_mean_degree scalar NULL NULL  
mol_mr scalar NULL NULL  
mol_num_aromatic_atoms scalar NULL NULL  
mol_num_aromatic_bonds scalar NULL NULL  
mol_num_atoms scalar NULL NULL  
mol_num_bonds scalar NULL NULL  
mol_num_carbons scalar NULL NULL  
mol_num_double_bonds scalar NULL NULL  
mol_num_explicit_h scalar NULL NULL  
mol_num_fragments scalar NULL NULL  
mol_num_halogens scalar NULL NULL  
mol_num_implicit_h scalar NULL NULL  
mol_num_nitrogens scalar NULL NULL  
mol_num_oxygens scalar NULL NULL  
mol_num_ring_atoms scalar NULL NULL  
mol_num_ring_bonds scalar NULL NULL  
mol_num_single_bonds scalar NULL NULL  
mol_num_total_h scalar NULL NULL  
mol_num_triple_bonds scalar NULL NULL  
mol_substructure_count scalar NULL NULL  
mol_substructure_matches_json scalar NULL NULL  
mol_weight scalar NULL NULL  
morgan_fp_bits scalar NULL NULL  
murcko_scaffold scalar NULL NULL  
neutralize_charges scalar NULL NULL  
normalize_smiles scalar NULL NULL  
num_aliphatic_carbocycles scalar NULL NULL  
num_aliphatic_heterocycles scalar NULL NULL  
num_aliphatic_rings scalar NULL NULL  
num_aromatic_carbocycles scalar NULL NULL  
num_aromatic_heterocycles scalar NULL NULL  
num_aromatic_rings scalar NULL NULL  
num_h_acceptors scalar NULL NULL  
num_h_donors scalar NULL NULL  
num_heteroatoms scalar NULL NULL  
num_rotatable_bonds scalar NULL NULL  
num_saturated_carbocycles scalar NULL NULL  
num_saturated_heterocycles scalar NULL NULL  
num_saturated_rings scalar NULL NULL  
pdb_to_pdbqt scalar NULL NULL  
prepare_receptor scalar NULL NULL  
qed scalar NULL NULL  
ring_count scalar NULL NULL  
ring_systems_json scalar NULL NULL  
roc_auc scalar NULL NULL  
russel_bit scalar NULL NULL  
scaffold_network_json scalar NULL NULL  
sdf_count scalar NULL NULL  
sdf_properties_json scalar NULL NULL  
sdf_property scalar NULL NULL  
selfies_is_valid scalar NULL NULL  
selfies_to_smiles scalar NULL NULL  
smiles_to_pdbqt scalar NULL NULL  
smiles_to_selfies scalar NULL NULL  
sokal_bit scalar NULL NULL  
strip_salts scalar NULL NULL  
structural_alert_count scalar NULL NULL  
structural_alerts_json scalar NULL NULL  
structure_atom_count scalar NULL NULL  
structure_centroid_x scalar NULL NULL  
structure_centroid_y scalar NULL NULL  
structure_centroid_z scalar NULL NULL  
structure_chain_count scalar NULL NULL  
structure_max_x scalar NULL NULL  
structure_max_y scalar NULL NULL  
structure_max_z scalar NULL NULL  
structure_min_x scalar NULL NULL  
structure_min_y scalar NULL NULL  
structure_min_z scalar NULL NULL  
structure_model_count scalar NULL NULL  
structure_radius_of_gyration scalar NULL NULL  
structure_residue_count scalar NULL NULL  
tanimoto_bit scalar NULL NULL  
tpsa scalar NULL NULL  
tversky_bit scalar NULL NULL  

Overloaded Functions

This extension does not add any function overloads.

Added Types

This extension does not add any types.

Added Settings

This extension does not add any settings.