diff --git a/.github/workflows/build_wheels.yml b/.github/workflows/build_wheels.yml index a16246d2..ab254844 100644 --- a/.github/workflows/build_wheels.yml +++ b/.github/workflows/build_wheels.yml @@ -37,6 +37,7 @@ jobs: python -m cibuildwheel --output-dir dist env: CIBW_BUILD: ${{ matrix.cibw_build }} + CIBW_BUILD_VERBOSITY: 3 CIBW_SKIP: "*musllinux*" CIBW_MANYLINUX_X86_64_IMAGE: manylinux2014 CIBW_BEFORE_ALL_MACOS: brew install llvm && @@ -53,7 +54,6 @@ jobs: CIBW_ENVIRONMENT_LINUX: LD_LIBRARY_PATH="/tmp/filepattern_bld/local_install/lib:/tmp/filepattern_bld/local_install/lib64:$LD_LIBRARY_PATH" ON_GITHUB="TRUE" FILEPATTERN_DEP_DIR="/tmp/filepattern_bld/local_install" CIBW_ENVIRONMENT_WINDOWS: PATH="$TEMP\\filepattern\\bin;$PATH" ON_GITHUB="TRUE" FILEPATTERN_DEP_DIR="C:\\TEMP\\filepattern_bld\\local_install" CIBW_REPAIR_WHEEL_COMMAND_MACOS: DYLD_LIBRARY_PATH=$REPAIR_LIBRARY_PATH delocate-listdeps {wheel} && DYLD_LIBRARY_PATH=$REPAIR_LIBRARY_PATH delocate-wheel --require-archs {delocate_archs} -w {dest_dir} {wheel} - CIBW_REPAIR_WHEEL_COMMAND_WINDOWS: "delvewheel repair -w {dest_dir} {wheel}" CIBW_ARCHS: ${{ matrix.cibw_archs }} CIBW_TEST_REQUIRES: pytest pydantic CIBW_TEST_COMMAND: pytest {project}/tests/ diff --git a/CMakeLists.txt b/CMakeLists.txt index 5ec5443b..e2a26efb 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -10,82 +10,25 @@ endif() set(CMAKE_CXX_STANDARD 17) set(CMAKE_CXX_STANDARD_REQUIRED ON) - -file(READ src/filepattern/cpp/version.h VER_FILE ) -string(REGEX MATCH "#define PROJECT_VER \"([0-9]+)\.([0-9]+)\.([0-9+])\"" _ "${VER_FILE}") -set (filepattern_VERSION_MAJOR ${CMAKE_MATCH_1}) -set (filepattern_VERSION_MINOR ${CMAKE_MATCH_2}) -set (filepattern_VERSION_PATCH ${CMAKE_MATCH_3}) -set(filepattern_VERSION "${filepattern_VERSION_MAJOR}.${filepattern_VERSION_MINOR}.${filepattern_VERSION_PATCH}") -message(STATUS "Building filepattern ${filepattern_VERSION}" ) - option(RUN_GTEST "Downloads google unit test API and runs google test scripts to test Filepattern" OFF) -if(JAVA_BINDING) - add_compile_definitions(JAVA_BINDING) -endif() - -#==== Source files -set(SOURCE src/filepattern/cpp/pattern.cpp - src/filepattern/cpp/interface/filepattern.cpp - src/filepattern/cpp/internal/internal_pattern.cpp - src/filepattern/cpp/internal/filepattern.cpp - src/filepattern/cpp/internal/stringpattern.cpp - src/filepattern/cpp/internal/vectorpattern.cpp - src/filepattern/cpp/external/external_pattern.cpp - src/filepattern/cpp/external/external_filepattern.cpp - src/filepattern/cpp/external/external_stringpattern.cpp - src/filepattern/cpp/external/external_vectorpattern.cpp - src/filepattern/cpp/util/fs_stream.cpp - src/filepattern/cpp/util/sort.cpp - src/filepattern/cpp/util/vector_parser.cpp -) -if (NOT BUILD_PYTHON_LIB) # Not taking the setup.py route, just building libs - if (NOT MSVC) - if (NOT DEFINED CMAKE_CXX_VISIBILITY_PRESET AND - NOT DEFINED CMAKE_VISIBILITY_INLINES_HIDDEN) - set(CMAKE_CXX_VISIBILITY_PRESET hidden) - set(CMAKE_VISIBILITY_INLINES_HIDDEN YES) - endif () - endif() - - - if(DEFINED filepattern_SHARED_LIB) - set(BUILD_SHARED_LIBS ${filepattern_SHARED_LIB}) - endif() - add_library(filepattern ${SOURCE}) - add_library(filepattern::filepattern ALIAS filepattern) - set_target_properties(filepattern PROPERTIES - VERSION ${filepattern_VERSION} - SOVERSION ${filepattern_VERSION_MAJOR}) - target_include_directories( - filepattern PUBLIC "$") - include(GenerateExportHeader) - generate_export_header(filepattern EXPORT_FILE_NAME include/filepattern_export.h) - target_compile_definitions( - filepattern PUBLIC "$<$>:FILEPATTERN_STATIC_DEFINE>") - target_compile_definitions(filepattern PUBLIC FP_CPP_LIB_EXPORT) - target_include_directories( - filepattern PUBLIC "$") - if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") - target_link_libraries(filepattern PRIVATE stdc++fs) - endif() - string(COMPARE EQUAL "${CMAKE_SOURCE_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}" is_top_level) - option(filepattern_INCLUDE_PACKAGING "Include packaging rules for FilePattern" "${is_top_level}") - if (filepattern_INCLUDE_PACKAGING) - add_subdirectory(packaging) - endif () -endif() if(BUILD_PYTHON_LIB) - find_package(pybind11 CONFIG REQUIRED) - pybind11_add_module(backend - ${SOURCE} src/filepattern/cpp/bindings.cpp ) - target_compile_definitions(backend PRIVATE WITH_PYTHON_H) + find_package(filepattern QUIET) + if (NOT filepattern_FOUND) + message(STATUS "libfilepattern not found. It will be build from source.") + set(filepattern_SHARED_LIB ON) + add_subdirectory(src/filepattern/cpp ${CMAKE_BINARY_DIR}/third-party) + add_dependencies(backend filepattern) + target_include_directories(backend PRIVATE ${CMAKE_BINARY_DIR}/third-party/include) + else() + target_compile_definitions(backend PRIVATE WITH_LIBFILEPATTERN) + endif() + target_link_libraries(backend PRIVATE filepattern::filepattern) if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") target_link_libraries(backend PRIVATE stdc++fs) endif() diff --git a/setup.py b/setup.py index b41dbd3d..7f1762f4 100644 --- a/setup.py +++ b/setup.py @@ -1,15 +1,16 @@ # -*- coding: utf-8 -*- +from distutils.version import LooseVersion +from pathlib import Path +from setuptools import find_packages, Extension +from setuptools.command.build_ext import build_ext import os +import platform import re +import setuptools +import shutil +import subprocess import sys import versioneer -import platform -import subprocess -import setuptools - -from distutils.version import LooseVersion -from setuptools import find_packages, Extension -from setuptools.command.build_ext import build_ext with open("README.md", "r") as fh: long_description = fh.read() @@ -70,6 +71,13 @@ def build_extension(self, ext): cwd=self.build_temp, env=env) subprocess.check_call(['cmake', '--build', '.'] + build_args, cwd=self.build_temp) + if platform.system() == "Windows": + dll_files = list(Path(os.path.abspath(self.build_temp)).rglob("filepattern.dll")) + if len(dll_files) > 0: + for file in dll_files: + print(f"Copying ${file.as_posix()} -> {extdir}") + shutil.copy(file.as_posix(), extdir) + print() # Add an empty line for cleaner output\ diff --git a/src/filepattern/cpp/CMakeLists.txt b/src/filepattern/cpp/CMakeLists.txt new file mode 100644 index 00000000..f8e76c20 --- /dev/null +++ b/src/filepattern/cpp/CMakeLists.txt @@ -0,0 +1,78 @@ +cmake_minimum_required(VERSION 3.20) +project(libfilepattern) + +set(CMAKE_CXX_STANDARD 17) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + +if(DEFINED ENV{FILEPATTERN_DEP_DIR}) + set(CMAKE_PREFIX_PATH $ENV{FILEPATTERN_DEP_DIR}) + link_directories($ENV{FILEPATTERN_DEP_DIR}/lib) +endif() + +file(READ version.h VER_FILE ) +string(REGEX MATCH "#define PROJECT_VER \"([0-9]+)\.([0-9]+)\.([0-9+])\"" _ "${VER_FILE}") +set (filepattern_VERSION_MAJOR ${CMAKE_MATCH_1}) +set (filepattern_VERSION_MINOR ${CMAKE_MATCH_2}) +set (filepattern_VERSION_PATCH ${CMAKE_MATCH_3}) +set(filepattern_VERSION "${filepattern_VERSION_MAJOR}.${filepattern_VERSION_MINOR}.${filepattern_VERSION_PATCH}") +message(STATUS "Building libfilepattern ${filepattern_VERSION}" ) + +if(JAVA_BINDING) + add_compile_definitions(JAVA_BINDING) +endif() + +#==== Source files +set(SOURCE pattern.cpp + interface/filepattern.cpp + internal/internal_pattern.cpp + internal/filepattern.cpp + internal/stringpattern.cpp + internal/vectorpattern.cpp + external/external_pattern.cpp + external/external_filepattern.cpp + external/external_stringpattern.cpp + external/external_vectorpattern.cpp + util/fs_stream.cpp + util/sort.cpp + util/vector_parser.cpp +) + +if (NOT MSVC) + if (NOT DEFINED CMAKE_CXX_VISIBILITY_PRESET AND + NOT DEFINED CMAKE_VISIBILITY_INLINES_HIDDEN) + set(CMAKE_CXX_VISIBILITY_PRESET hidden) + set(CMAKE_VISIBILITY_INLINES_HIDDEN YES) + endif () +endif() + + +if(DEFINED filepattern_SHARED_LIB) + set(BUILD_SHARED_LIBS ${filepattern_SHARED_LIB}) +endif() +add_library(filepattern ${SOURCE}) +add_library(filepattern::filepattern ALIAS filepattern) +set_target_properties(filepattern PROPERTIES + VERSION ${filepattern_VERSION} + SOVERSION ${filepattern_VERSION_MAJOR}) +target_include_directories( + filepattern PUBLIC "$") +include(GenerateExportHeader) +generate_export_header(filepattern EXPORT_FILE_NAME include/filepattern_export.h) +target_compile_definitions( + filepattern PUBLIC "$<$>:FILEPATTERN_STATIC_DEFINE>") +target_compile_definitions(filepattern PUBLIC FP_CPP_LIB_EXPORT) +target_include_directories( + filepattern PUBLIC "$") +if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + target_link_libraries(filepattern PRIVATE stdc++fs) +endif() + +string(COMPARE EQUAL "${CMAKE_SOURCE_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}" is_top_level) +option(filepattern_INCLUDE_PACKAGING "Include packaging rules for FilePattern" "${is_top_level}") +if (filepattern_INCLUDE_PACKAGING) + add_subdirectory(packaging) +endif () + + +set(CMAKE_POSITION_INDEPENDENT_CODE ON) + diff --git a/src/filepattern/cpp/bindings.cpp b/src/filepattern/cpp/bindings.cpp index 769e9c84..1d5c3c30 100644 --- a/src/filepattern/cpp/bindings.cpp +++ b/src/filepattern/cpp/bindings.cpp @@ -3,14 +3,16 @@ #include #include #include -#include -#include "include/filepattern.h" #include "pattern_object.hpp" -namespace py = pybind11; +#ifdef WITH_LIBFILEPATTERN +#include "filepattern/filepattern.h" +#else +#include "include/filepattern.h" +#endif -//PYBIND11_MAKE_OPAQUE(std::vector>); +namespace py = pybind11; PYBIND11_MODULE(backend, m){ diff --git a/src/filepattern/cpp/interface/filepattern.cpp b/src/filepattern/cpp/interface/filepattern.cpp index 4e5989d9..70781358 100644 --- a/src/filepattern/cpp/interface/filepattern.cpp +++ b/src/filepattern/cpp/interface/filepattern.cpp @@ -1,6 +1,5 @@ #include "../include/filepattern.h" #include "filepattern_factory.h" -#include "../pattern_object.hpp" FilePattern::FilePattern(const std::string& path, const std::string& filePattern, const std::string& block_size, bool recursive, bool suppressWarnings) { diff --git a/packaging/CMakeLists.txt b/src/filepattern/cpp/packaging/CMakeLists.txt similarity index 92% rename from packaging/CMakeLists.txt rename to src/filepattern/cpp/packaging/CMakeLists.txt index 43b78bdd..721cdf69 100644 --- a/packaging/CMakeLists.txt +++ b/src/filepattern/cpp/packaging/CMakeLists.txt @@ -14,7 +14,7 @@ install(TARGETS filepattern EXPORT filepattern_Targets INCLUDES DESTINATION "${CMAKE_INSTALL_INCLUDEDIR}" ) -install(DIRECTORY "${filepattern_SOURCE_DIR}/src/filepattern/cpp/include/" "${filepattern_BINARY_DIR}/include/" +install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/../include/" "${CMAKE_CURRENT_BINARY_DIR}/../include/" DESTINATION "${CMAKE_INSTALL_INCLUDEDIR}/filepattern/" COMPONENT filepattern_Development) diff --git a/packaging/filepatternConfig.cmake b/src/filepattern/cpp/packaging/filepatternConfig.cmake similarity index 97% rename from packaging/filepatternConfig.cmake rename to src/filepattern/cpp/packaging/filepatternConfig.cmake index f2b9b0de..574dc49c 100644 --- a/packaging/filepatternConfig.cmake +++ b/src/filepattern/cpp/packaging/filepatternConfig.cmake @@ -55,3 +55,5 @@ else () filepattern_load_targets(shared) endif () endif () + +message(STATUS "Found libfilepattern: ${filepattern_VERSION}") \ No newline at end of file diff --git a/src/filepattern/cpp/pattern_object.hpp b/src/filepattern/cpp/pattern_object.hpp index 59cb8b84..d6973b15 100644 --- a/src/filepattern/cpp/pattern_object.hpp +++ b/src/filepattern/cpp/pattern_object.hpp @@ -7,7 +7,25 @@ #include #include -#include "util/util.hpp" + +#if __has_include() + #include + namespace fs = std::filesystem; +#elif __has_include() + #include + namespace fs = std::experimental::filesystem; +#else + error "Missing the header." +#endif + +using Types = std::variant; +using Map = std::map; +#ifdef JAVA_BINDING +using Tuple = std::tuple>; +#else +using Tuple = std::tuple>; +#endif + class PatternObject { public: @@ -83,4 +101,4 @@ class PatternObject { -}; +}; \ No newline at end of file diff --git a/src/filepattern/cpp/util/fs_stream.cpp b/src/filepattern/cpp/util/fs_stream.cpp index fcc36310..892bb6ee 100644 --- a/src/filepattern/cpp/util/fs_stream.cpp +++ b/src/filepattern/cpp/util/fs_stream.cpp @@ -192,10 +192,10 @@ void FilesystemStream::writeValidFiles(const Tuple& mapping){ } for(const auto& element: get<1>(mapping)){ - #ifdef WITH_PYTHON_H - file << element.string() << "," << '\n'; - #else + #ifdef JAVA_BINDING file << element << "," << '\n'; + #else + file << element.string() << "," << '\n'; #endif }