Делаем standalone exe на IronPython

в 8:50, , рубрики: .net, exe, ironpython, python, windows, метки: , , , ,

Иногда требуется написать маленькую программу, которая будет распространяться в виде исполняемого файла, и при этом не хочется, чтобы с программой ещё было море файлов. Один exe-шник и всё, да при этом хочется, чтобы его написание не занимало много времени (какой-нибудь лёгкий язык).
CPython в комплекте с py2exe или cx_Freeze не даёт требуемого результата: много файлов и большой размер программы, хотя и работает очень быстро.
Даже попробовал в Racket Creating Stand-Alone Executables, но хотелось всё же использовать Python, так как много наработок. Да и Racket тоже сгенерировал немало дополнительного «мусора».
Чистое решение смог получить в IronPython с помощью встроенного компилятора pyc. Даже IDE не потребовалась. Подробности под катом.

Всё оказалось просто

Допустим у вас уже установлен IronPython. И у вас есть следующий исходный код:

import clr
clr.AddReference("System.Windows.Forms")

from System.Windows.Forms import Application, Form

class HabrForm(Form):

     def __init__(self):
         self.Text = 'Habr!'
         self.Name = 'Habr!'

form = HabrForm()
Application.Run(form)

Сохраните его в файл mini.py. Зайдите в папку с программой из консоли и наберите следующую команду:

ipy.exe C:IronPythonToolsScriptspyc.py /target:winexe /main:mini.py /standalone

Если установить target в exe получите консольную программу, что удобно для отладки. Также можно сделать dll.

Компилятор выдаст примерно что-то такое:

Input Files:
Output:
        mini
Target:
        WindowApplication
Platform:
        ILOnly
Machine:
        I386
Threading:
        STA

Compiling...
Generating stand alone executable
        Embedding Microsoft.Dynamic 1.1.0.20
        Embedding Microsoft.Scripting 1.1.0.20
        Embedding IronPython 2.7.0.40
        Embedding IronPython.Modules 2.7.0.40
        Embedding IronPython.SQLite 2.7.0.40
        Embedding IronPython.Wpf 2.7.0.40
Saved to mini

Exe-шник готов! Только учтите, что стандартной библиотеки в этой сборке нет. И это хорошо. Можно построить программу используя только clr модуль на быстрых .NET библиотеках.

Подключение стандартной библиотеки

Если нужна стандартная библиотека, то есть 2 способа подключения. Первый — скомпилировать всю папку Lib в одну dll и сделать AddReference. Есть готовое решение на Stackowerflow, но в этом решении программа работает слишком медленно!

Я пошёл по другому пути. Учитывая, что IronPython имеет в составе встроенный модуль sys, а загрузчик модулей умеет читать модули из zip, то решение стало очевидным: запаковать содержимое папки Lib (из папки IronPython) и поместить рядом с exe файлом, при этом добавив следующий код:

import sys
sys.path.append(r'.Lib.zip')

Теперь можно импортировать другие модули, вроде json или urllib.
Вот и всё, посмотрите как здорово это выглядит:
Делаем standalone exe на IronPython

Автор: deko


* - обязательные к заполнению поля


https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js