#!/usr/bin/python -u
#
# Setup script for libxml2 and libxslt if found
#
import sys, os
from distutils.core import setup, Extension

# Below ROOT, we expect to find include, include/libxml2, lib and bin.
# On *nix, it is not needed (but should not harm),
# on Windows, it is set by configure.js.
ROOT = r'@prefix@'

# Thread-enabled libxml2
with_threads = @WITH_THREADS@

# If this flag is set (windows only),
# a private copy of the dlls are included in the package.
# If this flag is not set, the libxml2 and libxslt
# dlls must be found somewhere in the PATH at runtime.
WITHDLLS = 1 and sys.platform.startswith('win')

def missing(file):
    if os.access(file, os.R_OK) == 0:
        return 1
    return 0

try:
    HOME = os.environ['HOME']
except:
    HOME="C:"

if WITHDLLS:
    # libxml dlls (expected in ROOT/bin)
    dlls = [ 'iconv.dll','libxml2.dll','libxslt.dll','libexslt.dll' ]
    dlls = [os.path.join(ROOT,'bin',dll) for dll in dlls]

    # create __init__.py for the libxmlmods package
    if not os.path.exists("libxmlmods"):
        os.mkdir("libxmlmods")
        open("libxmlmods/__init__.py","w").close()

    def altImport(s):
        s = s.replace("import libxml2mod","from libxmlmods import libxml2mod")
        s = s.replace("import libxsltmod","from libxmlmods import libxsltmod")
        return s

if sys.platform.startswith('win'):
    libraryPrefix = 'lib'
    platformLibs = []
else:
    libraryPrefix = ''
    platformLibs = ["m","z"]

# those are examined to find
# - libxml2/libxml/tree.h
# - iconv.h
# - libxslt/xsltconfig.h
includes_dir = [
"/usr/include",
"/usr/local/include",
"/opt/include",
os.path.join(ROOT,'include'),
HOME
];

xml_includes=""
for dir in includes_dir:
    if not missing(dir + "/libxml2/libxml/tree.h"):
        xml_includes=dir + "/libxml2"
        break;

if xml_includes == "":
    print("failed to find headers for libxml2: update includes_dir")
    sys.exit(1)

iconv_includes=""
for dir in includes_dir:
    if not missing(dir + "/iconv.h"):
        iconv_includes=dir
        break;

if iconv_includes == "":
    print("failed to find headers for libiconv: update includes_dir")
    sys.exit(1)

# those are added in the linker search path for libraries
libdirs = [
os.path.join(ROOT,'lib'),
]

xml_files = ["libxml2-api.xml", "libxml2-python-api.xml",
             "libxml.c", "libxml.py", "libxml_wrap.h", "types.c",
             "xmlgenerator.py", "README", "TODO", "drv_libxml2.py"]

xslt_files = ["libxslt-api.xml", "libxslt-python-api.xml",
             "libxslt.c", "libxsl.py", "libxslt_wrap.h",
             "xsltgenerator.py"]

if missing("libxml2-py.c") or missing("libxml2.py"):
    try:
        try:
            import xmlgenerator
        except:
            import generator
    except:
        print("failed to find and generate stubs for libxml2, aborting ...")
        print(sys.exc_info()[0], sys.exc_info()[1])
        sys.exit(1)

    head = open("libxml.py", "r")
    generated = open("libxml2class.py", "r")
    result = open("libxml2.py", "w")
    for line in head.readlines():
        if WITHDLLS:
            result.write(altImport(line))
        else:
            result.write(line)
    for line in generated.readlines():
        result.write(line)
    head.close()
    generated.close()
    result.close()

with_xslt=0
if missing("libxslt-py.c") or missing("libxslt.py"):
    if missing("xsltgenerator.py") or missing("libxslt-api.xml"):
        print("libxslt stub generator not found, libxslt not built")
    else:
        try:
            import xsltgenerator
        except:
            print("failed to generate stubs for libxslt, aborting ...")
            print(sys.exc_info()[0], sys.exc_info()[1])
        else:
            head = open("libxsl.py", "r")
            generated = open("libxsltclass.py", "r")
            result = open("libxslt.py", "w")
            for line in head.readlines():
                if WITHDLLS:
                    result.write(altImport(line))
                else:
                    result.write(line)
            for line in generated.readlines():
                result.write(line)
            head.close()
            generated.close()
            result.close()
            with_xslt=1
else:
    with_xslt=1

if with_xslt == 1:
    xslt_includes=""
    for dir in includes_dir:
        if not missing(dir + "/libxslt/xsltconfig.h"):
            xslt_includes=dir + "/libxslt"
            break;

    if xslt_includes == "":
        print("failed to find headers for libxslt: update includes_dir")
        with_xslt = 0


descr = "libxml2 package"
modules = [ 'libxml2', 'drv_libxml2' ]
if WITHDLLS:
    modules.append('libxmlmods.__init__')
c_files = ['libxml2-py.c', 'libxml.c', 'types.c' ]
includes= [xml_includes, iconv_includes]
libs    = [libraryPrefix + "xml2"] + platformLibs
macros  = []
if with_threads:
    macros.append(('_REENTRANT','1'))
if with_xslt == 1:
    descr = "libxml2 and libxslt package"
    if not sys.platform.startswith('win'):
        #
        # We are gonna build 2 identical shared libs with merge initializing
        # both libxml2mod and libxsltmod
        #
        c_files = c_files + ['libxslt-py.c', 'libxslt.c']
        xslt_c_files = c_files
        macros.append(('MERGED_MODULES', '1'))
    else:
        #
        # On windows the MERGED_MODULE option is not needed
        # (and does not work)
        #
        xslt_c_files = ['libxslt-py.c', 'libxslt.c', 'types.c']
    libs.insert(0, libraryPrefix + 'exslt')
    libs.insert(0, libraryPrefix + 'xslt')
    includes.append(xslt_includes)
    modules.append('libxslt')


extens=[Extension('libxml2mod', c_files, include_dirs=includes,
                  library_dirs=libdirs,
                  libraries=libs, define_macros=macros)]
if with_xslt == 1:
    extens.append(Extension('libxsltmod', xslt_c_files, include_dirs=includes,
                            library_dirs=libdirs,
                            libraries=libs, define_macros=macros))

if missing("MANIFEST"):

    manifest = open("MANIFEST", "w")
    manifest.write("setup.py\n")
    for file in xml_files:
        manifest.write(file + "\n")
    if with_xslt == 1:
        for file in xslt_files:
            manifest.write(file + "\n")
    manifest.close()

if WITHDLLS:
    ext_package = "libxmlmods"
    if sys.version >= "2.2":
        base = "lib/site-packages/"
    else:
        base = ""
    data_files = [(base+"libxmlmods",dlls)]
else:
    ext_package = None
    data_files = []

setup (name = "libxml2-python",
       # On *nix, the version number is created from setup.py.in
       # On windows, it is set by configure.js
       version = "@LIBXML_VERSION@",
       description = descr,
       author = "Daniel Veillard",
       author_email = "veillard@redhat.com",
       url = "http://xmlsoft.org/python.html",
       licence="MIT Licence",
       py_modules=modules,
       ext_modules=extens,
       ext_package=ext_package,
       data_files=data_files,
       )

sys.exit(0)

