Migrated Python pkg mgmt to Poetry
This commit is contained in:
142
pkg/pypi/build.py
Normal file
142
pkg/pypi/build.py
Normal file
@@ -0,0 +1,142 @@
|
||||
"""
|
||||
Poetry build.py
|
||||
|
||||
See: https://stackoverflow.com/questions/60073711/how-to-build-c-extensions-via-poetry
|
||||
"""
|
||||
import os
|
||||
import shutil
|
||||
import subprocess
|
||||
from distutils.command.build_ext import build_ext
|
||||
from distutils.errors import DistutilsPlatformError, CCompilerError, DistutilsExecError
|
||||
from distutils.extension import Extension
|
||||
|
||||
from glob import glob
|
||||
|
||||
|
||||
DIR = os.path.dirname(os.path.realpath(__file__))
|
||||
ROOT_DIR = os.path.abspath(os.path.join(DIR, "..", ".."))
|
||||
|
||||
INCLUDE_DIRS = [
|
||||
os.path.join(ROOT_DIR, "include"),
|
||||
os.path.join(ROOT_DIR, "src"),
|
||||
os.path.join(ROOT_DIR, "src/bindings/python"),
|
||||
os.path.join(ROOT_DIR, "ext/concurrentqueue"),
|
||||
os.path.join(ROOT_DIR, "ext/lwip/src/include"),
|
||||
os.path.join(ROOT_DIR, "ext/lwip-contrib/ports/unix/port/include"),
|
||||
os.path.join(ROOT_DIR, "ext/ZeroTierOne/include"),
|
||||
os.path.join(ROOT_DIR, "ext/ZeroTierOne"),
|
||||
os.path.join(ROOT_DIR, "ext/ZeroTierOne/node"),
|
||||
os.path.join(ROOT_DIR, "ext/ZeroTierOne/service"),
|
||||
os.path.join(ROOT_DIR, "ext/ZeroTierOne/osdep"),
|
||||
os.path.join(ROOT_DIR, "ext/ZeroTierOne/controller"),
|
||||
]
|
||||
|
||||
|
||||
class LibztModule(Extension):
|
||||
"""Libzt extension module"""
|
||||
def __init__(self):
|
||||
sources = [
|
||||
*glob(os.path.join(ROOT_DIR, "src/bindings/python/*.cxx")),
|
||||
*glob(os.path.join(ROOT_DIR, "src/bindings/python/zt.i")),
|
||||
*glob(os.path.join(ROOT_DIR, "src/*.cpp")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/ZeroTierOne/node/*.cpp")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/ZeroTierOne/osdep/OSUtils.cpp")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/ZeroTierOne/osdep/PortMapper.cpp")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/ZeroTierOne/osdep/ManagedRoute.cpp")),
|
||||
]
|
||||
# noinspection PyUnresolvedReferences
|
||||
assert len(sources) > 0, "no sources found"
|
||||
|
||||
# noinspection PyTypeChecker
|
||||
super().__init__(
|
||||
"libzt._libzt",
|
||||
sources=sources,
|
||||
include_dirs=INCLUDE_DIRS,
|
||||
extra_compile_args=[
|
||||
"-std=c++11",
|
||||
"-DZTS_ENABLE_PYTHON=1",
|
||||
"-DZT_SDK",
|
||||
"-Wno-parentheses-equality",
|
||||
"-Wno-macro-redefined",
|
||||
"-Wno-tautological-overlap-compare",
|
||||
"-Wno-tautological-constant-out-of-range-compare",
|
||||
],
|
||||
swig_opts=[
|
||||
"-c++",
|
||||
f"-I{os.path.join(ROOT_DIR, 'include')}",
|
||||
],
|
||||
)
|
||||
|
||||
|
||||
def cstuff():
|
||||
"""C library"""
|
||||
sources = [
|
||||
# libnatpmp
|
||||
*glob(os.path.join(ROOT_DIR, "ext/ZeroTierOne/ext/libnatpmp/natpmp.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/ZeroTierOne/ext/libnatpmp/wingettimeofday.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/ZeroTierOne/ext/libnatpmp/getgateway.c")),
|
||||
# miniupnpc
|
||||
*glob(os.path.join(ROOT_DIR, "ext/miniupnpc/*.c")),
|
||||
# lwip
|
||||
*glob(os.path.join(ROOT_DIR, "ext/lwip/src/netif/*.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/lwip/src/api/*.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/lwip/src/core/*.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/lwip/src/core/ipv4/*.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/lwip/src/core/ipv6/*.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/lwip/src/netif/*.c")),
|
||||
*glob(os.path.join(ROOT_DIR, "ext/lwip-contrib/ports/unix/port/sys_arch.c")),
|
||||
]
|
||||
# noinspection PyUnresolvedReferences
|
||||
assert len(sources) > 0, "no sources"
|
||||
|
||||
return ("cstuff", {
|
||||
"sources": sources,
|
||||
"include_dirs": INCLUDE_DIRS,
|
||||
})
|
||||
|
||||
|
||||
class BuildFailed(Exception):
|
||||
pass
|
||||
|
||||
|
||||
class ExtBuilder(build_ext):
|
||||
|
||||
def run(self):
|
||||
try:
|
||||
build_ext.run(self)
|
||||
except (DistutilsPlatformError, FileNotFoundError):
|
||||
raise BuildFailed('File not found. Could not compile C extension.')
|
||||
|
||||
def build_extension(self, ext):
|
||||
try:
|
||||
build_ext.build_extension(self, ext)
|
||||
except (CCompilerError, DistutilsExecError, DistutilsPlatformError, ValueError):
|
||||
raise BuildFailed('Could not compile C extension.')
|
||||
|
||||
|
||||
def build(setup_kwargs):
|
||||
"""Build """
|
||||
|
||||
assert os.getcwd() == DIR, f"must be invoked from {DIR}"
|
||||
|
||||
# Ensure git submodules are loaded
|
||||
subprocess.run(["git", "submodule", "update", "--init"])
|
||||
|
||||
# Copy Python files into packaging directory
|
||||
src_dir = os.path.join(ROOT_DIR, "src", "bindings", "python")
|
||||
dst_dir = os.path.join(DIR, "libzt")
|
||||
for filename in os.listdir(src_dir):
|
||||
if os.path.isfile(os.path.join(src_dir, filename)) and filename.endswith(".py"):
|
||||
shutil.copy(os.path.join(src_dir, filename), os.path.join(dst_dir, filename))
|
||||
|
||||
# LICENSE file
|
||||
shutil.copy(os.path.join(ROOT_DIR, "LICENSE.txt"), os.path.join(DIR, "LICENSE"))
|
||||
|
||||
# Pass up extensions information
|
||||
setup_kwargs["libraries"] = [cstuff()]
|
||||
setup_kwargs["ext_modules"] = [LibztModule()]
|
||||
setup_kwargs["cmdclass"] = {"build_ext": ExtBuilder}
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,39 +0,0 @@
|
||||
#!/bin/bash
|
||||
|
||||
PYBIN=python3
|
||||
|
||||
# Build the extension module
|
||||
ext()
|
||||
{
|
||||
# Symbolic link to source tree so that sdist structure makes sense
|
||||
ln -s ../../ native
|
||||
# Re-build wrapper to export C symbols
|
||||
swig -c++ -python -o native/src/bindings/python/zt_wrap.cxx -I./native/include native/src/bindings/python/zt.i
|
||||
# Copy language bindings into module directory
|
||||
cp -f native/src/bindings/python/*.py libzt/
|
||||
cp -f native/LICENSE.txt LICENSE
|
||||
# Build C libraries (and then) C++ extension
|
||||
$PYBIN setup.py build_clib --verbose build_ext -i --verbose
|
||||
}
|
||||
|
||||
# Build a wheel
|
||||
wheel()
|
||||
{
|
||||
ext
|
||||
$PYBIN setup.py bdist_wheel
|
||||
}
|
||||
|
||||
clean()
|
||||
{
|
||||
find . -name '*.so' -type f -delete
|
||||
find . -name '*.pyc' -type f -delete
|
||||
find . -name '__pycache__' -type d -delete
|
||||
rm -rf libzt/sockets.py
|
||||
rm -rf libzt/libzt.py
|
||||
rm -rf libzt/node.py
|
||||
rm -rf src ext build dist native
|
||||
rm -rf libzt.egg-info
|
||||
rm -rf LICENSE
|
||||
}
|
||||
|
||||
"$@"
|
||||
@@ -1 +1,2 @@
|
||||
__version__ = "1.8.4"
|
||||
import pkg_resources
|
||||
__version__ = pkg_resources.get_distribution("libzt").version
|
||||
|
||||
60
pkg/pypi/pyproject.toml
Normal file
60
pkg/pypi/pyproject.toml
Normal file
@@ -0,0 +1,60 @@
|
||||
[tool.poetry]
|
||||
name = "libzt"
|
||||
version = "1.8.4"
|
||||
description = "ZeroTier"
|
||||
authors = ["ZeroTier, Inc."]
|
||||
license = "BUSL 1.1"
|
||||
readme = "README.md"
|
||||
homepage = "https://www.zerotier.com/"
|
||||
repository = "https://github.com/zerotier/libzt/"
|
||||
documentation = "https://docs.zerotier.com/"
|
||||
keywords = [
|
||||
"zerotier",
|
||||
"p2p",
|
||||
"peer-to-peer",
|
||||
"sdwan",
|
||||
"sdn",
|
||||
"virtual",
|
||||
"network",
|
||||
"socket",
|
||||
"tcp",
|
||||
"udp",
|
||||
"zt",
|
||||
"encryption",
|
||||
"encrypted",
|
||||
]
|
||||
classifiers = [
|
||||
"Topic :: Internet",
|
||||
"Topic :: System :: Networking",
|
||||
"Topic :: Security :: Cryptography",
|
||||
"Intended Audience :: Developers",
|
||||
"Intended Audience :: Information Technology",
|
||||
"Intended Audience :: System Administrators",
|
||||
"Intended Audience :: Telecommunications Industry",
|
||||
"Intended Audience :: End Users/Desktop",
|
||||
"License :: Free for non-commercial use",
|
||||
"Operating System :: MacOS",
|
||||
"Operating System :: POSIX :: BSD",
|
||||
"Operating System :: POSIX :: Linux",
|
||||
"Operating System :: Unix",
|
||||
"Programming Language :: C",
|
||||
"Programming Language :: Python",
|
||||
"Programming Language :: C++",
|
||||
]
|
||||
packages = [
|
||||
{ include = "libzt" },
|
||||
]
|
||||
build = "build.py"
|
||||
|
||||
[tool.poetry.dependencies]
|
||||
python = "^3.5"
|
||||
|
||||
[tool.poetry.dev-dependencies]
|
||||
|
||||
[tool.poetry.urls]
|
||||
"GitHub" = "https://github.com/zerotier/libzt/"
|
||||
"Issue Tracker" = "https://github.com/zerotier/libzt/issues"
|
||||
|
||||
[build-system]
|
||||
requires = ["poetry-core>=1.0.0"]
|
||||
build-backend = "poetry.core.masonry.api"
|
||||
@@ -1,6 +0,0 @@
|
||||
[metadata]
|
||||
version = attr: libzt.__version__
|
||||
description_file = README.md
|
||||
license_files =
|
||||
native/LICENSE.txt
|
||||
native/ext/THIRDPARTY.txt
|
||||
@@ -1,133 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
|
||||
from setuptools import setup, Extension, Command, Distribution
|
||||
from distutils.util import convert_path
|
||||
import glob
|
||||
import os
|
||||
|
||||
main_ns = {}
|
||||
ver_path = convert_path('libzt/version.py')
|
||||
with open(ver_path) as ver_file:
|
||||
exec(ver_file.read(), main_ns)
|
||||
|
||||
from os import path
|
||||
this_directory = path.abspath(path.dirname(__file__))
|
||||
with open(path.join(this_directory, 'README.md'), encoding='utf-8') as f:
|
||||
long_description = f.read()
|
||||
|
||||
class BinaryDistribution(Distribution):
|
||||
def is_pure(self):
|
||||
return False
|
||||
|
||||
# monkey-patch for parallel compilation
|
||||
# Copied from: https://stackoverflow.com/a/13176803
|
||||
def parallelCCompile(self, sources, output_dir=None, macros=None, include_dirs=None, debug=0, extra_preargs=None, extra_postargs=None, depends=None):
|
||||
# those lines are copied from distutils.ccompiler.CCompiler directly
|
||||
macros, objects, extra_postargs, pp_opts, build = self._setup_compile(output_dir, macros, include_dirs, sources, depends, extra_postargs)
|
||||
cc_args = self._get_cc_args(pp_opts, debug, extra_preargs)
|
||||
# parallel code
|
||||
N=16 # number of parallel compilations
|
||||
import multiprocessing.pool
|
||||
def _single_compile(obj):
|
||||
try: src, ext = build[obj]
|
||||
except KeyError: return
|
||||
self._compile(obj, src, ext, cc_args, extra_postargs, pp_opts)
|
||||
# convert to list, imap is evaluated on-demand
|
||||
list(multiprocessing.pool.ThreadPool(N).imap(_single_compile,objects))
|
||||
return objects
|
||||
import distutils.ccompiler
|
||||
distutils.ccompiler.CCompiler.compile=parallelCCompile
|
||||
|
||||
# Build
|
||||
|
||||
cpp_glob = []
|
||||
c_glob = []
|
||||
|
||||
# Windows
|
||||
if os.name == 'nt':
|
||||
print('TODO')
|
||||
#extra_compile_args=['/std:c++14', '-DNOMINMAX=1', '-DZT_SDK', '-DSDK'],
|
||||
#extra_link_args=['/LIBPATH:.', 'WS2_32.Lib', 'ShLwApi.Lib', 'iphlpapi.Lib','lwip.lib'],
|
||||
|
||||
# Everything else
|
||||
else:
|
||||
cpp_glob.extend(list(glob.glob('native/src/bindings/python/*.cxx')))
|
||||
cpp_glob.extend(list(glob.glob('native/src/*.cpp')))
|
||||
cpp_glob.extend(list(glob.glob('native/ext/ZeroTierOne/node/*.cpp')))
|
||||
cpp_glob.extend(list(glob.glob('native/ext/ZeroTierOne/osdep/OSUtils.cpp')))
|
||||
cpp_glob.extend(list(glob.glob('native/ext/ZeroTierOne/osdep/PortMapper.cpp')))
|
||||
cpp_glob.extend(list(glob.glob('native/ext/ZeroTierOne/osdep/ManagedRoute.cpp')))
|
||||
|
||||
my_include_dirs=['native/include',
|
||||
'native/src',
|
||||
'native/src/bindings/python',
|
||||
'native/ext/concurrentqueue',
|
||||
'native/ext/lwip/src/include',
|
||||
'native/ext/lwip-contrib/ports/unix/port/include',
|
||||
'native/ext/ZeroTierOne/include',
|
||||
'native/ext/ZeroTierOne',
|
||||
'native/ext/ZeroTierOne/node',
|
||||
'native/ext/ZeroTierOne/service',
|
||||
'native/ext/ZeroTierOne/osdep',
|
||||
'native/ext/ZeroTierOne/controller']
|
||||
|
||||
libzt_module = Extension('libzt._libzt',
|
||||
extra_compile_args=['-std=c++11', '-DZTS_ENABLE_PYTHON=1', '-DZT_SDK', '-Wno-parentheses-equality', '-Wno-macro-redefined', '-Wno-tautological-overlap-compare', '-Wno-tautological-constant-out-of-range-compare'],
|
||||
sources=cpp_glob, include_dirs=my_include_dirs)
|
||||
|
||||
# Separate C library, this is needed since C++ compiler flags are applied
|
||||
# to everything in the extension module regardless of type.
|
||||
|
||||
# libnatpmp
|
||||
c_glob.extend(list(glob.glob('native/ext/ZeroTierOne/ext/libnatpmp/natpmp.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/ZeroTierOne/ext/libnatpmp/wingettimeofday.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/ZeroTierOne/ext/libnatpmp/getgateway.c')))
|
||||
# miniupnpc
|
||||
c_glob.extend(list(glob.glob('native/ext/miniupnpc/*.c')))
|
||||
# lwip
|
||||
c_glob.extend(list(glob.glob('native/ext/lwip/src/netif/*.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/lwip/src/api/*.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/lwip/src/core/*.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/lwip/src/core/ipv4/*.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/lwip/src/core/ipv6/*.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/lwip/src/netif/*.c')))
|
||||
c_glob.extend(list(glob.glob('native/ext/lwip-contrib/ports/unix/port/sys_arch.c')))
|
||||
|
||||
cstuff = ('cstuff', {'sources':
|
||||
c_glob, 'include_dirs': my_include_dirs})
|
||||
|
||||
setup(
|
||||
name = 'libzt',
|
||||
version = main_ns['__version__'],
|
||||
description = 'ZeroTier',
|
||||
long_description=long_description,
|
||||
long_description_content_type='text/markdown',
|
||||
author = 'ZeroTier, Inc.',
|
||||
author_email = 'joseph@zerotier.com',
|
||||
url = 'https://github.com/zerotier/libzt',
|
||||
license='BUSL 1.1',
|
||||
download_url = 'https://github.com/zerotier/libzt/releases',
|
||||
keywords = 'zerotier p2p peer-to-peer sdwan sdn virtual network socket tcp udp zt encryption encrypted',
|
||||
py_modules = ['libzt'],
|
||||
packages = ['libzt'],
|
||||
classifiers = ['Topic :: Internet',
|
||||
'Topic :: System :: Networking',
|
||||
'Topic :: Security :: Cryptography',
|
||||
'Intended Audience :: Developers',
|
||||
'Intended Audience :: Information Technology',
|
||||
'Intended Audience :: System Administrators',
|
||||
'Intended Audience :: Telecommunications Industry',
|
||||
'Intended Audience :: End Users/Desktop',
|
||||
'License :: Free for non-commercial use',
|
||||
'Operating System :: MacOS',
|
||||
'Operating System :: POSIX :: BSD',
|
||||
'Operating System :: POSIX :: Linux',
|
||||
'Operating System :: Unix',
|
||||
'Programming Language :: C',
|
||||
'Programming Language :: C++',
|
||||
'Programming Language :: Python'
|
||||
],
|
||||
distclass=BinaryDistribution,
|
||||
libraries=[cstuff],
|
||||
ext_modules = [libzt_module],
|
||||
)
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,60 +0,0 @@
|
||||
/* ----------------------------------------------------------------------------
|
||||
* This file was automatically generated by SWIG (http://www.swig.org).
|
||||
* Version 4.0.2
|
||||
*
|
||||
* This file is not intended to be easily readable and contains a number of
|
||||
* coding conventions designed to improve portability and efficiency. Do not make
|
||||
* changes to this file unless you know what you are doing--modify the SWIG
|
||||
* interface file instead.
|
||||
* ----------------------------------------------------------------------------- */
|
||||
|
||||
#ifndef SWIG_libzt_WRAP_H_
|
||||
#define SWIG_libzt_WRAP_H_
|
||||
|
||||
#include <map>
|
||||
#include <string>
|
||||
|
||||
|
||||
class SwigDirector_PythonDirectorCallbackClass : public PythonDirectorCallbackClass, public Swig::Director {
|
||||
|
||||
public:
|
||||
SwigDirector_PythonDirectorCallbackClass(PyObject *self);
|
||||
virtual void on_zerotier_event(zts_event_msg_t *msg);
|
||||
virtual ~SwigDirector_PythonDirectorCallbackClass();
|
||||
|
||||
/* Internal director utilities */
|
||||
public:
|
||||
bool swig_get_inner(const char *swig_protected_method_name) const {
|
||||
std::map<std::string, bool>::const_iterator iv = swig_inner.find(swig_protected_method_name);
|
||||
return (iv != swig_inner.end() ? iv->second : false);
|
||||
}
|
||||
void swig_set_inner(const char *swig_protected_method_name, bool swig_val) const {
|
||||
swig_inner[swig_protected_method_name] = swig_val;
|
||||
}
|
||||
private:
|
||||
mutable std::map<std::string, bool> swig_inner;
|
||||
|
||||
#if defined(SWIG_PYTHON_DIRECTOR_VTABLE)
|
||||
/* VTable implementation */
|
||||
PyObject *swig_get_method(size_t method_index, const char *method_name) const {
|
||||
PyObject *method = vtable[method_index];
|
||||
if (!method) {
|
||||
swig::SwigVar_PyObject name = SWIG_Python_str_FromChar(method_name);
|
||||
method = PyObject_GetAttr(swig_get_self(), name);
|
||||
if (!method) {
|
||||
std::string msg = "Method in class PythonDirectorCallbackClass doesn't exist, undefined ";
|
||||
msg += method_name;
|
||||
Swig::DirectorMethodException::raise(msg.c_str());
|
||||
}
|
||||
vtable[method_index] = method;
|
||||
}
|
||||
return method;
|
||||
}
|
||||
private:
|
||||
mutable swig::SwigVar_PyObject vtable[1];
|
||||
#endif
|
||||
|
||||
};
|
||||
|
||||
|
||||
#endif
|
||||
Reference in New Issue
Block a user