Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support for library reloading #636

Merged
merged 24 commits into from
Nov 30, 2021
Merged

Support for library reloading #636

merged 24 commits into from
Nov 30, 2021

Conversation

veloman-yunkan
Copy link
Collaborator

@veloman-yunkan veloman-yunkan commented Nov 20, 2021

Enables kiwix/kiwix-tools#497 to fix kiwix/kiwix-tools#243

This PR provides facilities for reloading and updating the library with any of

  • new books
  • removed books
  • any changes in book metadata.

The PR also includes various improvements/bugfixes noticed while working on this PR, as well as a few new unit-tests.

API changes introduced by this PR are addressed in kiwix-desktop by kiwix/kiwix-desktop#732.

@codecov
Copy link

codecov bot commented Nov 20, 2021

Codecov Report

Merging #636 (3a127e4) into master (c7b8839) will increase coverage by 0.55%.
The diff coverage is 76.64%.

❗ Current head 3a127e4 differs from pull request most recent head 405ea29. Consider uploading reports for the commit 405ea29 to get more accurate results
Impacted file tree graph

@@            Coverage Diff             @@
##           master     #636      +/-   ##
==========================================
+ Coverage   66.62%   67.17%   +0.55%     
==========================================
  Files          53       53              
  Lines        3823     3906      +83     
  Branches     1931     1979      +48     
==========================================
+ Hits         2547     2624      +77     
- Misses       1274     1281       +7     
+ Partials        2        1       -1     
Impacted Files Coverage Δ
include/name_mapper.h 71.42% <33.33%> (+4.76%) ⬆️
include/library.h 92.30% <50.00%> (+0.64%) ⬆️
src/manager.cpp 77.27% <72.72%> (-0.71%) ⬇️
src/library.cpp 77.72% <73.33%> (-0.79%) ⬇️
include/manager.h 100.00% <100.00%> (+22.22%) ⬆️
src/book.cpp 93.10% <100.00%> (ø)
src/name_mapper.cpp 100.00% <100.00%> (+50.00%) ⬆️
src/opds_dumper.cpp 100.00% <100.00%> (ø)
... and 1 more

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update c7b8839...405ea29. Read the comment docs.

@veloman-yunkan veloman-yunkan changed the title [WIP] Support for library reloading Support for library reloading (without handling book removal). Nov 22, 2021
@veloman-yunkan veloman-yunkan marked this pull request as ready for review November 22, 2021 17:23
Copy link
Member

@mgautierfr mgautierfr left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've nothing to say about the quality of the code itself here. Really good as usual.

I'm a bit disturbed by the ReloadableLibrary.
The idea was to have the Library as a "simple" container of book and have all manipulation of the library put elsewhere (Manager/Manipulator)
The ReloadableLibray takes the opposite direction by creating a library which knows from what is was created and can reload itself.
I would have extend the Manager to be able to do a "diff" between the "library.xml" it is reading and the Library it is managing and apply this "diff" to the Library

What about multithreading ?
We will reload the library while a server will run in the same time.
We must be prepared to concurrent access/modifications.

And we need book removal.
The new library.xml will have new books added and old books removed. We must correctly handle this

include/name_mapper.h Outdated Show resolved Hide resolved
src/library.cpp Show resolved Hide resolved
include/reloadable_library.h Outdated Show resolved Hide resolved
veloman-yunkan added a commit to kiwix/kiwix-desktop that referenced this pull request Nov 28, 2021
Fixed the build failure caused by the libkiwix API changes done in
kiwix/libkiwix#636.
@veloman-yunkan veloman-yunkan changed the title Support for library reloading (without handling book removal). Support for library reloading Nov 28, 2021
@veloman-yunkan
Copy link
Collaborator Author

@mgautierfr

What about multithreading ? We will reload the library while a server will run in the same time. We must be prepared to concurrent access/modifications.

Library is now thread safe as long as its usage in kiwix-serve is concerned.

And we need book removal. The new library.xml will have new books added and old books removed. We must correctly handle this

Added prototype support for book removal during library reloading that neglects LibraryManipulator. If you don't object against my approach, then respecting LibraryManipulator should not be a problem, though there are several options to do that.

Copy link
Member

@mgautierfr mgautierfr left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you don't object against my approach, then respecting LibraryManipulator should not be a problem, though there are several options to do that.

Marking the book updated is a good enough way to detect books not updated.


In this PR you modify a bit the LibraryManipulator to provide a default implementation and also a bit the behavior of the Manager (The Manager is not a one shoot object but it is keep alive to be reused).
I'm not against those changes, on the contrary. If you think we can go further to reorganize all those different classes, please do not hesitate to do it (maybe not in this PR, or open a discussion to be sure about what we can do).

src/library.cpp Show resolved Hide resolved
if ( ! booksReferToTheSameArchive(oldbook, book) ) {
dropReader(book.getId());
}
oldbook.update(book); // XXX: This may have no effect if oldbook is readonly
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't know why we have this "readonly" attribute on the book.
This is something pretty old and we don't use it at all. Maybe @kelson42 knows why it has been introduced.

But if you want to drop it, I agree 🙂

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If @kelson42 doesn't come up with arguments against removing Book::m_readOnly I will do it in a separate PR.

src/library.cpp Show resolved Hide resolved
@mgautierfr
Copy link
Member

Please rebase-fixup and we can merge.

Originally `LibraryManipulator` was an abstract class completely decoupled
from `Library`. Its `addBookToLibrary()` and `addBookmarkToLibrary()`
methods could be defined in an arbitrary way. Now `LibraryManipulator` has to be
bound to a library object, those methods are no longer virtual, they always
update the library and allow for some additional actions via virtual
functions `bookWasAddedToLibrary()` and `bookmarkWasAddedToLibrary()`.
Introducing a mutex in `Library` necessitates manually implementing the
move constructor and assignment operator. It's better to still delegate
that work to the compiler to eliminate any possibility of bugs when new
data members are added to `Library`. The trick is to move the data into
an auxiliary class `LibraryBase` and derive `Library` from it.
Library became thread-safe with the exception of `getBookById()`
and `getBookByPath()` methods - thread safety in those accessors is
rendered meaningless by their return type (they return a reference
to a book which can be removed any time later by another thread).
@veloman-yunkan
Copy link
Collaborator Author

Please rebase-fixup and we can merge.

Done (also fixed a few typos noticed during the final quick review).

@mgautierfr mgautierfr merged commit 01ac0b2 into master Nov 30, 2021
@mgautierfr mgautierfr deleted the library_reloading branch November 30, 2021 17:08
mgautierfr pushed a commit to kiwix/kiwix-desktop that referenced this pull request Dec 1, 2021
Fixed the build failure caused by the libkiwix API changes done in
kiwix/libkiwix#636.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

kiwix-serve should reload automatically content (library/files)
2 participants