Skip to main content

Pure Python module that facilitates writing AOT compilable code

Project description

Nimic

Nimic is a pure Python module that facilitates writing AOT compilable code with a subset of Python (domain specific language). Based on ctypes built-in module, it includes emulation of native types, pointers and operations on them, implementing dispatch, operator overloading, and templates. Nimic closely follows Nim programming language, to which nimic code transpiles.

Key principle: nimic code is valid Python that runs natively and transpiles to equivalent Nim code.

Module Architecture

nimic/
├── ntypes.py       — Public API: re-exports type system + Nim keyword/builtin shims
├── ntypesystem.py  — Core type system (Object, NScalar, seq, dispatch, distinct, converter)
├── transpiler.py   — AST-based Python → Nim source code transpiler
├── inliner.py      — Template function inlining (@template, @template_expand)
├── ncode/          — Nim definitions (pydefs.nim, pystd/)
├── std/            — Python shims for Nim stdlib (math, options, os, paths, strformat, ...)
└── system/         — Python shims for Nim system modules (ansi_c)

ntypesystem.py — Core Type System

Organized in layers from low-level memory to high-level abstractions:

Layer Classes Purpose
Memory Ntype, NTypeRegistry ctypes-backed buffers with value semantics
Scalars NScalarNInteger / NFloat Fixed-width types (int8..int64, uint8..uint64, float16..float64) with arithmetic promotion
Structs Object Nim "object" — fields via annotations, backed by ctypes.Structure
Enums NIntEnum Nim integer enums with auto-registration
Variants Object + match kind: Nim "case object" — discriminated unions
Containers seq[T], UncheckedArray[T] Growable sequence and pointer-indexed array
Dispatch @dispatch, DispDict, NMetaClass Nim-style multi-dispatch via type annotations
Modifiers @distinct, @converter Type distinctness and trivial type conversions
Strings string str subclass with Nim-compatible &, %, isEmpty

ntypes.py — Public API & Keywords

Re-exports all of ntypesystem and adds Nim keyword/builtin emulation:

  • Compiler hintsconst, let, var, block, export, alias (no-ops in Python, scoping in Nim)
  • Reference typesref, ptr, mut@ (@ operator returns identity)
  • Enum utilitiesNStrEnum with succ/pred/ord/nrange/low/high
  • Cast & memorycast[T](x), sizeof(x), addr(x), unsafeAddr(x)
  • Type aliasesSomeInteger, SomeFloat, untyped, u64, i64, f64
  • Iterationfields(obj), fields(a, b), countdown(a, b)
  • Compile-timecomptime(x), defined(varname), static
  • Templates@template, @template_expand (re-exported from inliner)

transpiler.py — Python → Nim Transpiler

A modified CPython ast.py where _Unparser is extended to emit Nim syntax. Implements 30+ transformation rules for indentation, type definitions, function signatures, operators, imports, and control flow.

inliner.py — Template Inlining

@template + @template_expand decorators perform AST-level function inlining for untyped templates, substituting parameter names with call arguments.

DSL Conventions

Nimic uses Python syntax with specific conventions that have dual meaning — runtime behavior in Python and transpilation semantics for Nim:

Convention Example Purpose
with let/var/const: with let: x = vec3(1,2,3) Variable declaration scope qualifier
mut @ annotation def f(x: mut @ Vec3): Mutable argument (var in Nim)
{.pragma.} docstring """{.inline.}""" Nim pragma (inline, borrow, noSideEffect)
@dispatch @dispatch
def f(x: float64):
Multi-dispatch by argument types
@distinct @distinct
class Color(Vec3):
Distinct type (no implicit conversion)
@template @template
def toUV(v):
Template (inlined at call site)
@converter @converter
def toVec3(uv):
Implicit type converter
<<= dst <<= -src Value assignment to mutable variable
match kind: match kind:
  case K.a: ...
Variant type definition (case object)
comptime(expr) if comptime(cond): Compile-time evaluation (when in Nim)
fields(obj) for f in fields(obj): Iterate over object fields
with export: with export: mod1, mod2 Re-export modules

Quick Example

from __future__ import annotations
from nimic.ntypes import *

# Struct definition (Nim object)
class Vec3(Object):
    x: float64
    y: float64
    z: float64

    def __add__(self: Vec3, v: Vec3) -> Vec3:
        """{.inline.}"""
        result = Vec3()
        result.x = self.x + v.x
        result.y = self.y + v.y
        result.z = self.z + v.z
        return result

# Distinct type
@distinct
class Point3(Vec3):
    """{.borrow: `.`.}"""

# Multi-dispatch
@dispatch
def point3(x: float64, y: float64, z: float64) -> Point3:
    result = Point3(Vec3())
    result.x = x; result.y = y; result.z = z
    return result

# Usage
with let:
    a = point3(1.0, 2.0, 3.0)
    b = point3(4.0, 5.0, 6.0)
    c = Vec3(a) + Vec3(b)

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

nimic-0.0.4.tar.gz (52.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

nimic-0.0.4-py3-none-any.whl (60.5 kB view details)

Uploaded Python 3

File details

Details for the file nimic-0.0.4.tar.gz.

File metadata

  • Download URL: nimic-0.0.4.tar.gz
  • Upload date:
  • Size: 52.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: uv/0.9.21 {"installer":{"name":"uv","version":"0.9.21","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

File hashes

Hashes for nimic-0.0.4.tar.gz
Algorithm Hash digest
SHA256 743de9181232e129ae4c65a3a8666575d0d0fff1fbba17524e46e7259c4fd632
MD5 00cc377a485ab34a4e970fefdc9502cc
BLAKE2b-256 a1537ef0e44bf4bc742c3433b54ec95c6106d0736127e57234875de702333205

See more details on using hashes here.

File details

Details for the file nimic-0.0.4-py3-none-any.whl.

File metadata

  • Download URL: nimic-0.0.4-py3-none-any.whl
  • Upload date:
  • Size: 60.5 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: uv/0.9.21 {"installer":{"name":"uv","version":"0.9.21","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

File hashes

Hashes for nimic-0.0.4-py3-none-any.whl
Algorithm Hash digest
SHA256 50fb3bad160e1355f2888ea3bf230a8fdd9a271e11092211b84af3a63a720cf1
MD5 0cc88b8ca707152953971a64b2065015
BLAKE2b-256 ab882d3708c9f304ece53826dfd696c0e830030d58174f662a714b6386849d64

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page