Discover ways to bundle a Python app on this tutorial.
For essentially the most half, when you’ve written your Python code, you merely deploy it to a server, set up the setting, seize the dependencies and also you’re completed.
Nonetheless, there are occasions when chances are you’ll wish to present your app to another person and don’t need the trouble of getting them setup with all of the coaching round ensuring they’ve Python on their machine and might run your app.
Maybe it’s even since you don’t need the opposite social gathering to have your treasured supply code. Python is an interpreted language, making this principally unavoidable.
What if there have been one other manner? … enter Nuitka!
What’s Nuitka?
Nuitka might be understood as being a compiler in your python code. No, it technically isn’t a compiler. What it actually does is convert your code to C after which compile that right down to a binary for distribution.
Present me an instance!
Should you’re saying “This all sounds too good, don’t inform me.. Present Me!”, then prepare, as a result of I plan to do exactly that!
Putting in Nuitka to Bundle a Python App
As with most issues Python, it’s fast to get straight to the purpose.
Head over to PyPi and seek for Nuitka to verify now we have the most recent model.
<a href=" goal="_blank" rel="noreferrer noopener nofollow">https://pypi.org/undertaking/Nuitka/</a>
N.B. Earlier than performing the following step, be sure that to setup a Python Digital Setting so that every one packages will likely be put in domestically to this tutorial.
Persevering with; This offers us a simple method to get going, pip set up Nuitka
.
mkdir -p ~/src/tutorials/nuitka_testing
cd $_
virtualenv -p python3 venv
. venv/bin/activate
Now run the pip set up Nuitka
:
$ pip set up nuitka
Accumulating nuitka
Downloading Nuitka-0.6.7.tar.gz (2.3 MB)
|████████████████████████████████| 2.3 MB 1.6 MB/s
Constructing wheels for collected packages: nuitka
Constructing wheel for nuitka (setup.py) ... completed
Created wheel for nuitka: filename=Nuitka-0.6.7-py3-none-any.whl dimension=2117847 sha256=5ce6d2ef97e7fd72aa8980c8ba7d6cfdecaf6f7b8971fd397241070d8a0f6e2e
Saved in listing: /Customers/ao/Library/Caches/pip/wheels/60/7f/ef/8c1ef8cf2b509e25ead8f221725a8f95db6d7af0fc67565fde
Efficiently constructed nuitka
Putting in collected packages: nuitka
Efficiently put in nuitka-0.6.7
Should you acquired stuff for some purpose, learn extra about downloading Nuitka from the undertaking’s web site immediately.
Testing out Nuitka
Nuitka is a Python module that we run towards a undertaking or python script.
This implies we’d like a pleasant little check script to strive it out.
Create a file referred to as test1.py
and enter the next code in it:
import string
from random import *
characters = string.ascii_letters + string.punctuation + string.digits
password = "".be a part of(alternative(characters) for x in vary(randint(12, 16)))
print(password)
It will generate a novel sturdy password for us, between 12 and 16 characters.
If we run the script utilizing python, we get output much like this:
$ python test1.py
KdcM[btk8JvW
Excellent!
So now let’s add Nuitka into the mix. Run the following:
python -m nuitka test1.py
This will take a moment and will not render any output to the screen.
If we execute a ls -lashp
then we will see what has been created:
$ ls -lashp
total 496
0 drwxr-xr-x 6 ao staff 192B ... ./
0 drwxr-xr-x 4 ao staff 128B ... ../
488 -rwxr-xr-x 1 ao staff 243K ... test1.bin
0 drwxr-xr-x 18 ao staff 576B ... test1.build/
8 -rw-r--r-- 1 ao staff 195B ... test1.py
0 drwxr-xr-x 6 ao staff 192B ... venv/
We can now execute ./test1.bin
directly and see the application run.
$ ./test1.bin
7'4^5`YNux5Z
Additional CLI arguments
While the default arguments work pretty well, if we want to add debug symbols, or package our application as a standalone app, there are a ton of additional arguments we can pass in.
Issue a python -m nuitka --help
to see all the options.
$ python -m nuitka --help
Usage: __main__.py [--module] [--run] [options] main_module.py
Choices:
--version
-h, --help
--module
--standalone
--python-debug
--python-flag=PYTHON_FLAGS
--python-for-scons=PYTHON_SCONS
--warn-implicit-exceptions
--warn-unusual-code
--assume-yes-for-downloads
Management the inclusion of modules and packages:
--include-package=PACKAGE
--include-module=MODULE
--include-plugin-directory=MODULE/PACKAGE
--include-plugin-files=PATTERN
Management the recursion into imported modules:
--follow-stdlib, --recurse-stdlib
--nofollow-imports, --recurse-none
--follow-imports, --recurse-all
--follow-import-to=MODULE/PACKAGE, --recurse-to=MODULE/PACKAGE
--nofollow-import-to=MODULE/PACKAGE, --recurse-not-to=MODULE/PACKAGE
Speedy execution after compilation:
--run
--debugger, --gdb
--execute-with-pythonpath
Dump choices for inside tree:
--xml
Code technology selections:
--full-compat
--file-reference-choice=FILE_REFERENCE_MODE
Output selections:
-o FILENAME
--output-dir=DIRECTORY
--remove-output
--no-pyi-file
Debug options:
--debug
--unstripped
--profile
--graph
--trace-execution
--recompile-c-only
--generate-c-only
--experimental=EXPERIMENTAL
Backend C compiler alternative:
--clang
--mingw64
--msvc=MSVC
-j N, --jobs=N
--lto
Tracing options:
--show-scons
--show-progress
--show-memory
--show-modules
--verbose
Home windows particular controls:
--windows-dependency-tool=DEPENDENCY_TOOL
--windows-disable-console
--windows-icon=ICON_PATH
Plugin management:
--plugin-enable=PLUGINS_ENABLED, --enable-plugin=PLUGINS_ENABLED
--plugin-disable=PLUGINS_DISABLED, --disable-plugin=PLUGINS_DISABLED
--plugin-no-detection
--plugin-list
--user-plugin=USER_PLUGINS
First let’s take away all of the outdated stuff in order that we are able to see what occurs when a standalone
construct happens.
$ rm -rf test1.bin test1.construct
$ ls -lashp
whole 8
0 drwxr-xr-x 4 ao employees 128B ... ./
0 drwxr-xr-x 4 ao employees 128B ... ../
8 -rw-r--r-- 1 ao employees 195B ... test1.py
0 drwxr-xr-x 6 ao employees 192B ... venv/
Find out how to Construct a standalone Python App
python -m nuitka --standalone test1.py
This takes a second or two, however when it’s completed we see our distribution created.
$ ls -lashp
whole 8
0 drwxr-xr-x 6 ao employees 192B ... ./
0 drwxr-xr-x 4 ao employees 128B ... ../
0 drwxr-xr-x 20 ao employees 640B ... test1.construct/
0 drwxr-xr-x 65 ao employees 2.0K ... test1.dist/
8 -rw-r--r-- 1 ao employees 195B ... test1.py
0 drwxr-xr-x 6 ao employees 192B ... venv/
Let’s look at the construct in additional depth:
$ tree -L 2
.
├── test1.construct
│ ├── @sources.tmp
│ ├── __constants.bin
│ ├── __constants.c
│ ├── __constants.o
│ ├── __constants_data.c
│ ├── __constants_data.o
│ ├── __frozen.c
│ ├── __frozen.o
│ ├── __helpers.c
│ ├── __helpers.h
│ ├── __helpers.o
│ ├── build_definitions.h
│ ├── module.__main__.c
│ ├── module.__main__.o
│ ├── scons-report.txt
│ └── static_src
├── test1.dist
│ ├── Python
│ ├── _asyncio.so
│ ├── _bisect.so
│ ├── _blake2.so
│ ├── _bz2.so
│ ├── _codecs_cn.so
│ ├── _codecs_hk.so
│ ├── _codecs_iso2022.so
│ ├── _codecs_jp.so
│ ├── _codecs_kr.so
│ ├── _codecs_tw.so
│ ├── _contextvars.so
│ ├── _crypt.so
│ ├── _csv.so
│ ├── _ctypes.so
│ ├── _curses.so
│ ├── _curses_panel.so
│ ├── _datetime.so
│ ├── _dbm.so
│ ├── _decimal.so
│ ├── _elementtree.so
│ ├── _gdbm.so
│ ├── _hashlib.so
│ ├── _heapq.so
│ ├── _json.so
│ ├── _lsprof.so
│ ├── _lzma.so
│ ├── _multibytecodec.so
│ ├── _multiprocessing.so
│ ├── _opcode.so
│ ├── _pickle.so
│ ├── _posixsubprocess.so
│ ├── _queue.so
│ ├── _random.so
│ ├── _scproxy.so
│ ├── _sha3.so
│ ├── _socket.so
│ ├── _sqlite3.so
│ ├── _ssl.so
│ ├── _struct.so
│ ├── _tkinter.so
│ ├── _uuid.so
│ ├── array.so
│ ├── audioop.so
│ ├── binascii.so
│ ├── fcntl.so
│ ├── grp.so
│ ├── libcrypto.1.1.dylib
│ ├── libgdbm.6.dylib
│ ├── liblzma.5.dylib
│ ├── libreadline.8.dylib
│ ├── libsqlite3.0.dylib
│ ├── libssl.1.1.dylib
│ ├── math.so
│ ├── mmap.so
│ ├── pyexpat.so
│ ├── readline.so
│ ├── choose.so
│ ├── web site
│ ├── termios.so
│ ├── test1
│ ├── unicodedata.so
│ └── zlib.so
├── test1.py
└── venv
├── bin
├── embody
└── lib
8 directories, 78 recordsdata
From the above output, we see the construct
listing accommodates C language code, whereas the dist
listing accommodates a self executable test1
software.
I actually like the concept of Nuitka
and the potential it brings to the desk.
Having the ability to compile Python code could be a improbable edge to the Python group. Albeit if solely ever used to bundle a Python app and to distribute it.
Inform me what you suppose.