Skip to main content

trolskgen

pip install trolskgen

Easily compose types/values/string-templates/AST-nodes, then convert to source.

Codgen .to_source()
trolskgen.e(
    "foo: {t}",
    t=trolskgen.e("some.Class") | int,
)
foo: some.Class | int
trolskgen.e(
    """
    class {name}({bases:*}):
        {fields:*}
    """,
    name="Foo",
    bases=[int, list],
    fields=[
        trolskgen.e("foo: {int}", int=int),
        trolskgen.e("{field_name}: str", field_name="bar"),
    ],
)
class Foo(int, list):
    foo: int
    bar: str
trolskgen.e(
    "f({args,kwargs:*})",
    args=[],
    kwargs={"a": 1, "b": [2, 3]},
)
f(a=1, b=[2, 3])

If you want formatting, run ruff format over the output. If you want comments, sorry, instead use a docstring, some Annotated[] wizardry, or fork this library to use LibCST.

Blog post with a motivating example.

API

Building templates
trolskgen.t(s: str, **kwargs: object) -> trolskgen.templates.Template
trolskgen.e(s: str, **kwargs: object) -> trolskgen.ASTModule

trolskgen.t creates source templates. If you use the format string :*, it will splat in place - see above: {bases:*}, {fields:*}, {args,kwargs:*}

Note on Python 3.14 template strings.

From Python 3.14 upwards, there are template strings, these make trolskgen significantly more succinct.

Where previously you'd do:

name = trolskgen.t("f")
func = trolskgen.t(
    """
    def {name}():
        ...
    """,
    name=name,
)
trolskgen.to_source(func)

As of Python 3.14, you can do:

name = t"f"
func = t"""
    def {name}():
        ...
"""
trolskgen.to_source(func)

There are some if sys.version_info >= (3, 14) flags around, but it should just work come release date.


e is for "eager" - this might be preferable to use, otherwise error messages can become pretty inscrutable.



Converting to AST/source
trolskgen.to_ast(o: object, *, config: Config) -> trolskgen.ASTModule
trolskgen.to_source(o: object, *, config: Config, ruff_format: bool, ruff_line_length: int) -> str

Lower level functions to convert o into an ast.AST/str representation.

The following are special cases for the value of o:

  • ast.Module | ast.expr nodes - these just get passed straight back out.
  • trolskgen.templates.Template or string.templatelib.Template - these get parsed as Python code.

trolskgen will generate sensible ASTs, for the following types:

  • None
  • int
  • float
  • str
  • bool
  • list
  • tuple
  • dict
  • set
  • classes
  • functions
  • dt.datetime
  • dt.date
  • enum.Enum
  • decimal.Decimal
  • dataclass
  • Annotated, T | U, etc.
  • pydantic.BaseModel

If you have ruff installed, you can call with ruff_format=True.



Configuring/Overriding
__trolskgen__
__trolskgen_cls__
trolskgen.Converter
trolskgen.Config
trolskgen.Config().prepend_converter(converter: Converter, *, before: Converter | None) -> Config
trolskgen.GLOBAL_CONFIG

If you own the class, you can just add a __trolskgen__ method:

For example:

class MyInterfaceClass:
    def __trolskgen__(self, f: trolskgen.F) -> ast.Module:
        return f(trolskgen.t("MyInterfaceClass({values:*})", values=[1, 2, 3]))


trolskgen.to_source(MyInterfaceClass()) == "MyInterfaceClass(1, 2, 3)"

You can also add a __trolskgen_cls__ @classmethod:

@dataclass
class MyJustName:
    a: str

    @classmethod
    def __trolskgen_cls__(cls, f: trolskgen.F) -> ast.Module:
        return f(trolskgen.t("Foo"))


trolskgen.to_source(MyJustName("bar")) == "Foo(a='bar')"

Note that we use f to recursively call trolskgen.to_ast(...) while preserving the current Config.


You can do simple overrides with a dict in Annotated, for example:

MySpecialInt = Annotated[int, {"__trolskgen__": "my_module.MySpecialInt"}]

If you don't own the class, you can build a trolskgen.Config with a custom Converter function.

For example, if you for some reason wanted to render all ints in the form x + 1, you could:

def custom_int_converter(o: object, f: trolskgen.F) -> ast.Module | None:
    if not isinstance(o, int):
        return None
    return f(trolskgen.t(f"{o - 1} + 1"))


config = trolskgen.Config().prepend_converter(custom_int_converter)
trolskgen.to_source([6, 9], config=config) == "[5 + 1, 8 + 1]"

You can also set a global trolskgen.GLOBAL_CONFIG ContextVar.

with trolskgen.GLOBAL_CONFIG.set(config):
    trolskgen.to_source([6, 9]) == "[5 + 1, 8 + 1]"

Metadata

Release files for trolskgen 0.0.26

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for trolskgen 0.0.26
File Size Uploaded Provenance
trolskgen-0.0.26.tar.gz 16.9 kB Without provenance Details

Built distribution (wheel)

Table of built distributions (wheels) for trolskgen 0.0.26
File Interpreter ABI Platform
trolskgen-0.0.26-py3-none-any.whl Python 3 none any Details

Total release size: 29.8 kB

Release files / trolskgen-0.0.26.tar.gz

Download URL trolskgen-0.0.26.tar.gz
Size 16.9 kB
Tags Source
SHA-256 checksum
How to use checksums
bc198a2d0ab114dfda6e0598b2571cc38ac9f93e7689552158622bcce1e6b43c
BLAKE2b-256 checksum
How to use checksums
f740946df6ba1fd6b7beab55e4cc8139b2aab28e0981912065546150b636a2ca
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via uv/0.12.17 {"installer":{"name":"uv","version":"0.12.17","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release files / trolskgen-0.0.26-py3-none-any.whl

Download URL trolskgen-0.0.26-py3-none-any.whl
Size 12.9 kB
Tags Python 3
SHA-256 checksum
How to use checksums
4359b23d150d4bc76dbc1f96223a890f586ca4f6313b821390b8911aa67e2b8e
BLAKE2b-256 checksum
How to use checksums
bb9800c102c7ccab1f7196df3d7f16990ec1a333c79c47fb9ad113a6b1c5f22b
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via uv/0.12.17 {"installer":{"name":"uv","version":"0.12.17","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Security for trolskgen 0.0.26

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.0.26 This release

2 release files No provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page