Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions README.rst
Original file line number Diff line number Diff line change
@@ -1,3 +1,15 @@

About this fork:

This is the version that is working for me.

I made these updates:

* [bug] fixed module length issue [https://github.com/Akrog/pinliner/issues/10]
* [feature] added --verbose flag for debugging

Original description is below:

===========================
pinliner - Python Inliner
===========================
Expand Down
30 changes: 25 additions & 5 deletions pinliner/importer.template
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import types

PINLINED_DEFAULT_PACKAGE = '%{DEFAULT_PACKAGE}'
PINLINER_MODULE_NAME = 'pinliner_loader'
CONFIG_VERBOSE = %{CONFIG_VERBOSE}
loader_version = '0.2.1'

FORCE_EXC_HOOK = %{FORCE_EXC_HOOK}
Expand All @@ -15,15 +16,17 @@ import os
import struct
import sys
import types
import re


class InlinerImporter(object):
version = '%(loader_version)s'
def __init__(self, data, datafile, set_excepthook=True):
def __init__(self, data, datafile, set_excepthook=True, verbose=False):
self.data = data
self.datafile = datafile
if set_excepthook:
sys.excepthook = self.excepthook
self.__verbose = verbose

@staticmethod
def excepthook(type, value, traceback):
Expand All @@ -37,10 +40,12 @@ class InlinerImporter(object):

def get_source(self, fullname):
__, start, end, ts = self.data[fullname]
if self.__verbose:
print('loading source file contents for file '+str(fullname)+' from position '+str(start)+' to position '+str(end)+'')
with open(self.datafile) as datafile:
datafile.seek(start)
code = datafile.read(end - start)
return code
return code

def get_code(self, fullname, filename):
py_ts = self.data[fullname][3]
Expand All @@ -52,8 +57,15 @@ class InlinerImporter(object):
return marshal.load(pyc)
except:
pass

code = self.get_source(fullname)

if self.__verbose:
print('getting compiled code for package: ' + fullname)
with open(fullname + '.sample.py', 'w', encoding='utf-8') as f:
f.write(code)
f.close()

compiled_code = compile(code, filename, 'exec')

try:
Expand Down Expand Up @@ -139,7 +151,7 @@ def prepare_package():
set_excepthook = FORCE_EXC_HOOK

importer = module.InlinerImporter(inliner_packages, filename,
set_excepthook)
set_excepthook, verbose=CONFIG_VERBOSE)
sys.meta_path.append(importer)

# If this is a bundle (multiple packages) without default then don't import
Expand All @@ -151,6 +163,14 @@ def prepare_package():
with open(filename) as datafile:
datafile.seek(start)
code = datafile.read(end - start)

# delete .pyc files before first loaded package
# if we don't do so
# we are getting an error "ImportError: invalid flags 1730942170 in 'src'"
path = '.'
for fname_remove in os.listdir(path):
if os.path.isfile(os.path.join(path, fname_remove)) and (os.path.splitext(fname_remove)[-1].lower()=='.pyc'):
os.remove(os.path.join(path, fname_remove))

# We need everything to be local variables before we clear the global dict
def_package = PINLINED_DEFAULT_PACKAGE
Expand All @@ -175,4 +195,4 @@ def prepare_package():

# Prepare loader's module and populate this namespace only with package's
# __init__
prepare_package()
prepare_package()
21 changes: 12 additions & 9 deletions pinliner/pinliner.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,9 @@ def process_file(cfg, base_dir, package_path):

# Insert escape character before ''' since we'll be using ''' to insert
# the code as a string
output(cfg, code.replace("'''", r"\'''"), newline=cfg.tagging)
package_end = cfg.outfile.tell()
code = code.replace("'''", r"\'''")
output(cfg, code, newline=cfg.tagging)
package_end = package_start + len(code)
is_package = 1 if path.endswith('__init__') else 0
if is_package:
path = path[:-9]
Expand All @@ -50,8 +51,7 @@ def template(cfg):
prefix_end = template.index(TEMPLATE_PATTERN)
prefix_data = template[:prefix_end].replace('%{FORCE_EXC_HOOK}',
str(cfg.set_hook))
prefix_data = prefix_data.replace('%{DEFAULT_PACKAGE}',
cfg.default_package)
prefix_data = prefix_data.replace('%{DEFAULT_PACKAGE}', cfg.default_package).replace('%{CONFIG_VERBOSE}','True' if cfg.verbose else 'False')
cfg.outfile.write(prefix_data)
postfix_begin = prefix_end + len(TEMPLATE_PATTERN)
return template[postfix_begin:]
Expand Down Expand Up @@ -117,8 +117,8 @@ def error(self, message):
└── [my_package]
├── file_a.py
├── [sub_package]
   ├── file_b.py
   └── __init__.py
├── file_b.py
└── __init__.py
├── __init__.py

And you execute:
Expand Down Expand Up @@ -159,6 +159,9 @@ def error(self, message):
parser.add_argument('--tag', default=False, dest='tagging',
action='store_true',
help="Mark with <tag:file_path> each added file.")
parser.add_argument('--verbose', default=False, dest='verbose',
action='store_true',
help="Print messages about modules being loaded and safe module files with code along with .pyc for debugging")
parser.add_argument('-d', '--default-pkg', default=None,
dest='default_package',
help='Define the default package when multiple '
Expand Down Expand Up @@ -196,8 +199,8 @@ def validate_args(cfg):

if cfg.default_package:
if cfg.default_package not in cfg.packages:
sys.stderr.write('ERROR: %s is not a valid default package' %
cfg.default_pkg)
sys.stderr.write('ERROR: %s is not a valid default package, valid are only: [ %s ]' %
( cfg.default_package, ', '.join(list(cfg.packages)) ))
sys.exit(2)
# Convert the default package from path to package
cfg.default_package = os.path.split(cfg.default_package)[1]
Expand All @@ -210,4 +213,4 @@ def main():


if __name__ == '__main__':
main()
main()