{"id":13478012,"url":"https://github.com/c0fec0de/anytree","last_synced_at":"2025-10-21T06:16:00.193Z","repository":{"id":10844284,"uuid":"66707325","full_name":"c0fec0de/anytree","owner":"c0fec0de","description":"Python tree data library","archived":false,"fork":false,"pushed_at":"2024-08-03T22:21:22.000Z","size":635,"stargazers_count":1017,"open_issues_count":43,"forks_count":135,"subscribers_count":25,"default_branch":"main","last_synced_at":"2025-03-22T08:41:16.565Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/c0fec0de.png","metadata":{"files":{"readme":"README.rst","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2016-08-27T09:42:38.000Z","updated_at":"2025-03-21T13:37:16.000Z","dependencies_parsed_at":"2023-02-18T17:00:28.644Z","dependency_job_id":"26de619d-1761-4e3a-b879-fe3f1d189bcd","html_url":"https://github.com/c0fec0de/anytree","commit_stats":{"total_commits":436,"total_committers":30,"mean_commits":"14.533333333333333","dds":"0.15825688073394495","last_synced_commit":"65a5d09ce0a592a80918f094ec3fa48b7faca250"},"previous_names":[],"tags_count":35,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/c0fec0de%2Fanytree","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/c0fec0de%2Fanytree/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/c0fec0de%2Fanytree/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/c0fec0de%2Fanytree/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/c0fec0de","download_url":"https://codeload.github.com/c0fec0de/anytree/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":245162186,"owners_count":20570692,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-07-31T16:01:51.265Z","updated_at":"2025-10-21T06:16:00.187Z","avatar_url":"https://github.com/c0fec0de.png","language":"Python","readme":".. image:: https://badge.fury.io/py/anytree.svg\n    :target: https://badge.fury.io/py/anytree\n\n.. image:: https://img.shields.io/pypi/dm/anytree.svg?label=pypi%20downloads\n   :target: https://pypi.python.org/pypi/anytree\n\n.. image:: https://readthedocs.org/projects/anytree/badge/?version=latest\n    :target: https://anytree.readthedocs.io/en/latest/?badge=latest\n\n.. image:: https://coveralls.io/repos/github/c0fec0de/anytree/badge.svg\n    :target: https://coveralls.io/github/c0fec0de/anytree\n\n.. image:: https://api.codeclimate.com/v1/badges/e6d325d6fd23a93aab20/maintainability\n   :target: https://codeclimate.com/github/c0fec0de/anytree/maintainability\n   :alt: Maintainability\n\n.. image:: https://img.shields.io/pypi/pyversions/anytree.svg\n   :target: https://pypi.python.org/pypi/anytree\n\n.. image:: https://img.shields.io/badge/code%20style-pep8-brightgreen.svg\n   :target: https://www.python.org/dev/peps/pep-0008/\n\n.. image:: https://img.shields.io/badge/code%20style-pep257-brightgreen.svg\n   :target: https://www.python.org/dev/peps/pep-0257/\n\n.. image:: https://img.shields.io/badge/linter-pylint-%231674b1?style=flat\n   :target: https://www.pylint.org/\n\n.. image:: https://img.shields.io/badge/code%20style-black-000000.svg\n   :target: https://github.com/psf/black\n\n.. image:: https://img.shields.io/github/contributors/c0fec0de/anytree.svg\n   :target: https://github.com/c0fec0de/anytree/graphs/contributors/\n\n.. image:: https://img.shields.io/badge/PRs-welcome-brightgreen.svg?style=flat-square\n   :target: http://makeapullrequest.com\n\n.. image:: https://img.shields.io/github/issues-pr/c0fec0de/anytree.svg\n   :target: https://github.com/c0fec0de/anytree/pulls\n\n.. image:: https://img.shields.io/github/issues-pr-closed/c0fec0de/anytree.svg\n   :target: https://github.com/c0fec0de/anytree/pulls?q=is%3Apr+is%3Aclosed\n\n\nLinks\n=====\n\n* Documentation_\n* PyPI_\n* GitHub_\n* Changelog_\n* Issues_\n* Contributors_\n* If you enjoy anytree_\n\n.. image:: https://github.com/c0fec0de/anytree/raw/devel/docs/static/buymeacoffee.png\n   :target: https://www.buymeacoffee.com/1oYX0sw\n\n.. _anytree: https://anytree.readthedocs.io/en/stable/\n.. _Documentation: https://anytree.readthedocs.io/en/stable/\n.. _PyPI: https://pypi.org/project/anytree\n.. _GitHub: https://github.com/c0fec0de/anytree\n.. _Changelog: https://github.com/c0fec0de/anytree/releases\n.. _Issues: https://github.com/c0fec0de/anytree/issues\n.. _Contributors: https://github.com/c0fec0de/anytree/graphs/contributors\n\n.. _Node: https://anytree.readthedocs.io/en/stable/api/anytree.node.html#anytree.node.node.Node\n.. _RenderTree: https://anytree.readthedocs.io/en/stable/api/anytree.render.html#anytree.render.RenderTree\n.. _UniqueDotExporter: https://anytree.readthedocs.io/en/stable/exporter/dotexporter.html#anytree.exporter.dotexporter.UniqueDotExporter\n.. _NodeMixin: https://anytree.readthedocs.io/en/stable/api/anytree.node.html#anytree.node.nodemixin.NodeMixin\n.. _Importers: https://anytree.readthedocs.io/en/stable/importer.html\n.. _Exporters: https://anytree.readthedocs.io/en/stable/exporter.html\n\nGetting started\n---------------\n\n.. _getting_started:\n\nUsage is simple.\n\n**Construction**\n\n\u003e\u003e\u003e from anytree import Node, RenderTree\n\u003e\u003e\u003e udo = Node(\"Udo\")\n\u003e\u003e\u003e marc = Node(\"Marc\", parent=udo)\n\u003e\u003e\u003e lian = Node(\"Lian\", parent=marc)\n\u003e\u003e\u003e dan = Node(\"Dan\", parent=udo)\n\u003e\u003e\u003e jet = Node(\"Jet\", parent=dan)\n\u003e\u003e\u003e jan = Node(\"Jan\", parent=dan)\n\u003e\u003e\u003e joe = Node(\"Joe\", parent=dan)\n\n**Node**\n\n\u003e\u003e\u003e print(udo)\nNode('/Udo')\n\u003e\u003e\u003e print(joe)\nNode('/Udo/Dan/Joe')\n\n**Tree**\n\n\u003e\u003e\u003e for pre, fill, node in RenderTree(udo):\n...     print(\"%s%s\" % (pre, node.name))\nUdo\n├── Marc\n│   └── Lian\n└── Dan\n    ├── Jet\n    ├── Jan\n    └── Joe\n\nFor details see Node_ and RenderTree_.\n\n**Visualization**\n\n\u003e\u003e\u003e from anytree.exporter import UniqueDotExporter\n\u003e\u003e\u003e # graphviz needs to be installed for the next line!\n\u003e\u003e\u003e UniqueDotExporter(udo).to_picture(\"udo.png\")\n\n.. image:: https://anytree.readthedocs.io/en/latest/_images/udo.png\n\nThe UniqueDotExporter_ can be started at any node and has various formatting hookups:\n\n\u003e\u003e\u003e UniqueDotExporter(dan,\n...                   nodeattrfunc=lambda node: \"fixedsize=true, width=1, height=1, shape=diamond\",\n...                   edgeattrfunc=lambda parent, child: \"style=bold\"\n... ).to_picture(\"dan.png\")\n\n.. image:: https://anytree.readthedocs.io/en/latest/_images/dan.png\n\nThere are various other Importers_ and Exporters_.\n\n**Manipulation**\n\nA second tree:\n\n\u003e\u003e\u003e mary = Node(\"Mary\")\n\u003e\u003e\u003e urs = Node(\"Urs\", parent=mary)\n\u003e\u003e\u003e chris = Node(\"Chris\", parent=mary)\n\u003e\u003e\u003e marta = Node(\"Marta\", parent=mary)\n\u003e\u003e\u003e print(RenderTree(mary))\nNode('/Mary')\n├── Node('/Mary/Urs')\n├── Node('/Mary/Chris')\n└── Node('/Mary/Marta')\n\nAppend:\n\n\u003e\u003e\u003e udo.parent = mary\n\u003e\u003e\u003e print(RenderTree(mary))\nNode('/Mary')\n├── Node('/Mary/Urs')\n├── Node('/Mary/Chris')\n├── Node('/Mary/Marta')\n└── Node('/Mary/Udo')\n    ├── Node('/Mary/Udo/Marc')\n    │   └── Node('/Mary/Udo/Marc/Lian')\n    └── Node('/Mary/Udo/Dan')\n        ├── Node('/Mary/Udo/Dan/Jet')\n        ├── Node('/Mary/Udo/Dan/Jan')\n        └── Node('/Mary/Udo/Dan/Joe')\n\nSubtree rendering:\n\n\u003e\u003e\u003e print(RenderTree(marc))\nNode('/Mary/Udo/Marc')\n└── Node('/Mary/Udo/Marc/Lian')\n\nCut:\n\n\u003e\u003e\u003e dan.parent = None\n\u003e\u003e\u003e print(RenderTree(dan))\nNode('/Dan')\n├── Node('/Dan/Jet')\n├── Node('/Dan/Jan')\n└── Node('/Dan/Joe')\n\n**Extending any python class to become a tree node**\n\nThe entire tree magic is encapsulated by NodeMixin_\nadd it as base class and the class becomes a tree node:\n\n\u003e\u003e\u003e from anytree import NodeMixin, RenderTree\n\u003e\u003e\u003e class MyBaseClass(object):  # Just an example of a base class\n...     foo = 4\n\u003e\u003e\u003e class MyClass(MyBaseClass, NodeMixin):  # Add Node feature\n...     def __init__(self, name, length, width, parent=None, children=None):\n...         super(MyClass, self).__init__()\n...         self.name = name\n...         self.length = length\n...         self.width = width\n...         self.parent = parent\n...         if children:\n...             self.children = children\n\nJust set the `parent` attribute to reflect the tree relation:\n\n\u003e\u003e\u003e my0 = MyClass('my0', 0, 0)\n\u003e\u003e\u003e my1 = MyClass('my1', 1, 0, parent=my0)\n\u003e\u003e\u003e my2 = MyClass('my2', 0, 2, parent=my0)\n\n\u003e\u003e\u003e for pre, fill, node in RenderTree(my0):\n...     treestr = u\"%s%s\" % (pre, node.name)\n...     print(treestr.ljust(8), node.length, node.width)\nmy0      0 0\n├── my1  1 0\n└── my2  0 2\n\nThe `children` can be used likewise:\n\n\u003e\u003e\u003e my0 = MyClass('my0', 0, 0, children=[\n...     MyClass('my1', 1, 0),\n...     MyClass('my2', 0, 2),\n... ])\n\n\u003e\u003e\u003e for pre, fill, node in RenderTree(my0):\n...     treestr = u\"%s%s\" % (pre, node.name)\n...     print(treestr.ljust(8), node.length, node.width)\nmy0      0 0\n├── my1  1 0\n└── my2  0 2\n\nDocumentation\n-------------\n\nPlease see the Documentation_ for all details.\n\nInstallation\n------------\n\nTo install the `anytree` module run::\n\n    pip install anytree\n\nIf you do not have write-permissions to the python installation, try::\n\n    pip install anytree --user\n","funding_links":["https://www.buymeacoffee.com/1oYX0sw"],"categories":["Python","Data Processing","Data Structures"],"sub_categories":["Data Representation"],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fc0fec0de%2Fanytree","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fc0fec0de%2Fanytree","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fc0fec0de%2Fanytree/lists"}