Skip to content

Conversation

@GianniCarlo
Copy link
Collaborator

@GianniCarlo GianniCarlo commented Jan 31, 2026

Bugfixes

– Prevent users from importing the app's own Documents folder, which corrupts the library directory
– Fix searching by author
– Fix content bottom inset in the Account screen
– Hide mini-player when the keyboard is showing

Improvements

– New style for edit toolbar in library screen

If you'd like to contribute with translations to other languages, please reach us at support@bookplayer.app

Copy link

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

This PR addresses version 5.16.1 release with several bug fixes and enhancements focused on search functionality, UI improvements, and data integrity.

Changes:

  • Enhanced search functionality to include author/details field alongside title searches
  • Improved keyboard handling to hide mini-player when keyboard is visible
  • Added protection against importing the app's own Documents folder to prevent library corruption
  • Updated API models (publicId → externalId) and improved server error handling

Reviewed changes

Copilot reviewed 12 out of 12 changed files in this pull request and generated 4 comments.

Show a summary per file
File Description
Shared/Services/LibraryService.swift Updated search predicates to search both title and details (author) fields
Shared/Services/Account/PasskeyModels.swift Renamed publicId field to externalId for API consistency
Shared/Network/NetworkClient.swift Added proper error handling for 5xx server responses
Shared/CoreData/DataManager.swift Added isAppOwnFolder() method to prevent importing app's own folders
BookPlayerTests/Services/LibraryServiceTests.swift Added comprehensive test suite for search functionality
BookPlayer/Utils/Extensions/View+BookPlayer.swift Implemented KeyboardObserver and menuTint helper for UI improvements
BookPlayer/Search/SearchViewModel.swift Added logic to properly handle bound books in search results
BookPlayer/Profile/Account/AccountView.swift Added mini-player safe area inset for consistent spacing
BookPlayer/MainView.swift Integrated keyboard observer to conditionally show mini-player
BookPlayer/Library/ItemList/ItemListViewModel.swift Added folder import validation with isAppOwnFolder check
BookPlayer/Library/ItemList/ItemListView.swift Refactored edit toolbar with new menu-based design
BookPlayer/Import/ImportManager.swift Replaced string literal with constant for better maintainability

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.


let destinationURL = documentsFolder.appendingPathComponent(url.lastPathComponent)
if !FileManager.default.fileExists(atPath: destinationURL.path) {
try! FileManager.default.copyItem(at: url, to: destinationURL)
Copy link

Copilot AI Jan 31, 2026

Choose a reason for hiding this comment

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

Using force-try (try!) here can crash the app if the file copy operation fails. This could happen due to insufficient storage space, permission issues, or if the destination already exists but is a different type (e.g., file vs directory). Consider handling this error gracefully and showing an error message to the user instead of crashing.

Suggested change
try! FileManager.default.copyItem(at: url, to: destinationURL)
do {
try FileManager.default.copyItem(at: url, to: destinationURL)
} catch {
// Handle copy errors gracefully instead of crashing
loadingState.error = error
}

Copilot uses AI. Check for mistakes.
// Left group: Edit, Move, Delete
HStack {
Button {
activeSheet = .itemDetails(item!)
Copy link

Copilot AI Jan 31, 2026

Choose a reason for hiding this comment

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

Force-unwrapping 'item!' is unsafe here. While the button is disabled when not isSingle, there's still a risk if the state changes between the disabled check and the button action. Consider using optional binding instead: 'if let item = item { activeSheet = .itemDetails(item) }' or using a guard statement to safely handle the nil case.

Suggested change
activeSheet = .itemDetails(item!)
if let item = item {
activeSheet = .itemDetails(item)
}

Copilot uses AI. Check for mistakes.

Button("details_title") {
Button {
activeSheet = .itemDetails(item!)
Copy link

Copilot AI Jan 31, 2026

Choose a reason for hiding this comment

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

Force-unwrapping 'item!' is unsafe here. While the button is disabled when not isSingle, there's still a risk if the state changes between the disabled check and the button action. Consider using optional binding instead: 'if let item = item { activeSheet = .itemDetails(item) }' or using a guard statement to safely handle the nil case.

Suggested change
activeSheet = .itemDetails(item!)
if let item = item {
activeSheet = .itemDetails(item)
}

Copilot uses AI. Check for mistakes.
Comment on lines +512 to +514
if DataManager.isAppOwnFolder(url) {
return
}
Copy link

Copilot AI Jan 31, 2026

Choose a reason for hiding this comment

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

When a user attempts to import the app's own Documents folder, the import is silently rejected without user feedback. Consider providing feedback to the user explaining why the import was blocked, such as showing an alert or toast message indicating that importing the app's own folder is not allowed to prevent data corruption.

Copilot uses AI. Check for mistakes.
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.

2 participants