diff --git a/.cirrus.yml b/.cirrus.yml index b67e17c5292..5afd9743238 100644 --- a/.cirrus.yml +++ b/.cirrus.yml @@ -30,23 +30,25 @@ task: freebsd_instance: cpu: 4 memory: 8G - image_family: freebsd-12-2 + image_family: freebsd-12-3 - name: 😈 FreeBSD 13 freebsd_instance: cpu: 4 memory: 8G - image_family: freebsd-13-0 + image_family: freebsd-13-1 - name: 😈 ASAN freebsd_instance: cpu: 8 memory: 8G - image_family: freebsd-13-0 + image_family: freebsd-13-1 env: ENABLE_ASAN: ON install_script: + - pkg update -f + - pkg upgrade -y - > pkg install -y bison diff --git a/CMakeLists.txt b/CMakeLists.txt index 34915dcb27d..2722f3b9300 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,4 +1,4 @@ -cmake_minimum_required (VERSION 3.4) +cmake_minimum_required (VERSION 3.12) # allows us to override platform specific variables set (CMAKE_USER_MAKE_RULES_OVERRIDE "${CMAKE_SOURCE_DIR}/scripts/cmake/Platform.cmake") @@ -12,20 +12,11 @@ set (ELEKTRA_DESCRIPTION "Elektra serves as a universal and secure framework to access configuration settings in a global, hierarchical key database.") set (ELEKTRA_HOMEPAGE_URL "https://www.libelektra.org") -if (CMAKE_VERSION VERSION_LESS 3.9) - project (Elektra VERSION "${KDB_VERSION}") -elseif (CMAKE_VERSION VERSION_LESS 3.12) - project ( - Elektra - VERSION ${KDB_VERSION} - DESCRIPTION ${ELEKTRA_DESCRIPTION}) -else (CMAKE_VERSION VERSION_LESS 3.12) - project ( - Elektra - VERSION ${KDB_VERSION} - DESCRIPTION ${ELEKTRA_DESCRIPTION} - HOMEPAGE_URL ${ELEKTRA_HOMEPAGE_URL}) -endif (CMAKE_VERSION VERSION_LESS 3.9) +project ( + Elektra + VERSION ${KDB_VERSION} + DESCRIPTION ${ELEKTRA_DESCRIPTION} + HOMEPAGE_URL ${ELEKTRA_HOMEPAGE_URL}) # fix macOS RPATH issues if (APPLE) diff --git a/doc/AUTHORS.md b/doc/AUTHORS.md index 5fc74b3fafd..17d42a2601a 100644 --- a/doc/AUTHORS.md +++ b/doc/AUTHORS.md @@ -161,7 +161,7 @@ notification system, I/O bindings ## Maximilian Irlinger -documentation +documentation, Python bindings for elektraMerge - email: max@maxirlinger.at - github user: [atmaxinger](https://github.com/atmaxinger) diff --git a/doc/news/2019-08-06_0.9.0.md b/doc/news/2019-08-06_0.9.0.md index 1595f34501b..f245605c3da 100644 --- a/doc/news/2019-08-06_0.9.0.md +++ b/doc/news/2019-08-06_0.9.0.md @@ -752,7 +752,7 @@ mounted, use `kdb gen -F : elektra ` to lo - The Docker images for - - [Debian stretch](../../scripts/docker/debian/stretch/Dockerfile), and + - [Debian stretch](https://git.libelektra.org/blob/799fecd94dcb482ea9338facaf63d39f8e5ab5bd/scripts/docker/debian/stretch/Dockerfile), and - [Debian sid](../../scripts/docker/debian/sid/Dockerfile), now include the Python YAML library recommended by [cmake format](https://github.com/cheshirekow/cmake_format). _(René Schwaiger)_ diff --git a/doc/news/2021-02-01_0.9.4.md b/doc/news/2021-02-01_0.9.4.md index c3d005f8749..0c8ee35b78d 100644 --- a/doc/news/2021-02-01_0.9.4.md +++ b/doc/news/2021-02-01_0.9.4.md @@ -280,7 +280,7 @@ you up to date with the multi-language support provided by Elektra. ### Docker -- We added a Docker image for [building the documentation on Debian Sid](../../scripts/docker/debian/sid/doc.Dockerfile). _(René Schwaiger)_ +- We added a Docker image for [building the documentation on Debian Sid](https://github.com/ElektraInitiative/libelektra/blob/799fecd94dcb482ea9338facaf63d39f8e5ab5bd/scripts/docker/debian/sid/doc.Dockerfile). _(René Schwaiger)_ - We removed the Docker image for building the documentation on Debian Stretch. _(René Schwaiger)_ - Add Fedora 33 Dockerfile for Cirrus and Jenkins CI. _(Mihael Pranjić)_ - Debian Sid: update to clang 11. _(Mihael Pranjić)_ diff --git a/doc/news/_preparation_next_release.md b/doc/news/_preparation_next_release.md index a5b9dcb624d..62e633a93fe 100644 --- a/doc/news/_preparation_next_release.md +++ b/doc/news/_preparation_next_release.md @@ -61,9 +61,9 @@ docker run -it elektra/elektra The following section lists news about the [plugins](https://www.libelektra.org/plugins/readme) we updated in this release. -### <> +### csvstorage -- <> +- Remove superfluous if-conditions that lead to a build error on Debian Unstable _(Maximilian Irlinger @atmaxinger)_ - <> - <> @@ -127,7 +127,7 @@ The text below summarizes updates to the [C (and C++)-based libraries](https://w ### <> -- <> +- opts: fix possible 'free(): invalid pointer' error and add test for it _(@hannes99)_ - <> - <> @@ -148,6 +148,12 @@ The text below summarizes updates to the [C (and C++)-based libraries](https://w Bindings allow you to utilize Elektra using [various programming languages](https://www.libelektra.org/bindings/readme). This section keeps you up-to-date with the multi-language support provided by Elektra. +### Python + +- add merging based on elektraMerge _(Maximilian Irlinger @atmaxinger)_ +- <> +- <> + ### <> - <> @@ -160,8 +166,9 @@ you up-to-date with the multi-language support provided by Elektra. - <> - <> -### <> +### Rust +- start again to publish on crates.io _(Markus Raab)_ - <> - <> - <> @@ -241,7 +248,7 @@ you up-to-date with the multi-language support provided by Elektra. ### Tutorials -- <> +- opts: use arg/help instead of arg/name _(@hannes99)_ - <> - <> - <> @@ -317,7 +324,7 @@ you up-to-date with the multi-language support provided by Elektra. ### CMake - Fix build with newer libgit2 versions _(Fabian Vogt)_ -- <> +- We now require at least CMake `3.12` (released in July 2018). _(Maximilian Irlinger @atmaxinger)_ - <> - <> - <> @@ -327,7 +334,7 @@ you up-to-date with the multi-language support provided by Elektra. ### Docker - Bump Alpine Linux to 3.16.0. _(Mihael Pranjić @mpranj)_ -- <> +- The Docker image for building the documentation is now [based on Debian Bullseye](../../scripts/docker/debian/bullseye/doc.Dockerfile). _(Maximilian Irlinger @atmaxinger)_ - <> - <> - <> @@ -337,7 +344,7 @@ you up-to-date with the multi-language support provided by Elektra. ### Jenkins -- <> +- We no longer build and test on Ubuntu Xenial and Debian Stretch due to outdated CMake versions _(Maximilian Irlinger @atmaxinger)_ - <> - <> - <> @@ -346,7 +353,7 @@ you up-to-date with the multi-language support provided by Elektra. ### Cirrus -- <> +- Update FreeBSD images to 13.1 and 12.3 and update packages before builds. _(Mihael Pranjić @mpranj)_ - <> - <> - <> diff --git a/doc/tutorials/command-line-options.md b/doc/tutorials/command-line-options.md index 00b09c5dbe2..58af9e33d91 100644 --- a/doc/tutorials/command-line-options.md +++ b/doc/tutorials/command-line-options.md @@ -397,10 +397,10 @@ opt/#0 = i opt/#0/long = interactive opt/#0/arg = optional opt/#0/flagvalue = always +opt/#0/arg/help = WHEN opt/#1 = I opt/#1/flagvalue = once opt/#1/arg = none -opt/arg/name = WHEN description = prompt according to WHEN: never, once (-I), or always (-i); without WHEN, prompt always [singlefs] @@ -416,7 +416,7 @@ description = do not treat '/' specially [preserve] opt/long = preserve-root opt/arg = optional -opt/arg/name = all +opt/arg/help = all opt/flagvalue = root description = do not remove '/' (default); with 'all', reject any command line argument on a separate device from its parent diff --git a/doc/tutorials/python-kdb.md b/doc/tutorials/python-kdb.md index c05d46bb259..5c472a10083 100644 --- a/doc/tutorials/python-kdb.md +++ b/doc/tutorials/python-kdb.md @@ -9,6 +9,7 @@ - [Import kdb](#Import-kdb) - [Keyset](#Keyset) - [Keys](#Keys) +- [Merging KeySets](#Merging KeySets) ## Introduction @@ -284,3 +285,39 @@ with KDB() as data: keyset.append(newer_key) print(describe(keyset, "Replace Key", newline=False)) ``` + +## Merging KeySets + +The internal three-way merge algorithm is also included in the Python bindings. + +```py +import kdb, kdb.merge + +baseKeys = kdb.KeySet(100, + kdb.Key("system:/test/key1", "k1"), + kdb.Key("system:/test/key2", "k2"), + kdb.KS_END, + ) + +ourKeys = kdb.KeySet(100, + kdb.Key("system:/test/key1", "k1"), + kdb.Key("system:/test/key3", "k3"), + kdb.KS_END, + ) + +theirKeys = kdb.KeySet(100, + kdb.Key("system:/test/key1", "k1"), + kdb.Key("system:/test/key4", "k4"), + kdb.KS_END, + ) + +base = kdb.merge.MergeKeys(baseKeys, kdb.Key("system:/test")) +theirs = kdb.merge.MergeKeys(theirKeys, kdb.Key("system:/test")) +ours = kdb.merge.MergeKeys(ourKeys, kdb.Key("system:/test")) + +merger = kdb.merge.Merger() +mergeResult = merger.merge(base, ours, theirs, kdb.Key("system:/test"), kdb.merge.ConflictStrategy.THEIR) + +# prints ['system:/test/key1', 'system:/test/key3', 'system:/test/key4'] +print(mergeResult.mergedKeys) +``` diff --git a/examples/gopts.c b/examples/gopts.c index 39a9da62360..5b2abbfb6a2 100644 --- a/examples/gopts.c +++ b/examples/gopts.c @@ -43,12 +43,12 @@ static KeySet * createSpec (void) "prompt according to WHEN: never, once (-I), or always (-i), without WHEN, prompt always", KEY_META, "opt", "#1", KEY_META, "opt/#0", "i", KEY_META, "opt/#0/arg", "optional", KEY_META, "opt/#0/flagvalue", "always", KEY_META, "opt/#0/long", "interactive", KEY_META, "opt/#1", "I", KEY_META, "opt/#1/arg", "none", KEY_META, "opt/#1/flagvalue", - "once", KEY_META, "opt/arg/name", "WHEN", KEY_END), + "once", KEY_META, "opt/#0/arg/help", "WHEN", KEY_END), keyNew (SPEC_BASE_KEY "/nopreserve", KEY_META, "description", "do not treat '/' specially", KEY_META, "opt/arg", "none", KEY_META, "opt/long", "no-preserve-root", KEY_END), keyNew (SPEC_BASE_KEY "/preserve", KEY_META, "description", "do not remove '/' (default), with 'all', reject any command line argument on a separate device from its parent", - KEY_META, "opt/arg", "optional", KEY_META, "opt/arg/name", "all", KEY_META, "opt/flagvalue", "root", KEY_META, + KEY_META, "opt/arg", "optional", KEY_META, "opt/arg/help", "all", KEY_META, "opt/flagvalue", "root", KEY_META, "opt/long", "preserve-root", KEY_END), keyNew (SPEC_BASE_KEY "/recursive", KEY_META, "description", "remove directories and their contents recursively", KEY_META, "opt", "#1", KEY_META, "opt/#0", "r", KEY_META, "opt/#0/arg", "none", KEY_META, "opt/#0/long", "recursive", diff --git a/examples/kdbset.c b/examples/kdbset.c index 85b0e43f718..b621fd90886 100644 --- a/examples/kdbset.c +++ b/examples/kdbset.c @@ -67,7 +67,7 @@ while (ret == -1) // as long as we have an error ksCut(theirs, parentKey), parentKey, ksCut(base, parentKey), parentKey, parentKey, strategy, parentKey); - int numberOfConflicts = getConflicts (parentKey); + int numberOfConflicts = elektraMergeGetConflicts (parentKey); ksDel (theirs); if (result != NULL) { ret = kdbSet (handle, result, parentKey); diff --git a/examples/opts.c b/examples/opts.c index be5db6307f6..14f2c27df46 100644 --- a/examples/opts.c +++ b/examples/opts.c @@ -31,12 +31,12 @@ static KeySet * createSpec (void) "prompt according to WHEN: never, once (-I), or always (-i), without WHEN, prompt always", KEY_META, "opt", "#1", KEY_META, "opt/#0", "i", KEY_META, "opt/#0/arg", "optional", KEY_META, "opt/#0/flagvalue", "always", KEY_META, "opt/#0/long", "interactive", KEY_META, "opt/#1", "I", KEY_META, "opt/#1/arg", "none", KEY_META, "opt/#1/flagvalue", - "once", KEY_META, "opt/arg/name", "WHEN", KEY_END), + "once", KEY_META, "opt/#0/arg/help", "WHEN", KEY_END), keyNew (SPEC_BASE_KEY "/nopreserve", KEY_META, "description", "do not treat '/' specially", KEY_META, "opt/arg", "none", KEY_META, "opt/long", "no-preserve-root", KEY_END), keyNew (SPEC_BASE_KEY "/preserve", KEY_META, "description", "do not remove '/' (default), with 'all', reject any command line argument on a separate device from its parent", - KEY_META, "opt/arg", "optional", KEY_META, "opt/arg/name", "all", KEY_META, "opt/flagvalue", "root", KEY_META, + KEY_META, "opt/arg", "optional", KEY_META, "opt/arg/help", "all", KEY_META, "opt/flagvalue", "root", KEY_META, "opt/long", "preserve-root", KEY_END), keyNew (SPEC_BASE_KEY "/recursive", KEY_META, "description", "remove directories and their contents recursively", KEY_META, "opt", "#1", KEY_META, "opt/#0", "r", KEY_META, "opt/#0/arg", "none", KEY_META, "opt/#0/long", "recursive", diff --git a/scripts/docker/debian/sid/doc.Dockerfile b/scripts/docker/debian/bullseye/doc.Dockerfile similarity index 93% rename from scripts/docker/debian/sid/doc.Dockerfile rename to scripts/docker/debian/bullseye/doc.Dockerfile index 5135b374b27..25c55229e60 100644 --- a/scripts/docker/debian/sid/doc.Dockerfile +++ b/scripts/docker/debian/bullseye/doc.Dockerfile @@ -1,4 +1,4 @@ -FROM debian:sid +FROM debian:bullseye ENV LANG C.UTF-8 ENV LANGUAGE C.UTF-8 @@ -52,5 +52,5 @@ RUN useradd \ USER ${JENKINS_USERID} # Ronn-NG -ENV PATH="$PATH:/home/jenkins/.local/share/gem/ruby/3.0.0/bin" +ENV PATH="$PATH:/home/jenkins/.local/share/gem/ruby/2.7.0/bin" RUN gem install --user-install ronn-ng -v 0.10.1.pre1 && ronn --version diff --git a/scripts/docker/debian/stretch/Dockerfile b/scripts/docker/debian/stretch/Dockerfile deleted file mode 100644 index 2a4093a22b8..00000000000 --- a/scripts/docker/debian/stretch/Dockerfile +++ /dev/null @@ -1,183 +0,0 @@ -FROM debian:stretch - -ENV LANG C.UTF-8 -ENV LANGUAGE C.UTF-8 -ENV LC_ALL C.UTF-8 - -RUN apt-get update && apt-get -y install \ - automake \ - autotools-dev \ - bison \ - build-essential \ - checkinstall \ - cmake \ - curl \ - devscripts \ - dh-exec \ - dh-lua \ - diffutils \ - discount \ - dnsutils \ - doxygen \ - ed \ - flex \ - gawk \ - git \ - git-buildpackage \ - gobject-introspection \ - graphviz \ - icheck \ - lcov \ - libaugeas-dev \ - libdbus-1-dev \ - libev-dev \ - libgirepository1.0-dev \ - libgit2-dev \ - libglib2.0-dev \ - libgpgme-dev \ - liblua5.3-dev \ - libmarkdown2-dev \ - libpcre++-dev \ - libpcre3-dev \ - libpython3-dev \ - libssl-dev \ - libsystemd-dev \ - libuv1-dev \ - libxerces-c-dev \ - libyajl-dev \ - libzmq3-dev \ - lintian \ - llvm \ - mingw-w64 \ - ninja-build \ - openjdk-8-jdk \ - patch \ - patchutils \ - pkg-config \ - python3-all \ - python3-pip \ - python3-all \ - qtbase5-dev \ - qtdeclarative5-dev \ - reprepro \ - ruby \ - ruby-dev \ - swig3.0 \ - systemd \ - tclcl-dev \ - unzip \ - uuid-dev \ - valgrind \ - virtualenv \ - wine \ - && rm -rf /var/lib/apt/lists/* - -# Build dependency for libelektra-fuse -RUN pip3 install wheel - -# Google Test -ENV GTEST_ROOT=/opt/gtest -ARG GTEST_VER=release-1.12.1 -RUN mkdir -p ${GTEST_ROOT} \ - && cd /tmp \ - && curl -o gtest.tar.gz \ - -L https://github.com/google/googletest/archive/${GTEST_VER}.tar.gz \ - && tar -zxvf gtest.tar.gz --strip-components=1 -C ${GTEST_ROOT} \ - && rm gtest.tar.gz - -# Handle Java -RUN echo 'export JAVA_HOME=$(readlink -f /usr/bin/javac | sed "s:/bin/javac::")'>> /etc/bash.bashrc -RUN echo '\ -/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/amd64/\n\ -/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/amd64/server/\n' > /etc/ld.so.conf.d/jdk.conf - -# ANTLR -ARG ANTLR_VERSION=4.7.2 -RUN cd /usr/local/lib \ - && curl -o antlr.jar -L https://www.antlr.org/download/antlr-${ANTLR_VERSION}-complete.jar \ - && cd /usr/local/bin \ - && printf '\ -#!/usr/bin/env sh\n\ -CLASSPATH=.:/usr/local/lib/antlr.jar exec java -jar /usr/local/lib/antlr.jar "$@"' > antlr4 \ - && printf '\ -#!/usr/bin/env sh\n\ -java -classpath .:/usr/local/lib/antlr.jar org.antlr.v4.gui.TestRig "$@"' > grun \ - && chmod a+x antlr4 grun -# ANTLR C++ runtime -RUN cd /tmp \ - && git clone --branch ${ANTLR_VERSION} --depth 1 https://github.com/antlr/antlr4.git \ - && cd antlr4/runtime/Cpp \ - && mkdir build \ - && cd build \ - && cmake -GNinja -DANTLR_JAR_LOCATION=/usr/local/lib/antlr.jar -DCMAKE_BUILD_TYPE=Release .. \ - && ninja \ - && ninja install \ - && cd /tmp \ - && rm -r antlr4 - -# yaml-cpp -RUN cd /tmp \ - && git clone --branch yaml-cpp-0.6.2 --depth 1 https://github.com/jbeder/yaml-cpp.git \ - && cd yaml-cpp \ - && mkdir build \ - && cd build \ - && cmake -GNinja -DYAML_CPP_BUILD_TESTS=OFF -DBUILD_SHARED_LIBS=ON .. \ - && ninja \ - && ninja install \ - && cd ../.. \ - && rm -r yaml-cpp - -# Update cache for shared libraries -RUN ldconfig - -# Create User:Group -# The id is important as jenkins docker agents use the same id that is running -# on the slaves to execute containers -ARG JENKINS_GROUPID -RUN groupadd \ - -g ${JENKINS_GROUPID} \ - -f \ - jenkins - -ARG JENKINS_USERID -RUN useradd \ - --create-home \ - --uid ${JENKINS_USERID} \ - --gid ${JENKINS_GROUPID} \ - --shell "/bin/bash" \ - jenkins - -# download and install gradle -RUN cd /tmp && wget https://services.gradle.org/distributions/gradle-7.4-bin.zip && unzip gradle-7.4-bin.zip && rm gradle-7.4-bin.zip && mv gradle-7.4 /opt/gradle -ENV PATH "${PATH}:/opt/gradle/bin" - -USER ${JENKINS_USERID} - - - -# Set git config -RUN git config --global user.email 'Jenkins ' \ - && git config --global user.name 'Jenkins' - -# shfmt -ENV SHFMT_PATH=/home/jenkins/bin -ENV SHFMT_VERSION=v3.3.1 -ENV PATH="${SHFMT_PATH}:${PATH}" -RUN mkdir -p "${SHFMT_PATH}" \ - && cd "${SHFMT_PATH}" \ - && curl -L "https://github.com/mvdan/sh/releases/download/${SHFMT_VERSION}/shfmt_${SHFMT_VERSION}_linux_amd64" -o shfmt \ - && chmod a+x shfmt - -# cmake-format -RUN pip3 install cmake-format[yaml]==0.6.13 - -# Coveralls -ENV COVERALLS_VIRTUALENV_PATH=/home/jenkins/coveralls -RUN virtualenv "${COVERALLS_VIRTUALENV_PATH}" \ - && cd "${COVERALLS_VIRTUALENV_PATH}" \ - && . bin/activate \ - && pip install "urllib3==1.22" \ - && pip install pyyaml \ - && pip install cpp-coveralls \ - && deactivate -ENV PATH="${PATH}:${COVERALLS_VIRTUALENV_PATH}/bin" diff --git a/scripts/docker/debian/stretch/i386.Dockerfile b/scripts/docker/debian/stretch/i386.Dockerfile deleted file mode 100644 index f1d2c5b9913..00000000000 --- a/scripts/docker/debian/stretch/i386.Dockerfile +++ /dev/null @@ -1,57 +0,0 @@ -FROM debian:stretch - -ENV LANG C.UTF-8 -ENV LANGUAGE C.UTF-8 -ENV LC_ALL C.UTF-8 - -RUN dpkg --add-architecture i386 \ - && apt-get update \ - && apt-get -y install \ - curl \ - build-essential \ - autotools-dev \ - automake \ - cmake \ - pkg-config \ - gcc-multilib \ - g++-multilib \ - file \ - python3-pip \ - && rm -rf /var/lib/apt/lists/* - -# Build dependency for libelektra-fuse -RUN pip3 install wheel - -# Google Test -ENV GTEST_ROOT=/opt/gtest -ARG GTEST_VER=release-1.12.1 -RUN mkdir -p ${GTEST_ROOT} \ - && cd /tmp \ - && curl -o gtest.tar.gz \ - -L https://github.com/google/googletest/archive/${GTEST_VER}.tar.gz \ - && tar -zxvf gtest.tar.gz --strip-components=1 -C ${GTEST_ROOT} \ - && rm gtest.tar.gz - -# Handle Java -RUN echo 'export JAVA_HOME=$(readlink -f /usr/bin/javac | sed "s:/bin/javac::")'>> /etc/bash.bashrc -RUN echo '\ -/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/amd64/\n\ -/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/amd64/server/\n' > /etc/ld.so.conf.d/jdk.conf -RUN ldconfig - -# Create User:Group -# The id is important as jenkins docker agents use the same id that is running -# on the slaves to execute containers -ARG JENKINS_GROUPID -RUN groupadd \ - -g ${JENKINS_GROUPID} \ - jenkins - -ARG JENKINS_USERID -RUN useradd \ - --create-home \ - --uid ${JENKINS_USERID} \ - --gid ${JENKINS_GROUPID} \ - --shell "/bin/bash" \ - jenkins -USER ${JENKINS_USERID} diff --git a/scripts/docker/debian/stretch/minimal.Dockerfile b/scripts/docker/debian/stretch/minimal.Dockerfile deleted file mode 100644 index f54edf5a26e..00000000000 --- a/scripts/docker/debian/stretch/minimal.Dockerfile +++ /dev/null @@ -1,37 +0,0 @@ -FROM debian:stretch - -ENV LANG C.UTF-8 -ENV LANGUAGE C.UTF-8 -ENV LC_ALL C.UTF-8 - -RUN apt-get update && apt-get -y install \ - cmake git build-essential curl file - -# Google Test -ENV GTEST_ROOT=/opt/gtest -ARG GTEST_VER=release-1.12.1 -RUN mkdir -p ${GTEST_ROOT} \ - && cd /tmp \ - && curl -o gtest.tar.gz \ - -L https://github.com/google/googletest/archive/${GTEST_VER}.tar.gz \ - && tar -zxvf gtest.tar.gz --strip-components=1 -C ${GTEST_ROOT} \ - && rm gtest.tar.gz - -# Create User:Group -# The id is important as jenkins docker agents use the same id that is running -# on the slaves to execute containers -ARG JENKINS_GROUPID -RUN groupadd \ - -f \ - -g ${JENKINS_GROUPID} \ - jenkins - -ARG JENKINS_USERID -RUN useradd \ - --create-home \ - --uid ${JENKINS_USERID} \ - --gid ${JENKINS_GROUPID} \ - --shell "/bin/bash" \ - jenkins - -USER ${JENKINS_USERID} diff --git a/scripts/docker/ubuntu/xenial/Dockerfile b/scripts/docker/ubuntu/xenial/Dockerfile deleted file mode 100644 index ba803275f2d..00000000000 --- a/scripts/docker/ubuntu/xenial/Dockerfile +++ /dev/null @@ -1,61 +0,0 @@ -FROM ubuntu:xenial - -RUN apt-get update && apt-get -y install \ - locales \ - curl \ - build-essential \ - autotools-dev \ - automake \ - cmake \ - pkg-config \ - ruby-dev \ - python-dev \ - python3-dev \ - libpython3-dev \ - liblua5.3-dev \ - tclcl-dev \ - libaugeas-dev \ - libyajl-dev \ - git \ - libgit2-dev \ - libssl-dev \ - libdbus-1-dev \ - libpcre3-dev \ - libpcre++-dev \ - libxerces-c-dev \ - valgrind \ - checkinstall \ - swig \ - python3-pip \ - && rm -rf /var/lib/apt/lists/* - -# Build dependency for libelektra-fuse -RUN pip3 install wheel - -# Google Test -ENV GTEST_ROOT=/opt/gtest -ARG GTEST_VER=release-1.12.1 -RUN mkdir -p ${GTEST_ROOT} \ - && cd /tmp \ - && curl -o gtest.tar.gz \ - -L https://github.com/google/googletest/archive/${GTEST_VER}.tar.gz \ - && tar -zxvf gtest.tar.gz --strip-components=1 -C ${GTEST_ROOT} \ - && rm gtest.tar.gz - -# Create User:Group -# The id is important as jenkins docker agents use the same id that is running -# on the slaves to execute containers -ARG JENKINS_GROUPID -RUN groupadd \ - -g ${JENKINS_GROUPID} \ - jenkins - -ARG JENKINS_USERID -RUN useradd \ - --create-home \ - --uid ${JENKINS_USERID} \ - --gid ${JENKINS_GROUPID} \ - --shell "/bin/bash" \ - jenkins - -USER ${JENKINS_USERID} diff --git a/scripts/jenkins/Jenkinsfile b/scripts/jenkins/Jenkinsfile index 7b994d8c17a..a6822f7684e 100644 --- a/scripts/jenkins/Jenkinsfile +++ b/scripts/jenkins/Jenkinsfile @@ -229,15 +229,6 @@ def dockerInit() { "./scripts/docker/debian/sid/Dockerfile" ) - /* Build Elektra's documentation with this image. - * Also contains latex for pdf creation. - */ - DOCKER_IMAGES.sid_doc = dockerUtils.createDockerImageDesc( - "debian-sid-doc", dockerUtils.&idTesting, - "./scripts/docker/debian/sid", - "./scripts/docker/debian/sid/doc.Dockerfile" - ) - /* * Debian Bullseye. Used for testing and packaging. */ @@ -265,6 +256,15 @@ def dockerInit() { "./scripts/docker/debian/bullseye/i386.Dockerfile" ) + /* Build Elektra's documentation with this image. + * Also contains latex for pdf creation. + */ + DOCKER_IMAGES.bullseye_doc = dockerUtils.createDockerImageDesc( + "debian-bullseye-doc", dockerUtils.&idTesting, + "./scripts/docker/debian/bullseye", + "./scripts/docker/debian/bullseye/doc.Dockerfile" + ) + /* Our main target for compatibility is Debian stable * (currently buster). * Hence we try to build all parts of Elektra via this image. @@ -296,40 +296,6 @@ def dockerInit() { "./scripts/docker/debian/buster/i386.Dockerfile" ) - /* A Debian oldstable image used for testing backwards compatibility. - */ - DOCKER_IMAGES.stretch = dockerUtils.createDockerImageDesc( - "debian-stretch", dockerUtils.&idTesting, - "./scripts/docker/debian/stretch", - "./scripts/docker/debian/stretch/Dockerfile" - ) - - /* A minimal Debian stretch image used to test Elektra without any - * additional requirements introduced by optional plugins, bindings, - * ... - */ - DOCKER_IMAGES.stretch_minimal = dockerUtils.createDockerImageDesc( - "debian-stretch-minimal", dockerUtils.&idTesting, - "./scripts/docker/debian/stretch", - "./scripts/docker/debian/stretch/minimal.Dockerfile" - ) - - /* A Docker image for crossbuilding i386 - */ - DOCKER_IMAGES.stretch_i386 = dockerUtils.createDockerImageDesc( - "debian-stretch-i386", dockerUtils.&idTesting, - "./scripts/docker/debian/stretch", - "./scripts/docker/debian/stretch/i386.Dockerfile" - ) - - /* Ubuntu xenial image used to test compatibility with Ubuntu. - */ - DOCKER_IMAGES.xenial = dockerUtils.createDockerImageDesc( - "ubuntu-xenial", dockerUtils.&idTesting, - "./scripts/docker/ubuntu/xenial", - "./scripts/docker/ubuntu/xenial/Dockerfile" - ) - /* Alpine: used to compile against musl and uses ash as shell */ DOCKER_IMAGES.alpine = dockerUtils.createDockerImageDesc( @@ -601,19 +567,6 @@ def generateFullBuildStages() { [TEST.ALL, TEST.MEM, TEST.NOKDB, TEST.INSTALL] ) - tasks << buildAndTest( - "debian-stretch-full", - DOCKER_IMAGES.stretch, - CMAKE_FLAGS_BUILD_ALL + - CMAKE_FLAGS_DEBUG + - CMAKE_FLAGS_BUILD_FULL + - CMAKE_FLAGS_BUILD_STATIC + - CMAKE_FLAGS_COVERAGE - , - [TEST.ALL, TEST.MEM, TEST.NOKDB, TEST.INSTALL] - ) - - // Build Elektra with ASAN enabled // Detects memory leaks via ASAN tasks << buildAndTestAsan( @@ -693,15 +646,7 @@ def generateFullBuildStages() { [TEST.ALL] ) - // Build Elektra on ubuntu-xenial - tasks << buildAndTest( - "ubuntu-xenial", - DOCKER_IMAGES.xenial, - CMAKE_FLAGS_BUILD_ALL, - [TEST.ALL] - ) - - // Build Elektra on a minimal Debian stretch Docker image + // Build Elektra on a minimal Debian buster Docker image tasks << buildAndTest( "debian-buster-minimal", DOCKER_IMAGES.buster_minimal, @@ -820,7 +765,7 @@ def buildTodo() { ''' return [(stageName): { stage(stageName) { - withDockerEnv(DOCKER_IMAGES.sid_doc) { + withDockerEnv(DOCKER_IMAGES.bullseye_doc) { sh "sloccount --duplicates --wide --details ${WORKSPACE} > sloccount.sc" step([$class: 'SloccountPublisher', ignoreBuildFailure: true]) recordIssues(tools: [taskScanner(ignoreCase: true, includePattern: openTaskPatterns, lowTags: 'TODO,FIXME')]) @@ -910,7 +855,7 @@ def buildDoc() { ] return [(stageName): { stage(stageName) { - withDockerEnv(DOCKER_IMAGES.sid_doc) { + withDockerEnv(DOCKER_IMAGES.bullseye_doc) { dir('build') { deleteDir() utils.cmake(env.WORKSPACE, cmakeFlags) diff --git a/src/bindings/rust/Cargo.lock b/src/bindings/rust/Cargo.lock deleted file mode 100644 index a3395780077..00000000000 --- a/src/bindings/rust/Cargo.lock +++ /dev/null @@ -1,418 +0,0 @@ -# This file is automatically @generated by Cargo. -# It is not intended for manual editing. -[[package]] -name = "aho-corasick" -version = "0.7.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "ansi_term" -version = "0.11.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "atty" -version = "0.2.13" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "libc 0.2.62 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "backtrace" -version = "0.3.35" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "backtrace-sys 0.1.31 (registry+https://github.com/rust-lang/crates.io-index)", - "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.62 (registry+https://github.com/rust-lang/crates.io-index)", - "rustc-demangle 0.1.16 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "backtrace-sys" -version = "0.1.31" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "cc 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.62 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "bindgen" -version = "0.50.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "cexpr 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)", - "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", - "clang-sys 0.28.1 (registry+https://github.com/rust-lang/crates.io-index)", - "clap 2.33.0 (registry+https://github.com/rust-lang/crates.io-index)", - "env_logger 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)", - "fxhash 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", - "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", - "peeking_take_while 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", - "regex 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "shlex 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", - "which 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "bitflags" -version = "1.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "byteorder" -version = "1.3.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "cc" -version = "1.0.40" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "cexpr" -version = "0.3.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "nom 4.2.3 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "cfg-if" -version = "0.1.9" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "clang-sys" -version = "0.28.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "glob 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.62 (registry+https://github.com/rust-lang/crates.io-index)", - "libloading 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "clap" -version = "2.33.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "ansi_term 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", - "atty 0.2.13 (registry+https://github.com/rust-lang/crates.io-index)", - "bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "strsim 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", - "textwrap 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", - "unicode-width 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", - "vec_map 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "elektra" -version = "0.9.0" -dependencies = [ - "bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "elektra-sys 0.9.0", -] - -[[package]] -name = "elektra-sys" -version = "0.9.0" -dependencies = [ - "bindgen 0.50.0 (registry+https://github.com/rust-lang/crates.io-index)", - "pkg-config 0.3.16 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "env_logger" -version = "0.6.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "atty 0.2.13 (registry+https://github.com/rust-lang/crates.io-index)", - "humantime 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", - "regex 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "termcolor 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "failure" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "backtrace 0.3.35 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "fxhash" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "glob" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "humantime" -version = "1.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "lazy_static" -version = "1.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "libc" -version = "0.2.62" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "libloading" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "cc 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "log" -version = "0.4.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "memchr" -version = "2.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "nom" -version = "4.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "peeking_take_while" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "pkg-config" -version = "0.3.16" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "proc-macro2" -version = "0.4.30" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "quick-error" -version = "1.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "quote" -version = "0.6.13" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "regex" -version = "1.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "aho-corasick 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)", - "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "regex-syntax 0.6.11 (registry+https://github.com/rust-lang/crates.io-index)", - "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "regex-syntax" -version = "0.6.11" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "rustc-demangle" -version = "0.1.16" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "shlex" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "strsim" -version = "0.8.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "termcolor" -version = "1.0.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "wincolor 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "textwrap" -version = "0.11.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "unicode-width 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "thread_local" -version = "0.3.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "unicode-width" -version = "0.1.6" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "unicode-xid" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "vec_map" -version = "0.8.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "version_check" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "which" -version = "2.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.62 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "winapi" -version = "0.3.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "winapi-i686-pc-windows-gnu" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "winapi-util" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "winapi-x86_64-pc-windows-gnu" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "wincolor" -version = "1.0.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[metadata] -"checksum aho-corasick 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)" = "58fb5e95d83b38284460a5fda7d6470aa0b8844d283a0b614b8535e880800d2d" -"checksum ansi_term 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ee49baf6cb617b853aa8d93bf420db2383fab46d314482ca2803b40d5fde979b" -"checksum atty 0.2.13 (registry+https://github.com/rust-lang/crates.io-index)" = "1803c647a3ec87095e7ae7acfca019e98de5ec9a7d01343f611cf3152ed71a90" -"checksum backtrace 0.3.35 (registry+https://github.com/rust-lang/crates.io-index)" = "1371048253fa3bac6704bfd6bbfc922ee9bdcee8881330d40f308b81cc5adc55" -"checksum backtrace-sys 0.1.31 (registry+https://github.com/rust-lang/crates.io-index)" = "82a830b4ef2d1124a711c71d263c5abdc710ef8e907bd508c88be475cebc422b" -"checksum bindgen 0.50.0 (registry+https://github.com/rust-lang/crates.io-index)" = "65a913de3fa2fa95f2c593bb7e33b1be1ce1ce8a83f34b6bb02e6f01400b96cc" -"checksum bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3d155346769a6855b86399e9bc3814ab343cd3d62c7e985113d46a0ec3c281fd" -"checksum byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a7c3dd8985a7111efc5c80b44e23ecdd8c007de8ade3b96595387e812b957cf5" -"checksum cc 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)" = "b548a4ee81fccb95919d4e22cfea83c7693ebfd78f0495493178db20b3139da7" -"checksum cexpr 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)" = "a7fa24eb00d5ffab90eaeaf1092ac85c04c64aaf358ea6f84505b8116d24c6af" -"checksum cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "b486ce3ccf7ffd79fdeb678eac06a9e6c09fc88d33836340becb8fffe87c5e33" -"checksum clang-sys 0.28.1 (registry+https://github.com/rust-lang/crates.io-index)" = "81de550971c976f176130da4b2978d3b524eaa0fd9ac31f3ceb5ae1231fb4853" -"checksum clap 2.33.0 (registry+https://github.com/rust-lang/crates.io-index)" = "5067f5bb2d80ef5d68b4c87db81601f0b75bca627bc2ef76b141d7b846a3c6d9" -"checksum env_logger 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "aafcde04e90a5226a6443b7aabdb016ba2f8307c847d524724bd9b346dd1a2d3" -"checksum failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "795bd83d3abeb9220f257e597aa0080a508b27533824adf336529648f6abf7e2" -"checksum fxhash 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "c31b6d751ae2c7f11320402d34e41349dd1016f8d5d45e48c4312bc8625af50c" -"checksum glob 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9b919933a397b79c37e33b77bb2aa3dc8eb6e165ad809e58ff75bc7db2e34574" -"checksum humantime 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3ca7e5f2e110db35f93b837c81797f3714500b81d517bf20c431b16d3ca4f114" -"checksum lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bc5729f27f159ddd61f4df6228e827e86643d4d3e7c32183cb30a1c08f604a14" -"checksum libc 0.2.62 (registry+https://github.com/rust-lang/crates.io-index)" = "34fcd2c08d2f832f376f4173a231990fa5aef4e99fb569867318a227ef4c06ba" -"checksum libloading 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "f2b111a074963af1d37a139918ac6d49ad1d0d5e47f72fd55388619691a7d753" -"checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7" -"checksum memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "88579771288728879b57485cc7d6b07d648c9f0141eb955f8ab7f9d45394468e" -"checksum nom 4.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2ad2a91a8e869eeb30b9cb3119ae87773a8f4ae617f41b1eb9c154b2905f7bd6" -"checksum peeking_take_while 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "19b17cddbe7ec3f8bc800887bab5e717348c95ea2ca0b1bf0837fb964dc67099" -"checksum pkg-config 0.3.16 (registry+https://github.com/rust-lang/crates.io-index)" = "72d5370d90f49f70bd033c3d75e87fc529fbfff9d6f7cccef07d6170079d91ea" -"checksum proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)" = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759" -"checksum quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9274b940887ce9addde99c4eee6b5c44cc494b182b97e73dc8ffdcb3397fd3f0" -"checksum quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)" = "6ce23b6b870e8f94f81fb0a363d65d86675884b34a09043c81e5562f11c1f8e1" -"checksum regex 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "88c3d9193984285d544df4a30c23a4e62ead42edf70a4452ceb76dac1ce05c26" -"checksum regex-syntax 0.6.11 (registry+https://github.com/rust-lang/crates.io-index)" = "b143cceb2ca5e56d5671988ef8b15615733e7ee16cd348e064333b251b89343f" -"checksum rustc-demangle 0.1.16 (registry+https://github.com/rust-lang/crates.io-index)" = "4c691c0e608126e00913e33f0ccf3727d5fc84573623b8d65b2df340b5201783" -"checksum shlex 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7fdf1b9db47230893d76faad238fd6097fd6d6a9245cd7a4d90dbd639536bbd2" -"checksum strsim 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "8ea5119cdb4c55b55d432abb513a0429384878c15dde60cc77b1c99de1a95a6a" -"checksum termcolor 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)" = "96d6098003bde162e4277c70665bd87c326f5a0c3f3fbfb285787fa482d54e6e" -"checksum textwrap 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d326610f408c7a4eb6f51c37c330e496b08506c9457c9d34287ecc38809fb060" -"checksum thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)" = "c6b53e329000edc2b34dbe8545fd20e55a333362d0a321909685a19bd28c3f1b" -"checksum unicode-width 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "7007dbd421b92cc6e28410fe7362e2e0a2503394908f417b68ec8d1c364c4e20" -"checksum unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" -"checksum vec_map 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)" = "05c78687fb1a80548ae3250346c3db86a80a7cdd77bda190189f2d0a0987c81a" -"checksum version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd" -"checksum which 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b57acb10231b9493c8472b20cb57317d0679a49e0bdbee44b3b803a6473af164" -"checksum winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)" = "f10e386af2b13e47c89e7236a7a14a086791a2b88ebad6df9bf42040195cf770" -"checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" -"checksum winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7168bab6e1daee33b4557efd0e95d5ca70a03706d39fa5f3fe7a236f584b03c9" -"checksum winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" -"checksum wincolor 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "96f5016b18804d24db43cebf3c77269e7569b8954a8464501c216cc5e070eaa9" diff --git a/src/bindings/rust/README.md b/src/bindings/rust/README.md index fd917cb6667..666cc097ebe 100644 --- a/src/bindings/rust/README.md +++ b/src/bindings/rust/README.md @@ -34,12 +34,12 @@ The `elektra-sys`, as well as the `elektra` crate have a feature called `pkg-con ```toml [dependencies] -elektra = { version = "0.9.0", features = ["pkg-config"] } +elektra = { version = "0.9.10", features = ["pkg-config"] } # Directly depending on elektra-sys is only needed if you need to use the raw bindings -elektra-sys = { version = "0.9.0", features = ["pkg-config"] } +elektra-sys = { version = "0.9.10", features = ["pkg-config"] } ``` -If you don't use the `pkg-config` feature, the build script will look for the elektra installation in `/usr/local/include/elektra` and `/usr/include/elektra`. +If you don't use the `pkg-config` feature, the build script will look for the Elektra installation in `/usr/local/include/elektra` and `/usr/include/elektra`. With this in place, the bindings should be built when you run `cargo build`. @@ -64,9 +64,9 @@ To start with a new project, use `cargo new elektra_rust`. Now add the `elektra` ```toml [dependencies] -elektra = { version = "0.9.0", path = "~/git/libelektra/build/src/bindings/rust/elektra" } +elektra = { version = "0.9.10", path = "~/git/libelektra/build/src/bindings/rust/elektra" } # Directly depending on elektra-sys is only needed if you need to use the raw bindings -elektra-sys = { version = "0.9.0", path = "~/git/libelektra/build/src/bindings/rust/elektra-sys" } +elektra-sys = { version = "0.9.10", path = "~/git/libelektra/build/src/bindings/rust/elektra-sys" } ``` If you run `cargo run` and everything builds correctly and prints `Hello, world!`, you can replace the contents of `main.rs` with the examples shown in the next section. @@ -177,8 +177,10 @@ extern crate elektra; use elektra::{KeySet, StringKey, WriteableKey, KDB}; fn main() -> Result<(), Box> { + let contract = KeySet::with_capacity(0); + // Open a KDB session - let mut kdb = KDB::open()?; + let mut kdb = KDB::open(contract)?; // Create a keyset that will hold the keys we get from the get call let mut ks = KeySet::with_capacity(10); diff --git a/src/bindings/rust/elektra-sys/published_Cargo.toml b/src/bindings/rust/elektra-sys/published_Cargo.toml index 98a430eecff..50186adc6af 100644 --- a/src/bindings/rust/elektra-sys/published_Cargo.toml +++ b/src/bindings/rust/elektra-sys/published_Cargo.toml @@ -1,6 +1,6 @@ [package] name = "elektra-sys" -version = "0.9.1" +version = "0.9.10" authors = ["PhilippGackstatter "] edition = "2018" build = "build.rs" @@ -17,4 +17,4 @@ default = [] [build-dependencies] bindgen = "0.50.0" -pkg-config = { version = "0.3.16", optional = true } \ No newline at end of file +pkg-config = { version = "0.3.16", optional = true } diff --git a/src/bindings/rust/elektra/published_Cargo.toml b/src/bindings/rust/elektra/published_Cargo.toml index 5e2fe35b47e..a934829bf2e 100644 --- a/src/bindings/rust/elektra/published_Cargo.toml +++ b/src/bindings/rust/elektra/published_Cargo.toml @@ -1,6 +1,6 @@ [package] name = "elektra" -version = "0.9.1" +version = "0.9.10" authors = ["PhilippGackstatter "] edition = "2018" description = "Elektra serves as a universal and secure framework to access configuration parameters in a global, hierarchical key database." @@ -17,4 +17,4 @@ pkg-config = ["elektra-sys/pkg-config"] [dependencies] elektra-sys = { version = "0.9.1" } -bitflags = "1.1.0" \ No newline at end of file +bitflags = "1.1.0" diff --git a/src/bindings/swig/python/CMakeLists.txt b/src/bindings/swig/python/CMakeLists.txt index 83f9c2b9927..e75ccbdd4f3 100644 --- a/src/bindings/swig/python/CMakeLists.txt +++ b/src/bindings/swig/python/CMakeLists.txt @@ -16,8 +16,8 @@ include (${SWIG_USE_FILE}) include (LibAddMacros) # set (PythonInterp_FIND_VERSION_EXACT ON) -find_package (PythonInterp 3 QUIET) -find_package (PythonLibs 3 QUIET) +find_package (PythonInterp 3.4 QUIET) +find_package (PythonLibs 3.4 QUIET) if (NOT PYTHONINTERP_FOUND) exclude_binding (python "python3 interpreter not found") @@ -61,34 +61,34 @@ else () set (SWIG_COMPILE_FLAGS "${SWIG_COMPILE_FLAGS} -Wno-stringop-truncation") endif () - # kdb module - add_cppheaders (HDR_FILES) - set_source_files_properties (kdb.i PROPERTIES CPLUSPLUS ON) - set_source_files_properties (kdb.i PROPERTIES SWIG_FLAGS "-py3;-extranative") - if (CMAKE_VERSION VERSION_LESS 3.8) - swig_add_module (swig-python python kdb.i) - else (CMAKE_VERSION VERSION_LESS 3.8) + macro (add_python_binding NAME SWIGFILE LINKLIBRARY) + set_source_files_properties (${SWIGFILE} PROPERTIES CPLUSPLUS ON) + set_source_files_properties (${SWIGFILE} PROPERTIES SWIG_FLAGS "-py3;-extranative") swig_add_library ( - swig-python + swig-python-${NAME} LANGUAGE python - SOURCES kdb.i + SOURCES ${SWIGFILE} TYPE MODULE) - endif (CMAKE_VERSION VERSION_LESS 3.8) - swig_link_libraries (swig-python elektra-core elektra-kdb ${PYTHON_LIBRARIES}) - set_target_properties (_swig-python PROPERTIES OUTPUT_NAME _kdb) - set_target_properties (_swig-python PROPERTIES SKIP_BUILD_RPATH TRUE) - set_target_properties (_swig-python PROPERTIES INSTALL_RPATH_USE_LINK_PATH TRUE) - set_source_files_properties (${swig_generated_file_fullname} PROPERTIES COMPILE_FLAGS "${SWIG_COMPILE_FLAGS}") + swig_link_libraries (swig-python-${NAME} ${LINKLIBRARY} ${PYTHON_LIBRARIES}) + set_target_properties (_swig-python-${NAME} PROPERTIES OUTPUT_NAME _${NAME}) + set_target_properties (_swig-python-${NAME} PROPERTIES SKIP_BUILD_RPATH TRUE) + set_target_properties (_swig-python-${NAME} PROPERTIES INSTALL_RPATH_USE_LINK_PATH TRUE) + set_source_files_properties (${swig_generated_file_fullname} PROPERTIES COMPILE_FLAGS "${SWIG_COMPILE_FLAGS}") + + if (BUILD_TESTING) + # add tests + add_subdirectory (tests_${NAME}) + endif () + endmacro () + + # kdb module + add_cppheaders (HDR_FILES) + add_python_binding (kdb kdb.i elektra-kdb) add_custom_command ( - TARGET _swig-python + TARGET _swig-python-kdb POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy "${CMAKE_CURRENT_SOURCE_DIR}/__init__.py" ${CMAKE_SWIG_OUTDIR}/) - if (BUILD_TESTING) - # add tests - add_subdirectory (tests) - endif () - # tools module # # we require SWIG 4 because of https://github.com/swig/swig/commit/9cb90982ee98b437fd3fe9f1257b48b5eef9b335 @@ -96,29 +96,12 @@ else () message (WARNING "Python bindings for elektra tools require SWIG 4 or later. Not building.") else (${SWIG_VERSION} VERSION_LESS "4.0.0") add_toolheaders (HDR_FILES) - set_source_files_properties (tools.i PROPERTIES CPLUSPLUS ON) - set_source_files_properties (tools.i PROPERTIES SWIG_FLAGS "-py3;-extranative") - if (CMAKE_VERSION VERSION_LESS 3.8) - swig_add_module (swig-python-tools python tools.i) - else (CMAKE_VERSION VERSION_LESS 3.8) - swig_add_library ( - swig-python-tools - LANGUAGE python - SOURCES tools.i - TYPE MODULE) - endif (CMAKE_VERSION VERSION_LESS 3.8) - swig_link_libraries (swig-python-tools elektratools ${PYTHON_LIBRARIES}) - set_target_properties (_swig-python-tools PROPERTIES OUTPUT_NAME _tools) - set_target_properties (_swig-python-tools PROPERTIES SKIP_BUILD_RPATH TRUE) - set_target_properties (_swig-python-tools PROPERTIES INSTALL_RPATH_USE_LINK_PATH TRUE) - set_source_files_properties (${swig_generated_file_fullname} PROPERTIES COMPILE_FLAGS "${SWIG_COMPILE_FLAGS}") - - if (BUILD_TESTING) - # add tests - add_subdirectory (tests_tools) - endif () + add_python_binding (tools tools.i elektratools) endif (${SWIG_VERSION} VERSION_LESS "4.0.0") + # merge module + add_python_binding (merge merge.i elektra-merge) + # install package set (PYTHON_GET_MODULES_DIR_COMMAND "from distutils.sysconfig import get_python_lib; print(get_python_lib(True, prefix='${CMAKE_INSTALL_PREFIX}'))") diff --git a/src/bindings/swig/python/merge.i b/src/bindings/swig/python/merge.i new file mode 100644 index 00000000000..bc2a50e776f --- /dev/null +++ b/src/bindings/swig/python/merge.i @@ -0,0 +1,51 @@ +%module merge + +%include "../common.i" + +%include +%include "../common.i" +%feature("autodoc", "3"); + +%import "kdb.i" + +%{ +#include "kdbmerge.h" +%} + + +ckdb::KeySet * elektraMerge (ckdb::KeySet * our, ckdb::Key * ourRoot, ckdb::KeySet * their, ckdb::Key * theirRoot, ckdb::KeySet * base, ckdb::Key * baseRoot, ckdb::Key * resultKey, + int strategy, ckdb::Key * informationKey); +int elektraMergeGetConflicts (ckdb::Key * informationKey); + +%pythoncode { +from enum import Enum + +class ConflictStrategy(Enum): + ABORT = 1 + INTERACTIVE = 2 + OUR = 3 + THEIR = 4 + +class MergeKeys: + def __init__(self, keys, parentKey): + self.keys = keys + self.root = parentKey + +class MergeResult: + def __init__(self, mergedKeys, informationKey): + if mergedKeys is None: + self.mergedKeys = None + else: + self.mergedKeys = kdb.KeySet(mergedKeys) + + self.mergeInformation = informationKey + + def hasConflicts(self): + return self.mergedKeys is None or elektraMergeGetConflicts(self.mergeInformation.getKey()) > 0 + +class Merger: + def merge(self, base, ours, theirs, root, conflictStrategy): + informationKey = kdb.Key() + res = elektraMerge(ours.keys.getKeySet(), ours.root.getKey(), theirs.keys.getKeySet(), theirs.root.getKey(), base.keys.getKeySet(), base.root.getKey(), root.getKey(), conflictStrategy.value, informationKey.getKey()) + return MergeResult(res, informationKey) +}; diff --git a/src/bindings/swig/python/tests/CMakeLists.txt b/src/bindings/swig/python/tests_kdb/CMakeLists.txt similarity index 100% rename from src/bindings/swig/python/tests/CMakeLists.txt rename to src/bindings/swig/python/tests_kdb/CMakeLists.txt diff --git a/src/bindings/swig/python/tests/test_gopts.py b/src/bindings/swig/python/tests_kdb/test_gopts.py similarity index 100% rename from src/bindings/swig/python/tests/test_gopts.py rename to src/bindings/swig/python/tests_kdb/test_gopts.py diff --git a/src/bindings/swig/python/tests/test_kdb.py b/src/bindings/swig/python/tests_kdb/test_kdb.py similarity index 100% rename from src/bindings/swig/python/tests/test_kdb.py rename to src/bindings/swig/python/tests_kdb/test_kdb.py diff --git a/src/bindings/swig/python/tests/test_key.py b/src/bindings/swig/python/tests_kdb/test_key.py similarity index 100% rename from src/bindings/swig/python/tests/test_key.py rename to src/bindings/swig/python/tests_kdb/test_key.py diff --git a/src/bindings/swig/python/tests/test_keyset.py b/src/bindings/swig/python/tests_kdb/test_keyset.py similarity index 100% rename from src/bindings/swig/python/tests/test_keyset.py rename to src/bindings/swig/python/tests_kdb/test_keyset.py diff --git a/src/bindings/swig/python/tests_merge/CMakeLists.txt b/src/bindings/swig/python/tests_merge/CMakeLists.txt new file mode 100644 index 00000000000..5160447f35d --- /dev/null +++ b/src/bindings/swig/python/tests_merge/CMakeLists.txt @@ -0,0 +1,34 @@ +set (PYTHON_MODULEPATH "${CMAKE_SWIG_OUTDIR}/..") + +function (do_python_test source) + cmake_parse_arguments (ARG "KDB_TEST" "" "REQUIRED_PLUGINS" ${ARGN}) + + foreach (plugin ${ARG_REQUIRED_PLUGINS}) + list (FIND REMOVED_PLUGINS ${plugin} plugin_index) + if (plugin_index GREATER -1) + return () + endif (plugin_index GREATER -1) + endforeach (plugin ${ARG_REQUIRED_PLUGINS}) + + get_filename_component (name ${source} NAME) + add_test (NAME ${name} COMMAND ${PYTHON_EXECUTABLE} -B "${CMAKE_CURRENT_SOURCE_DIR}/${source}") + + set_property (TEST ${name} PROPERTY ENVIRONMENT "PYTHONPATH=${PYTHON_MODULEPATH}" "LD_LIBRARY_PATH=${CMAKE_BINARY_DIR}/lib") + + set_property (TEST ${name} PROPERTY LABELS memleak bindings) + + if (ARG_KDB_TEST) + set_property ( + TEST ${name} + APPEND + PROPERTY LABELS kdbtests) + set_property ( + TEST ${name} + APPEND + PROPERTY RUN_SERIAL TRUE) + endif () +endfunction (do_python_test) + +if (NOT (APPLE AND ENABLE_ASAN)) + do_python_test (test_merge_simple.py) +endif (NOT (APPLE AND ENABLE_ASAN)) diff --git a/src/bindings/swig/python/tests_merge/test_merge_simple.py b/src/bindings/swig/python/tests_merge/test_merge_simple.py new file mode 100644 index 00000000000..081ec41e3fe --- /dev/null +++ b/src/bindings/swig/python/tests_merge/test_merge_simple.py @@ -0,0 +1,29 @@ +import kdb, kdb.merge, unittest + +class MergeSimple(unittest.TestCase): + def setUp(self): + self.ksBase = kdb.KeySet(100, + kdb.Key("system:/test/key1", "k1"), + kdb.Key("system:/test/key2", "k2"), + kdb.KS_END, + ) + + def test_load(self): + ourKeys = kdb.KeySet(100, + kdb.Key("system:/test/key1", "k1"), + kdb.Key("system:/test/key3", "k3"), + kdb.KS_END, + ) + + + base = kdb.merge.MergeKeys(self.ksBase, kdb.Key("system:/test")) + theirs = base + ours = kdb.merge.MergeKeys(ourKeys, kdb.Key("system:/test")) + + merger = kdb.merge.Merger() + result = merger.merge(base, ours, theirs, kdb.Key("system:/test"), kdb.merge.ConflictStrategy.ABORT) + + self.assertFalse(result.hasConflicts()) + +if __name__ == '__main__': + unittest.main() diff --git a/src/include/kdbmerge.h b/src/include/kdbmerge.h index 8e6b32700f9..1be0ca71a72 100644 --- a/src/include/kdbmerge.h +++ b/src/include/kdbmerge.h @@ -27,7 +27,7 @@ enum KeySet * elektraMerge (KeySet * our, Key * ourRoot, KeySet * their, Key * theirRoot, KeySet * base, Key * baseRoot, Key * resultKey, int strategy, Key * informationKey); -int getConflicts (Key * informationKey); +int elektraMergeGetConflicts (Key * informationKey); #ifdef __cplusplus } diff --git a/src/libs/merge/kdbmerge.c b/src/libs/merge/kdbmerge.c index c9681c42782..94d9b3ebbae 100644 --- a/src/libs/merge/kdbmerge.c +++ b/src/libs/merge/kdbmerge.c @@ -181,13 +181,21 @@ static int getTotalNonOverlaps (Key * informationKey) getNonOverlapOnlyBaseConflicts (informationKey); } + +int ELEKTRA_SYMVER (getConflicts, v1) (Key * informationKey) +{ + return elektraMergeGetConflicts (informationKey); +} + +ELEKTRA_SYMVER_DECLARE ("libelektra_0.8", getConflicts, v1) + /** * This function returns the number of conflicts that is store in the key * * @param informationKey contains the statistics in its meta information * @returns the number of conflicts stored in the key */ -int getConflicts (Key * informationKey) +int elektraMergeGetConflicts (Key * informationKey) { return getTotalNonOverlaps (informationKey) + getTotalOverlaps (informationKey); } @@ -1016,13 +1024,13 @@ KeySet * elektraMerge (KeySet * our, Key * ourRoot, KeySet * their, Key * theirR ELEKTRA_SET_INTERNAL_ERROR (informationKey, "Could not delete a key set."); return NULL; } - if (getConflicts (informationKey) > 0) + if (elektraMergeGetConflicts (informationKey) > 0) { if (strategy == MERGE_STRATEGY_ABORT) { ksDel (result); ELEKTRA_SET_INTERNAL_ERRORF (informationKey, "Abort strategy was set and %d conflicts occured.", - getConflicts (informationKey)); + elektraMergeGetConflicts (informationKey)); return NULL; } } diff --git a/src/libs/merge/symbols.map b/src/libs/merge/symbols.map index 7152aa06f07..0714e34bd15 100644 --- a/src/libs/merge/symbols.map +++ b/src/libs/merge/symbols.map @@ -4,3 +4,8 @@ libelektra_0.8 { getConflicts; }; +libelektra_0.9 { + # kdbmerge.h + elektraMergeGetConflicts; +}; + diff --git a/src/libs/opts/opts.c b/src/libs/opts/opts.c index ae162d6e82e..0fcdd4d4b15 100644 --- a/src/libs/opts/opts.c +++ b/src/libs/opts/opts.c @@ -889,13 +889,13 @@ bool processShortOptSpec (struct Specification * spec, struct OptionData * optio if (!hidden) { - char * argString = ""; + char * argString = NULL; if (elektraStrCmp (hasArg, "required") == 0) { argString = argName == NULL ? " ARG" : elektraFormat (" %s", argName); } - char * newShortOptLine = elektraFormat ("%s-%c%s, ", *shortOptLine, shortOpt, argString); + char * newShortOptLine = elektraFormat ("%s-%c%s, ", *shortOptLine, shortOpt, argString == NULL ? "" : argString); elektraFree (*shortOptLine); if (argName != NULL) { @@ -970,7 +970,7 @@ bool processLongOptSpec (struct Specification * spec, struct OptionData * option if (!hidden) { - char * argString = ""; + char * argString = NULL; if (elektraStrCmp (hasArg, "required") == 0) { argString = argName == NULL ? "=ARG" : elektraFormat ("=%s", argName); @@ -981,7 +981,7 @@ bool processLongOptSpec (struct Specification * spec, struct OptionData * option } - char * newLongOptLine = elektraFormat ("%s--%s%s, ", *longOptLine, longOpt, argString); + char * newLongOptLine = elektraFormat ("%s--%s%s, ", *longOptLine, longOpt, argString == NULL ? "" : argString); elektraFree (*longOptLine); if (argName != NULL) { diff --git a/src/plugins/csvstorage/csvstorage.c b/src/plugins/csvstorage/csvstorage.c index af5d9d6588f..2babf433cd4 100644 --- a/src/plugins/csvstorage/csvstorage.c +++ b/src/plugins/csvstorage/csvstorage.c @@ -280,7 +280,7 @@ static KeySet * createHeaders (Key * parentKey, int columns, const char ** colNa return NULL; } Key * key = keyDup (orderKey, KEY_CP_ALL); - if (colNames && (colNames + colCounter)) + if (colNames) keySetString (key, colNames[colCounter]); else keySetString (key, keyBaseName (key)); @@ -312,7 +312,7 @@ static KeySet * readHeaders (Key * parentKey, char * lineBuffer, char delim, int return NULL; } Key * key = keyDup (orderKey, KEY_CP_ALL); - if (colNames && (colNames + colCounter)) + if (colNames) { keySetString (key, colNames[colCounter]); } diff --git a/src/tools/kdb/cmerge.cpp b/src/tools/kdb/cmerge.cpp index 239b49e4236..8dfe1687601 100644 --- a/src/tools/kdb/cmerge.cpp +++ b/src/tools/kdb/cmerge.cpp @@ -111,7 +111,7 @@ int CMergeCommand::execute (Cmdline const & cl ELEKTRA_UNUSED) ckdb::Key * informationKey = keyNew ("/", KEY_END); ckdb::KeySet * c_merge_result = elektraMerge (c_ours, oursRoot.getKey (), c_theirs, theirsRoot.getKey (), c_base, baseRoot.getKey (), resultRoot.getKey (), strategy, informationKey); - int numberOfConflicts = getConflicts (informationKey); + int numberOfConflicts = elektraMergeGetConflicts (informationKey); ckdb::keyDel (informationKey); if (c_merge_result != NULL) { diff --git a/tests/ctest/CMakeLists.txt b/tests/ctest/CMakeLists.txt index 0f18afcf421..8a9277d06f9 100644 --- a/tests/ctest/CMakeLists.txt +++ b/tests/ctest/CMakeLists.txt @@ -37,5 +37,7 @@ target_link_elektra (test_cmerge elektra-merge) target_link_elektra (test_sha-256 elektra-ease) +target_link_elektra (test_merge elektra-merge) + # LibGit leaks memory set_property (TEST test_cmerge PROPERTY LABELS memleak) diff --git a/tests/ctest/test_merge.c b/tests/ctest/test_merge.c new file mode 100644 index 00000000000..24692de93f8 --- /dev/null +++ b/tests/ctest/test_merge.c @@ -0,0 +1,328 @@ +/** + * @file + * + * @brief + * + * @copyright BSD License (see LICENSE.md or https://www.libelektra.org) + */ + +#include +#include + +static void test_new_keys_in_both (void) +{ + printf ("test new keys in both merge scenario\n"); + + KeySet * ksBase = ksNew (0, KS_END); + KeySet * ksOurs = ksNew (0, KS_END); + KeySet * ksTheirs = ksNew (0, KS_END); + + Key * baseRoot = keyNew ("system:/test", KEY_END); + Key * oursRoot = keyNew ("system:/test", KEY_END); + Key * theirsRoot = keyNew ("system:/test", KEY_END); + Key * root = keyNew ("system:/test", KEY_END); + + ksAppendKey (ksBase, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + + ksAppendKey (ksOurs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksOurs, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + + ksAppendKey (ksTheirs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksTheirs, keyNew ("system:/test/k3", KEY_VALUE, "k3", KEY_END)); + + Key * information = keyNew ("system:/", KEY_END); + + KeySet * result = elektraMerge (ksOurs, oursRoot, ksTheirs, theirsRoot, ksBase, baseRoot, root, MERGE_STRATEGY_ABORT, information); + + succeed_if (result != NULL, "result must not be NULL"); + succeed_if (ksGetSize (result) == 3, "result must contain 3 keys"); + succeed_if (ksLookupByName (result, "system:/test/k1", KDB_O_NONE) != NULL, "system:/test/k1 must be included in result"); + succeed_if (ksLookupByName (result, "system:/test/k2", KDB_O_NONE) != NULL, "system:/test/k2 must be included in result"); + succeed_if (ksLookupByName (result, "system:/test/k3", KDB_O_NONE) != NULL, "system:/test/k3 must be included in result"); + succeed_if (elektraMergeGetConflicts (information) == 0, "must not have any conflicts"); + + keyDel (baseRoot); + keyDel (oursRoot); + keyDel (theirsRoot); + keyDel (root); + keyDel (information); + + ksDel (ksBase); + ksDel (ksOurs); + ksDel (ksTheirs); + ksDel (result); +} + +static void test_removed_keys_in_both (void) +{ + printf ("test removed keys in both merge scenario\n"); + + KeySet * ksBase = ksNew (0, KS_END); + KeySet * ksOurs = ksNew (0, KS_END); + KeySet * ksTheirs = ksNew (0, KS_END); + + Key * baseRoot = keyNew ("system:/test", KEY_END); + Key * oursRoot = keyNew ("system:/test", KEY_END); + Key * theirsRoot = keyNew ("system:/test", KEY_END); + Key * root = keyNew ("system:/test", KEY_END); + + ksAppendKey (ksBase, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksBase, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + ksAppendKey (ksBase, keyNew ("system:/test/k3", KEY_VALUE, "k3", KEY_END)); + + // we removed k3 + ksAppendKey (ksOurs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksOurs, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + + // they removed k2 + ksAppendKey (ksTheirs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksTheirs, keyNew ("system:/test/k3", KEY_VALUE, "k3", KEY_END)); + + Key * information = keyNew ("system:/", KEY_END); + + KeySet * result = elektraMerge (ksOurs, oursRoot, ksTheirs, theirsRoot, ksBase, baseRoot, root, MERGE_STRATEGY_ABORT, information); + + succeed_if (result != NULL, "result must not be NULL"); + succeed_if (ksGetSize (result) == 1, "result must contain 1 keys"); + succeed_if (ksLookupByName (result, "system:/test/k1", KDB_O_NONE) != NULL, "system:/test/k1 must be included in result"); + succeed_if (elektraMergeGetConflicts (information) == 0, "must not have any conflicts"); + + keyDel (baseRoot); + keyDel (oursRoot); + keyDel (theirsRoot); + keyDel (root); + keyDel (information); + + ksDel (ksBase); + ksDel (ksOurs); + ksDel (ksTheirs); + ksDel (result); +} + +static void test_changed_different_keys_in_both (void) +{ + printf ("test removed keys in both merge scenario\n"); + + KeySet * ksBase = ksNew (0, KS_END); + KeySet * ksOurs = ksNew (0, KS_END); + KeySet * ksTheirs = ksNew (0, KS_END); + + Key * baseRoot = keyNew ("system:/test", KEY_END); + Key * oursRoot = keyNew ("system:/test", KEY_END); + Key * theirsRoot = keyNew ("system:/test", KEY_END); + Key * root = keyNew ("system:/test", KEY_END); + + ksAppendKey (ksBase, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksBase, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + ksAppendKey (ksBase, keyNew ("system:/test/k3", KEY_VALUE, "k3", KEY_END)); + + // we changed k2 + ksAppendKey (ksOurs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksOurs, keyNew ("system:/test/k2", KEY_VALUE, "k2-c", KEY_END)); + ksAppendKey (ksOurs, keyNew ("system:/test/k3", KEY_VALUE, "k3", KEY_END)); + + // they changed k3 + ksAppendKey (ksTheirs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksTheirs, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + ksAppendKey (ksTheirs, keyNew ("system:/test/k3", KEY_VALUE, "k3-c", KEY_END)); + + Key * information = keyNew ("system:/", KEY_END); + + KeySet * result = elektraMerge (ksOurs, oursRoot, ksTheirs, theirsRoot, ksBase, baseRoot, root, MERGE_STRATEGY_ABORT, information); + + succeed_if (result != NULL, "result must not be NULL"); + + succeed_if (ksGetSize (result) == 3, "result must contain 3 keys"); + Key * k1 = ksLookupByName (result, "system:/test/k1", KDB_O_NONE); + succeed_if (k1 != NULL, "system:/test/k1 must be included in result"); + succeed_if (strcmp ("k1", keyString (k1)) == 0, "value of k1 must be 'k1'"); + + Key * k2 = ksLookupByName (result, "system:/test/k2", KDB_O_NONE); + succeed_if (k2 != NULL, "system:/test/k2 must be included in result"); + succeed_if (strcmp ("k2-c", keyString (k2)) == 0, "value of k2 must be 'k2-c'"); + + Key * k3 = ksLookupByName (result, "system:/test/k3", KDB_O_NONE); + succeed_if (k3 != NULL, "system:/test/k3 must be included in result"); + succeed_if (strcmp ("k3-c", keyString (k3)) == 0, "value of k3 must be 'k3-c'"); + + succeed_if (elektraMergeGetConflicts (information) == 0, "must not have any conflicts"); + + keyDel (baseRoot); + keyDel (oursRoot); + keyDel (theirsRoot); + keyDel (root); + keyDel (information); + + ksDel (ksBase); + ksDel (ksOurs); + ksDel (ksTheirs); + ksDel (result); +} + +static void test_changed_same_key_abort (void) +{ + printf ("test conflict with ABORT\n"); + + KeySet * ksBase = ksNew (0, KS_END); + KeySet * ksOurs = ksNew (0, KS_END); + KeySet * ksTheirs = ksNew (0, KS_END); + + Key * baseRoot = keyNew ("system:/test", KEY_END); + Key * oursRoot = keyNew ("system:/test", KEY_END); + Key * theirsRoot = keyNew ("system:/test", KEY_END); + Key * root = keyNew ("system:/test", KEY_END); + + ksAppendKey (ksBase, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksBase, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + + // we changed k2 + ksAppendKey (ksOurs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksOurs, keyNew ("system:/test/k2", KEY_VALUE, "k2-ours", KEY_END)); + + // they changed k2 + ksAppendKey (ksTheirs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksTheirs, keyNew ("system:/test/k2", KEY_VALUE, "k2-theirs", KEY_END)); + + Key * information = keyNew ("system:/", KEY_END); + + KeySet * result = elektraMerge (ksOurs, oursRoot, ksTheirs, theirsRoot, ksBase, baseRoot, root, MERGE_STRATEGY_ABORT, information); + + succeed_if (result == NULL, "result must be NULL"); + succeed_if (elektraMergeGetConflicts (information) == 1, "must have 1 conflicts"); + + keyDel (baseRoot); + keyDel (oursRoot); + keyDel (theirsRoot); + keyDel (root); + keyDel (information); + + ksDel (ksBase); + ksDel (ksOurs); + ksDel (ksTheirs); + ksDel (result); +} + +static void test_changed_same_key_their (void) +{ + printf ("test conflict with THEIR\n"); + + KeySet * ksBase = ksNew (0, KS_END); + KeySet * ksOurs = ksNew (0, KS_END); + KeySet * ksTheirs = ksNew (0, KS_END); + + Key * baseRoot = keyNew ("system:/test", KEY_END); + Key * oursRoot = keyNew ("system:/test", KEY_END); + Key * theirsRoot = keyNew ("system:/test", KEY_END); + Key * root = keyNew ("system:/test", KEY_END); + + ksAppendKey (ksBase, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksBase, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + + // we changed k2 + ksAppendKey (ksOurs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksOurs, keyNew ("system:/test/k2", KEY_VALUE, "k2-our", KEY_END)); + + // they changed k2 + ksAppendKey (ksTheirs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksTheirs, keyNew ("system:/test/k2", KEY_VALUE, "k2-their", KEY_END)); + + Key * information = keyNew ("system:/", KEY_END); + + KeySet * result = elektraMerge (ksOurs, oursRoot, ksTheirs, theirsRoot, ksBase, baseRoot, root, MERGE_STRATEGY_THEIR, information); + + succeed_if (result != NULL, "result must not be NULL"); + + succeed_if (ksGetSize (result) == 2, "result must contain 2 keys"); + Key * k1 = ksLookupByName (result, "system:/test/k1", KDB_O_NONE); + succeed_if (k1 != NULL, "system:/test/k1 must be included in result"); + succeed_if (strcmp ("k1", keyString (k1)) == 0, "value of k1 must be 'k1'"); + + Key * k2 = ksLookupByName (result, "system:/test/k2", KDB_O_NONE); + succeed_if (k2 != NULL, "system:/test/k2 must be included in result"); + succeed_if (strcmp ("k2-their", keyString (k2)) == 0, "value of k2 must be 'k2-their'"); + + succeed_if (elektraMergeGetConflicts (information) == 1, "must have 1 conflicts"); + + keyDel (baseRoot); + keyDel (oursRoot); + keyDel (theirsRoot); + keyDel (root); + keyDel (information); + + ksDel (ksBase); + ksDel (ksOurs); + ksDel (ksTheirs); + ksDel (result); +} + +static void test_changed_same_key_our (void) +{ + printf ("test conflict with OUR\n"); + + KeySet * ksBase = ksNew (0, KS_END); + KeySet * ksOurs = ksNew (0, KS_END); + KeySet * ksTheirs = ksNew (0, KS_END); + + Key * baseRoot = keyNew ("system:/test", KEY_END); + Key * oursRoot = keyNew ("system:/test", KEY_END); + Key * theirsRoot = keyNew ("system:/test", KEY_END); + Key * root = keyNew ("system:/test", KEY_END); + + ksAppendKey (ksBase, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksBase, keyNew ("system:/test/k2", KEY_VALUE, "k2", KEY_END)); + + // we changed k2 + ksAppendKey (ksOurs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksOurs, keyNew ("system:/test/k2", KEY_VALUE, "k2-our", KEY_END)); + + // they changed k2 + ksAppendKey (ksTheirs, keyNew ("system:/test/k1", KEY_VALUE, "k1", KEY_END)); + ksAppendKey (ksTheirs, keyNew ("system:/test/k2", KEY_VALUE, "k2-their", KEY_END)); + + Key * information = keyNew ("system:/", KEY_END); + + KeySet * result = elektraMerge (ksOurs, oursRoot, ksTheirs, theirsRoot, ksBase, baseRoot, root, MERGE_STRATEGY_OUR, information); + + succeed_if (result != NULL, "result must not be NULL"); + + succeed_if (ksGetSize (result) == 2, "result must contain 2 keys"); + Key * k1 = ksLookupByName (result, "system:/test/k1", KDB_O_NONE); + succeed_if (k1 != NULL, "system:/test/k1 must be included in result"); + succeed_if (strcmp ("k1", keyString (k1)) == 0, "value of k1 must be 'k1'"); + + Key * k2 = ksLookupByName (result, "system:/test/k2", KDB_O_NONE); + succeed_if (k2 != NULL, "system:/test/k2 must be included in result"); + succeed_if (strcmp ("k2-our", keyString (k2)) == 0, "value of k2 must be 'k2-our'"); + + succeed_if (elektraMergeGetConflicts (information) == 1, "must have 1 conflicts"); + + keyDel (baseRoot); + keyDel (oursRoot); + keyDel (theirsRoot); + keyDel (root); + keyDel (information); + + ksDel (ksBase); + ksDel (ksOurs); + ksDel (ksTheirs); + ksDel (result); +} + +int main (int argc, char ** argv) +{ + printf ("MERGE TESTS\n"); + printf ("==================\n\n"); + + init (argc, argv); + + test_new_keys_in_both (); + test_removed_keys_in_both (); + test_changed_different_keys_in_both (); + test_changed_same_key_abort (); + test_changed_same_key_their (); + test_changed_same_key_our (); + + printf ("\ntest_merge RESULTS: %d test(s) done. %d error(s).\n", nbTest, nbError); + + return nbError; +} diff --git a/tests/ctest/test_opts.c b/tests/ctest/test_opts.c index 3827bdf7dd5..4f30c388624 100644 --- a/tests/ctest/test_opts.c +++ b/tests/ctest/test_opts.c @@ -996,6 +996,7 @@ static void test_help (void) " --help Print this help message\n" " -a, -b BANANA, -C, --apple, --banana=BANANA, --cherry=[ARG]\n" " Apple/Banana/Cherry description\n" + " -i, -I, --interactive=[WHEN]prompt according to WHEN: never, once (-I), or always (-i), without WHEN, prompt always\n" " -p ARG A pear is not an apple, nor a banana, nor a cherry.\n" "\n" "PARAMETERS\n" @@ -1024,7 +1025,22 @@ static void test_help (void) keySetMeta (k, "env/#1", "BANANA"); keySetMeta (k, "env/#2", "CHERRY"); keySetMeta (k, "description", "Apple/Banana/Cherry description"); - ks = ksNew (4, k, + + + // example from the tutorial + Key * k2 = keyNew (SPEC_BASE_KEY "/interactive", KEY_END); + keySetMeta (k2, "description", "prompt according to WHEN: never, once (-I), or always (-i), without WHEN, prompt always"); + keySetMeta (k2, "opt", "#1"); + keySetMeta (k2, "opt/#0", "i"); + keySetMeta (k2, "opt/#0/arg", "optional"); + keySetMeta (k2, "opt/#0/flagvalue", "always"); + keySetMeta (k2, "opt/#0/long", "interactive"); + keySetMeta (k2, "opt/#0/arg/help", "WHEN"); + keySetMeta (k2, "opt/#1", "I"); + keySetMeta (k2, "opt/#1/arg", "none"); + keySetMeta (k2, "opt/#1/flagvalue", "once"); + + ks = ksNew (5, k, k2, keyNew (SPEC_BASE_KEY "/pear", KEY_META, "opt", "p", KEY_META, "description", "A pear is not an apple, nor a banana, nor a cherry.", KEY_END), keyNew (SPEC_BASE_KEY "/param1", KEY_META, "args", "indexed", KEY_META, "args/index", "0", KEY_META, "description",