Source code for skidl.scriptinfo

# -*- coding: utf-8 -*-

# The MIT License (MIT) - Copyright (c) 2016-2021 Dave Vandenbout.

"""
Routines for getting information about a script.
"""
from __future__ import (  # isort:skip
    absolute_import,
    division,
    print_function,
    unicode_literals,
)

import inspect
import os
import sys
import traceback
from builtins import str

from future import standard_library

standard_library.install_aliases()


[docs]def scriptinfo(): """ Returns a dictionary with information about the running top level Python script: --------------------------------------------------------------------------- dir: directory containing script or compiled executable name: name of script or executable source: name of source code file --------------------------------------------------------------------------- `name` and `source` are identical if and only if running interpreted code. When running code compiled by `py2exe` or `cx_freeze`, `source` contains the name of the originating Python script. If compiled by PyInstaller, `source` contains no meaningful information. Downloaded from: http://code.activestate.com/recipes/579018-python-determine-name-and-directory-of-the-top-lev/ """ # --------------------------------------------------------------------------- # scan through call stack for caller information # --------------------------------------------------------------------------- trc = "skidl" # Make sure this gets set to something when in interactive mode. for teil in inspect.stack(): # skip system calls if teil[1].startswith("<"): continue if teil[1].upper().startswith(sys.exec_prefix.upper()): continue trc = teil[1] # trc contains highest level calling script name # check if we have been compiled if getattr(sys, "frozen", False): scriptdir, scriptname = os.path.split(sys.executable) return {"dir": scriptdir, "name": scriptname, "source": trc} # from here on, we are in the interpreted case scriptdir, trc = os.path.split(trc) # if trc did not contain directory information, # the current working directory is what we need if not scriptdir: scriptdir = os.getcwd() scr_dict = {"name": trc, "source": trc, "dir": scriptdir} return scr_dict
[docs]def get_script_name(): """Return the name of the top-level script.""" return os.path.splitext(scriptinfo()["name"])[0]
[docs]def get_skidl_trace(): """ Return a list containing the source line trace where a SKiDL object was instantiated. """ # To determine where this object was created, trace the function # calls that led to it and place into a field # but strip off all the calls to internal SKiDL functions. call_stack = inspect.stack() # Get function call stack. # Use the function at the top of the stack to # determine the location of the SKiDL library functions. try: skidl_dir, _ = os.path.split(call_stack[0].filename) except AttributeError: skidl_dir, _ = os.path.split(call_stack[0][1]) # Record file_name:line_num starting from the bottom of the stack # and terminate as soon as a function is found that's in the # SKiDL library (no use recording internal calls). skidl_trace = [] for frame in reversed(call_stack): try: filename = frame.filename lineno = frame.lineno except AttributeError: filename = frame[1] lineno = frame[2] if os.path.split(filename)[0] == skidl_dir: # Found function in SKiDL library, so trace is complete. break # Get the absolute path to the file containing the function # and the line number of the call in the file. Append these # to the trace. filepath = os.path.abspath(filename) skidl_trace.append(":".join((filepath, str(lineno)))) return skidl_trace