mirror of
https://github.com/kiwix/libkiwix.git
synced 2025-12-30 09:58:10 -05:00
Compare commits
13 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
e05bd8efd6 | ||
|
|
71462696bd | ||
|
|
fb79cde729 | ||
|
|
c986290d83 | ||
|
|
af9afab821 | ||
|
|
14af7b756e | ||
|
|
ff605873ed | ||
|
|
6c49c7ee0a | ||
|
|
157d1664cf | ||
|
|
6f92b7e120 | ||
|
|
fd62acd232 | ||
|
|
1cdf830217 | ||
|
|
0b48ab20bb |
27
.github/workflows/ci.yml
vendored
27
.github/workflows/ci.yml
vendored
@@ -53,30 +53,41 @@ jobs:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
target:
|
||||
name:
|
||||
- native_static
|
||||
- native_dyn
|
||||
- native_dyn_bionic
|
||||
- android_arm
|
||||
- android_arm64
|
||||
- win32_static
|
||||
- win32_dyn
|
||||
include:
|
||||
- target: native_static
|
||||
- name: native_static
|
||||
target: native_static
|
||||
image_variant: xenial
|
||||
lib_postfix: '/x86_64-linux-gnu'
|
||||
- target: native_dyn
|
||||
- name: native_dyn
|
||||
target: native_dyn
|
||||
image_variant: xenial
|
||||
lib_postfix: '/x86_64-linux-gnu'
|
||||
- target: android_arm
|
||||
- name: native_dyn_bionic
|
||||
target: native_dyn
|
||||
image_variant: bionic
|
||||
lib_postfix: '/x86_64-linux-gnu'
|
||||
- name: android_arm
|
||||
target: android_arm
|
||||
image_variant: xenial
|
||||
lib_postfix: '/x86_64-linux-gnu'
|
||||
- target: android_arm64
|
||||
- name: android_arm64
|
||||
target: android_arm64
|
||||
image_variant: xenial
|
||||
lib_postfix: '/x86_64-linux-gnu'
|
||||
- target: win32_static
|
||||
- name: win32_static
|
||||
target: win32_static
|
||||
image_variant: f31
|
||||
lib_postfix: '64'
|
||||
- target: win32_dyn
|
||||
- name: win32_dyn
|
||||
target: win32_dyn
|
||||
image_variant: f31
|
||||
lib_postfix: '64'
|
||||
env:
|
||||
@@ -147,6 +158,6 @@ jobs:
|
||||
curl https://codecov.io/bash -o codecov.sh
|
||||
bash codecov.sh -n "${OS_NAME}_${{matrix.target}}" -Z
|
||||
rm codecov.sh
|
||||
if: startsWith(matrix.target, 'native_')
|
||||
if: startsWith(matrix.target, 'native_') && matrix.image_variant == 'xenial'
|
||||
env:
|
||||
CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }}
|
||||
|
||||
@@ -1,3 +1,11 @@
|
||||
kiwix-lib 9.2.3
|
||||
===============
|
||||
|
||||
* Add test on byte-range
|
||||
* Fix compilation on bionic and windows.
|
||||
* Allow building using debian packaged kainjow-mustache
|
||||
* Pass `-latomic` compile option for architectures that need it
|
||||
|
||||
kiwix-lib 9.2.2
|
||||
===============
|
||||
|
||||
|
||||
@@ -26,7 +26,7 @@ task writePom {
|
||||
project {
|
||||
groupId 'org.kiwix.kiwixlib'
|
||||
artifactId 'kiwixlib'
|
||||
version '9.2.2' + (System.env.KIWIXLIB_BUILDVERSION == null ? '' : '-'+System.env.KIWIXLIB_BUILDVERSION)
|
||||
version '9.2.3' + (System.env.KIWIXLIB_BUILDVERSION == null ? '' : '-'+System.env.KIWIXLIB_BUILDVERSION)
|
||||
packaging 'aar'
|
||||
name 'kiwixlib'
|
||||
url 'https://github.com/kiwix/kiwix-lib'
|
||||
|
||||
15
meson.build
15
meson.build
@@ -1,5 +1,5 @@
|
||||
project('kiwix-lib', 'cpp',
|
||||
version : '9.2.2', # Also change this in android-kiwix-lib-publisher/kiwixLibAndroid/build.gradle
|
||||
version : '9.2.3', # Also change this in android-kiwix-lib-publisher/kiwixLibAndroid/build.gradle
|
||||
license : 'GPL',
|
||||
default_options : ['c_std=c11', 'cpp_std=c++11', 'werror=true'])
|
||||
|
||||
@@ -18,6 +18,11 @@ if 'java' in wrapper
|
||||
add_languages('java')
|
||||
endif
|
||||
|
||||
# See https://github.com/kiwix/kiwix-lib/issues/371
|
||||
if target_machine.cpu_family() in ['arm', 'mips', 'm68k', 'ppc']
|
||||
extra_libs += '-latomic'
|
||||
endif
|
||||
|
||||
thread_dep = dependency('threads')
|
||||
libicu_dep = dependency('icu-i18n', static:static_deps)
|
||||
libzim_dep = dependency('libzim', version : '>=6.1.1', static:static_deps)
|
||||
@@ -25,7 +30,11 @@ pugixml_dep = dependency('pugixml', static:static_deps)
|
||||
libcurl_dep = dependency('libcurl', static:static_deps)
|
||||
microhttpd_dep = dependency('libmicrohttpd', static:static_deps)
|
||||
|
||||
if not compiler.has_header('mustache.hpp')
|
||||
if compiler.has_header('mustache.hpp')
|
||||
extra_include = []
|
||||
elif compiler.has_header('mustache.hpp', args: '-I/usr/include/kainjow')
|
||||
extra_include = ['/usr/include/kainjow']
|
||||
else
|
||||
error('Cannot found header mustache.hpp')
|
||||
endif
|
||||
|
||||
@@ -37,7 +46,7 @@ endif
|
||||
|
||||
all_deps = [thread_dep, libicu_dep, libzim_dep, pugixml_dep, libcurl_dep, microhttpd_dep]
|
||||
|
||||
inc = include_directories('include')
|
||||
inc = include_directories('include', extra_include)
|
||||
|
||||
conf = configuration_data()
|
||||
conf.set('VERSION', '"@0@"'.format(meson.project_version()))
|
||||
|
||||
@@ -53,6 +53,7 @@ kiwixlib = library('kiwix',
|
||||
kiwix_sources,
|
||||
include_directories : inc,
|
||||
dependencies : all_deps,
|
||||
link_args: extra_libs,
|
||||
version: meson.project_version(),
|
||||
install: true,
|
||||
install_dir: install_dir)
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
#include "tools/stringTools.h"
|
||||
|
||||
#include <cassert>
|
||||
#include <algorithm>
|
||||
|
||||
namespace kiwix {
|
||||
|
||||
|
||||
BIN
test/data/corner_cases.zim
Normal file
BIN
test/data/corner_cases.zim
Normal file
Binary file not shown.
0
test/data/corner_cases/empty.css
Normal file
0
test/data/corner_cases/empty.css
Normal file
0
test/data/corner_cases/empty.html
Normal file
0
test/data/corner_cases/empty.html
Normal file
0
test/data/corner_cases/empty.js
Normal file
0
test/data/corner_cases/empty.js
Normal file
0
test/data/corner_cases/empty.png
Normal file
0
test/data/corner_cases/empty.png
Normal file
15
test/data/create_corner_cases_zim_file
Executable file
15
test/data/create_corner_cases_zim_file
Executable file
@@ -0,0 +1,15 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
cd "$(dirname "$0")"
|
||||
rm -f corner_cases.zim
|
||||
zimwriterfs -w empty.html \
|
||||
-f empty.png \
|
||||
-l=en \
|
||||
-t="ZIM corner cases" \
|
||||
-d="" \
|
||||
-c="" \
|
||||
-p="" \
|
||||
corner_cases \
|
||||
corner_cases.zim \
|
||||
&& echo 'corner_cases.zim was successfully created' \
|
||||
|| echo '!!! Failed to create corner_cases.zim !!!' >&2
|
||||
@@ -29,6 +29,9 @@ if gtest_dep.found() and not meson.is_cross_build()
|
||||
configure_file(input : 'data/wikipedia_en_ray_charles_mini_2020-03.zim',
|
||||
output : 'zimfile.zim',
|
||||
copy: true )
|
||||
configure_file(input : 'data/corner_cases.zim',
|
||||
output : 'corner_cases.zim',
|
||||
copy: true )
|
||||
|
||||
foreach test_name : tests
|
||||
# XXX: implicit_include_directories must be set to false, otherwise
|
||||
|
||||
@@ -50,9 +50,10 @@ class ZimFileServer
|
||||
{
|
||||
public: // types
|
||||
typedef std::shared_ptr<httplib::Response> Response;
|
||||
typedef std::vector<std::string> FilePathCollection;
|
||||
|
||||
public: // functions
|
||||
ZimFileServer(int serverPort, std::string zimpath);
|
||||
ZimFileServer(int serverPort, const FilePathCollection& zimpaths);
|
||||
~ZimFileServer();
|
||||
|
||||
Response GET(const char* path, const Headers& headers = Headers())
|
||||
@@ -73,11 +74,13 @@ private: // data
|
||||
std::unique_ptr<httplib::Client> client;
|
||||
};
|
||||
|
||||
ZimFileServer::ZimFileServer(int serverPort, std::string zimpath)
|
||||
ZimFileServer::ZimFileServer(int serverPort, const FilePathCollection& zimpaths)
|
||||
: manager(&this->library)
|
||||
{
|
||||
if (!manager.addBookFromPath(zimpath, zimpath, "", false))
|
||||
throw std::runtime_error("Unable to add the ZIM file '" + zimpath + "'");
|
||||
for ( const auto zimpath : zimpaths ) {
|
||||
if (!manager.addBookFromPath(zimpath, zimpath, "", false))
|
||||
throw std::runtime_error("Unable to add the ZIM file '" + zimpath + "'");
|
||||
}
|
||||
|
||||
const std::string address = "127.0.0.1";
|
||||
nameMapper.reset(new kiwix::HumanReadableNameMapper(library, false));
|
||||
@@ -104,11 +107,14 @@ protected:
|
||||
std::unique_ptr<ZimFileServer> zfs1_;
|
||||
|
||||
const int PORT = 8001;
|
||||
const std::string ZIMFILE = "./test/zimfile.zim";
|
||||
const ZimFileServer::FilePathCollection ZIMFILES {
|
||||
"./test/zimfile.zim",
|
||||
"./test/corner_cases.zim"
|
||||
};
|
||||
|
||||
protected:
|
||||
void SetUp() override {
|
||||
zfs1_.reset(new ZimFileServer(PORT, ZIMFILE));
|
||||
zfs1_.reset(new ZimFileServer(PORT, ZIMFILES));
|
||||
}
|
||||
|
||||
void TearDown() override {
|
||||
@@ -174,6 +180,10 @@ const ResourceCollection resources200Uncompressible{
|
||||
{ WITH_ETAG, "/meta?content=zimfile&name=favicon" },
|
||||
|
||||
{ WITH_ETAG, "/zimfile/I/m/Ray_Charles_classic_piano_pose.jpg" },
|
||||
|
||||
{ WITH_ETAG, "/corner_cases/A/empty.html" },
|
||||
{ WITH_ETAG, "/corner_cases/-/empty.css" },
|
||||
{ WITH_ETAG, "/corner_cases/-/empty.js" },
|
||||
};
|
||||
|
||||
ResourceCollection all200Resources()
|
||||
@@ -307,7 +317,7 @@ TEST_F(ServerTest, ETagIsTheSameAcrossHeadAndGet)
|
||||
|
||||
TEST_F(ServerTest, DifferentServerInstancesProduceDifferentETags)
|
||||
{
|
||||
ZimFileServer zfs2(PORT + 1, ZIMFILE);
|
||||
ZimFileServer zfs2(PORT + 1, ZIMFILES);
|
||||
for ( const Resource& res : all200Resources() ) {
|
||||
if ( !res.etag_expected ) continue;
|
||||
const auto h1 = zfs1_->HEAD(res.url);
|
||||
@@ -428,7 +438,7 @@ TEST_F(ServerTest, ValidSingleRangeByteRangeRequestsAreHandledProperly)
|
||||
const auto p = zfs1_->GET(url, { {"Range", "bytes=0-10"} } );
|
||||
EXPECT_EQ(206, p->status);
|
||||
EXPECT_EQ("bytes 0-10/20077", p->get_header_value("Content-Range"));
|
||||
EXPECT_EQ(11, p->body.size());
|
||||
EXPECT_EQ(11U, p->body.size());
|
||||
EXPECT_EQ(full->body.substr(0, 11), p->body);
|
||||
EXPECT_EQ("bytes", p->get_header_value("Accept-Ranges"));
|
||||
}
|
||||
@@ -437,7 +447,7 @@ TEST_F(ServerTest, ValidSingleRangeByteRangeRequestsAreHandledProperly)
|
||||
const auto p = zfs1_->GET(url, { {"Range", "bytes=123-456"} } );
|
||||
EXPECT_EQ(206, p->status);
|
||||
EXPECT_EQ("bytes 123-456/20077", p->get_header_value("Content-Range"));
|
||||
EXPECT_EQ(334, p->body.size());
|
||||
EXPECT_EQ(334U, p->body.size());
|
||||
EXPECT_EQ(full->body.substr(123, 334), p->body);
|
||||
EXPECT_EQ("bytes", p->get_header_value("Accept-Ranges"));
|
||||
}
|
||||
@@ -480,6 +490,25 @@ TEST_F(ServerTest, InvalidAndMultiRangeByteRangeRequestsResultIn416Responses)
|
||||
}
|
||||
}
|
||||
|
||||
TEST_F(ServerTest, ValidByteRangeRequestsOfZeroSizedEntriesResultIn416Responses)
|
||||
{
|
||||
const char url[] = "/corner_cases/-/empty.js";
|
||||
|
||||
const char* ranges[] = {
|
||||
"bytes=0-",
|
||||
"bytes=-100"
|
||||
};
|
||||
|
||||
for( const char* range : ranges )
|
||||
{
|
||||
const TestContext ctx{ {"Range", range} };
|
||||
const auto p = zfs1_->GET(url, { {"Range", range } } );
|
||||
EXPECT_EQ(416, p->status) << ctx;
|
||||
EXPECT_TRUE(p->body.empty()) << ctx;
|
||||
EXPECT_EQ("bytes */0", p->get_header_value("Content-Range")) << ctx;
|
||||
}
|
||||
}
|
||||
|
||||
TEST_F(ServerTest, RangeHasPrecedenceOverCompression)
|
||||
{
|
||||
const char url[] = "/zimfile/I/m/Ray_Charles_classic_piano_pose.jpg";
|
||||
|
||||
Reference in New Issue
Block a user