python-follow


Namepython-follow JSON
Version 0.1.2 PyPI version JSON
download
home_pageNone
SummaryFollow is a flexible Python decorator that lets you trace, inspect, and log exactly what happens inside your Python code
upload_time2025-07-16 15:00:19
maintainerNone
docs_urlNone
authorNone
requires_python>=3.7
licenseMIT
keywords python-follow follow
VCS
bugtrack_url
requirements No requirements were recorded.
Travis-CI No Travis.
coveralls test coverage No coveralls.
            ## <ins> Follow </ins>

Follow is a flexible Python decorator that lets you trace, inspect, and log exactly what happens inside your Python code — line by line <br>
Use it to debug, audit, or understand your code’s behavior in real time <br>

### <ins> Features </ins>

- Trace every executed line of a decorated function
- Log local variables, line content, and time spent between lines
- Selectively tracing (FollowConfig)
- Custom follower — Send trace data to print, a logger, or your own collector
- Supports multithreaded tracing with automatic worker wrapping

### <ins> Installation </ins>

You can install this package via PIP: pip install python-follow <br>

### <ins> Usage </ins>

```python
from follow import follow, FollowConfig

# Define your config
config = FollowConfig(
    follow_threads=True,
    follow_for_loops=True,
    follow_variable_set=True,
    follow_prints=True,
)

# Decorate your function
@follow(config=config)
def my_function():
    a = 1
    for i in range(3):
        b = a + i

my_function()

# Output:
# {'function': 'my_function', 'instruction': 'a = 1', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}]}
# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}]}
# {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]}
# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]}
# {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]}
# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]}
# {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 3, 'type': 'int'}]}
# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': []}
```

## <ins> Usage - Custom Collector </ins>

```python
from follow import follow, FollowConfig

class CustomCollector:
    def __init__(self):
        self.traces = []

    def collect(self, data: dict):
        self.traces.append(data)

custom_collector = CustomCollector()

# Decorate your function
@follow(follower=custom_collector.collect)
def my_function():
    a = 1
    for i in range(3):
        b = a + i

my_function()

# Output:
# [
#     {'function': 'my_function', 'instruction': 'a = 1', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}]},
#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}]},
#     {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]},
#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]},
#     {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]},
#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]},
#     {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 3, 'type': 'int'}]},
#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': []}
# ]
print(custom_collector.traces)
```

            

Raw data

            {
    "_id": null,
    "home_page": null,
    "name": "python-follow",
    "maintainer": null,
    "docs_url": null,
    "requires_python": ">=3.7",
    "maintainer_email": null,
    "keywords": "python-follow, follow",
    "author": null,
    "author_email": "Omer Menashe <unspecified@mail.com>",
    "download_url": "https://files.pythonhosted.org/packages/c7/9a/9692c0913902b08005ebd4c91e32d1eef647b091ac70eaf533b71e18ac2c/python_follow-0.1.2.tar.gz",
    "platform": null,
    "description": "## <ins> Follow </ins>\r\n\r\nFollow is a flexible Python decorator that lets you trace, inspect, and log exactly what happens inside your Python code \u2014 line by line <br>\r\nUse it to debug, audit, or understand your code\u2019s behavior in real time <br>\r\n\r\n### <ins> Features </ins>\r\n\r\n- Trace every executed line of a decorated function\r\n- Log local variables, line content, and time spent between lines\r\n- Selectively tracing (FollowConfig)\r\n- Custom follower \u2014 Send trace data to print, a logger, or your own collector\r\n- Supports multithreaded tracing with automatic worker wrapping\r\n\r\n### <ins> Installation </ins>\r\n\r\nYou can install this package via PIP: pip install python-follow <br>\r\n\r\n### <ins> Usage </ins>\r\n\r\n```python\r\nfrom follow import follow, FollowConfig\r\n\r\n# Define your config\r\nconfig = FollowConfig(\r\n    follow_threads=True,\r\n    follow_for_loops=True,\r\n    follow_variable_set=True,\r\n    follow_prints=True,\r\n)\r\n\r\n# Decorate your function\r\n@follow(config=config)\r\ndef my_function():\r\n    a = 1\r\n    for i in range(3):\r\n        b = a + i\r\n\r\nmy_function()\r\n\r\n# Output:\r\n# {'function': 'my_function', 'instruction': 'a = 1', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}]}\r\n# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}]}\r\n# {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]}\r\n# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]}\r\n# {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]}\r\n# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]}\r\n# {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 3, 'type': 'int'}]}\r\n# {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': []}\r\n```\r\n\r\n## <ins> Usage - Custom Collector </ins>\r\n\r\n```python\r\nfrom follow import follow, FollowConfig\r\n\r\nclass CustomCollector:\r\n    def __init__(self):\r\n        self.traces = []\r\n\r\n    def collect(self, data: dict):\r\n        self.traces.append(data)\r\n\r\ncustom_collector = CustomCollector()\r\n\r\n# Decorate your function\r\n@follow(follower=custom_collector.collect)\r\ndef my_function():\r\n    a = 1\r\n    for i in range(3):\r\n        b = a + i\r\n\r\nmy_function()\r\n\r\n# Output:\r\n# [\r\n#     {'function': 'my_function', 'instruction': 'a = 1', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}]},\r\n#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}]},\r\n#     {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 0, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]},\r\n#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 1, 'type': 'int'}]},\r\n#     {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 1, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]},\r\n#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 2, 'type': 'int'}]},\r\n#     {'function': 'my_function', 'instruction': 'b = a + i', 'execution_time': 0.0, 'local_vars': [{'var': 'a', 'val': 1, 'type': 'int'}, {'var': 'i', 'val': 2, 'type': 'int'}, {'var': 'b', 'val': 3, 'type': 'int'}]},\r\n#     {'function': 'my_function', 'instruction': 'for i in range(3):', 'execution_time': 0.0, 'local_vars': []}\r\n# ]\r\nprint(custom_collector.traces)\r\n```\r\n",
    "bugtrack_url": null,
    "license": "MIT",
    "summary": "Follow is a flexible Python decorator that lets you trace, inspect, and log exactly what happens inside your Python code",
    "version": "0.1.2",
    "project_urls": {
        "Source": "https://github.com/iamomerm/python-follow"
    },
    "split_keywords": [
        "python-follow",
        " follow"
    ],
    "urls": [
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "e0eccff86d64e34877e02101cd05131bac0549bbb64ab233235d00bf23ba004a",
                "md5": "2d1b539569060c26c85a4d6d7d814c71",
                "sha256": "78cb101befc698c360cb9791df85a8944b4bcdf37433ea3351cce7004f15d014"
            },
            "downloads": -1,
            "filename": "python_follow-0.1.2-py3-none-any.whl",
            "has_sig": false,
            "md5_digest": "2d1b539569060c26c85a4d6d7d814c71",
            "packagetype": "bdist_wheel",
            "python_version": "py3",
            "requires_python": ">=3.7",
            "size": 4087,
            "upload_time": "2025-07-16T15:00:18",
            "upload_time_iso_8601": "2025-07-16T15:00:18.032893Z",
            "url": "https://files.pythonhosted.org/packages/e0/ec/cff86d64e34877e02101cd05131bac0549bbb64ab233235d00bf23ba004a/python_follow-0.1.2-py3-none-any.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "c79a9692c0913902b08005ebd4c91e32d1eef647b091ac70eaf533b71e18ac2c",
                "md5": "a492db97e7d41d698abf7913d8bc24f5",
                "sha256": "7ee7b8d45fdc05ca3050e4ba6e590d8a1c1ef96a4eaf3263edcc822fd0f197c7"
            },
            "downloads": -1,
            "filename": "python_follow-0.1.2.tar.gz",
            "has_sig": false,
            "md5_digest": "a492db97e7d41d698abf7913d8bc24f5",
            "packagetype": "sdist",
            "python_version": "source",
            "requires_python": ">=3.7",
            "size": 4595,
            "upload_time": "2025-07-16T15:00:19",
            "upload_time_iso_8601": "2025-07-16T15:00:19.659129Z",
            "url": "https://files.pythonhosted.org/packages/c7/9a/9692c0913902b08005ebd4c91e32d1eef647b091ac70eaf533b71e18ac2c/python_follow-0.1.2.tar.gz",
            "yanked": false,
            "yanked_reason": null
        }
    ],
    "upload_time": "2025-07-16 15:00:19",
    "github": true,
    "gitlab": false,
    "bitbucket": false,
    "codeberg": false,
    "github_user": "iamomerm",
    "github_project": "python-follow",
    "travis_ci": false,
    "coveralls": false,
    "github_actions": false,
    "lcname": "python-follow"
}
        
Elapsed time: 1.15080s