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

File sharing for macOS VFS (File Provider Module) #6614

Merged
merged 172 commits into from
Apr 17, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
172 commits
Select commit Hold shift + click to select a range
1522c22
Add new FileProviderUIExt target
claucambra Feb 20, 2024
8128697
Build and install FileProviderUIExt via CMake
claucambra Feb 21, 2024
d0baa23
Add FileProviderUIExt entitlements file
claucambra Feb 21, 2024
f35148b
Add logger extension to FileProviderUIExt
claucambra Feb 21, 2024
f44fec2
Add logging for prepare methods of document action view controller
claucambra Feb 21, 2024
76045fd
Create ShareViewController
claucambra Feb 21, 2024
45b4fee
Add convenience method to prepare child view controllers in DocumentA…
claucambra Feb 21, 2024
05e7f1b
Remove unused IBActions in DocumentActionViewController
claucambra Feb 21, 2024
13aced8
Properly add share custom action
claucambra Feb 21, 2024
ce026df
Add proper design for share view in file provider UI
claucambra Feb 21, 2024
7a9ca59
Store file provider item identifiers in ShareViewController
claucambra Feb 21, 2024
9bb67ee
Make close button work properly in share view
claucambra Feb 21, 2024
1e34aff
Add domain property to document action view controller
claucambra Feb 21, 2024
09042d7
Set the right filename and icon on share view controller view
claucambra Feb 21, 2024
5fbcec1
Extract display updating upon url acquisition to different method in …
claucambra Feb 21, 2024
dbe8a5f
Add starter FPUIExtensionService protocol
claucambra Feb 21, 2024
36a8298
Implement convenience method to acquire FPUIExtensionService in share…
claucambra Feb 21, 2024
8982857
Add starter FPUIExtensionServiceSource
claucambra Feb 21, 2024
0feb5da
Add starter ItemSharesController
claucambra Feb 27, 2024
07473ac
Add fetch method to itemsharescontroller
claucambra Feb 27, 2024
a586767
Add table to ShareViewControlelr XIB
claucambra Feb 27, 2024
023e145
Add starter ShareTableItemView XIB
claucambra Feb 27, 2024
90f7e3a
Add more complete ShareTableItemView design
claucambra Feb 27, 2024
b30f8c3
Add starter ShareTableViewDataSource
claucambra Feb 27, 2024
820c7e4
Add outlet for share view table view
claucambra Feb 27, 2024
8dc9807
Add base properties to ShareTableViewDataSource
claucambra Feb 27, 2024
af93122
Move serviceConnection method to table view data source
claucambra Feb 27, 2024
6dad778
Add share fetching routine to FPUIExtensionService
claucambra Feb 27, 2024
1288448
Add item shares loading routine to ShareTableViewDataSource
claucambra Feb 27, 2024
46ad6f0
Instantiate share data source in share view controller
claucambra Feb 27, 2024
e15db9b
Fix protocol used for FPUIExtensionServiceSource
claucambra Feb 27, 2024
9ce3af3
Fix visibility of logging in ItemSharesController
claucambra Feb 27, 2024
5b1b87b
Add FPUIExtensionServiceSource to services published by FileProviderExt
claucambra Feb 27, 2024
adb4028
Fix linking of FileProviderUIExt which was missing NextcloudKit symbols
claucambra Feb 27, 2024
02b5a31
Add method to export NextcloudAccount details to dictionary
claucambra Feb 27, 2024
259a28e
Add method to convert dictionary to NextcloudAccount
claucambra Feb 27, 2024
a6992cf
Add NextcloudAccount to FileProviderUIExt
claucambra Feb 27, 2024
81dc8ce
Add method to FPUIExtensionServiceSource to get extension account det…
claucambra Feb 27, 2024
e6f20e9
Remove logging from NextcloudAccount
claucambra Feb 27, 2024
145d92e
Add method to get an item's server path through FPUIExtensionService
claucambra Feb 27, 2024
d53680e
Add release entitlements fro FileProviderUIExt
claucambra Feb 27, 2024
765f33b
Add essential table view data source method to ShareTableViewDataSource
claucambra Feb 27, 2024
8add57a
Implement NSTableViewDelegate viewFor method in sharetableviewdatasource
claucambra Feb 27, 2024
331a761
Register shareItemView nib in shareTableView
claucambra Feb 27, 2024
ff9e344
Move all share fetching logic to FileProviderUIExt
claucambra Feb 27, 2024
f118078
Remove default item view in ShareViewController table XIB
claucambra Feb 27, 2024
731a5e1
Set delegate for shares table view
claucambra Feb 27, 2024
c2ec72c
Add corresponding class for ShareTableItemView
claucambra Feb 27, 2024
ee21715
Set basic property of sharetableitemview in delegate method of data s…
claucambra Feb 27, 2024
b6c247b
Ensure usable rowHeight for shares table view
claucambra Feb 27, 2024
dda5ec2
Customise prepareForReuse in ShareTableItemView
claucambra Feb 28, 2024
4ba2bc8
Add starter NKShare extension
claucambra Feb 28, 2024
930106e
Add ShareType enum to NKShare extension
claucambra Feb 28, 2024
41f9337
Add typeImage property to NKShare extension
claucambra Feb 28, 2024
46e2ca5
Add displayString property to NKShare extension
claucambra Feb 28, 2024
18de0d0
Make share property central to display update of share table item view
claucambra Feb 28, 2024
4f0e25a
Improve share table style
claucambra Feb 28, 2024
540eb11
Implement share link copying in share table item view
claucambra Feb 28, 2024
3067397
Temporarily change copy share link button image after clicking
claucambra Feb 28, 2024
18862be
Add popover and corresponding view controller to sharetableitemview
claucambra Feb 28, 2024
da8ae80
Add starter ShareOptionsView
claucambra Feb 28, 2024
cad56f1
Implement ShareOptionsView design
claucambra Feb 28, 2024
ecf4efd
Replace ShareOptionsView with a ShareOptionsWindow
claucambra Feb 28, 2024
d3d75e8
Add starter ShareOptionsWindow class
claucambra Feb 28, 2024
70a565d
Redesign shares to incorporate share options into main share view
claucambra Feb 28, 2024
1b64e29
Extract options view to different XIB
claucambra Feb 28, 2024
d23f30a
Add a shareview ui delegate protocol for datasources
claucambra Feb 28, 2024
9b1ad4d
Treat bottom view in share view as a target view to inject other views
claucambra Feb 28, 2024
8956fce
Implement ui delegate in ShareTableViewDataSource
claucambra Feb 28, 2024
c74575c
Re-integrate share options view into main share view controller XIB
claucambra Feb 28, 2024
13fa2bc
Implement hide and show of share options in share view controller
claucambra Feb 28, 2024
55cdbe8
Add a loading overlay to table view to indicate fetch in progress
claucambra Feb 28, 2024
e113a09
Add fetch related handling functions to ui delegate
claucambra Feb 28, 2024
26d635b
Tell delegate when fetch ongoing in share table view data source
claucambra Feb 28, 2024
7a40f6f
Ensure calls are made via main actor to delegate in share table view …
claucambra Feb 28, 2024
322ae52
Add a ShareOptionsView class
claucambra Feb 28, 2024
52dbfc3
Improve placeholder text for share view password field
claucambra Mar 4, 2024
ec145d8
Handle state of share options view via setting of NKShare
claucambra Mar 4, 2024
5e0d990
Handle optionsview as ShareOptionsView in share view controller
claucambra Mar 4, 2024
aa57ba1
Add starter sharecontroller for fileprovider
claucambra Mar 4, 2024
3186617
Add convenience property to nkshare extension to get valid expiration…
claucambra Mar 4, 2024
2926234
Add functionality to share controller to save changes
claucambra Mar 4, 2024
f654a8c
Use ShareController in ShareOptionsView
claucambra Mar 4, 2024
755897b
Add convenience function to format date to valid server string in nks…
claucambra Mar 4, 2024
422a6c7
Respond to changes in share of sharecontroller in shareoptionsview
claucambra Mar 4, 2024
19316f4
Add convenience function to enable or disable all share option fields
claucambra Mar 4, 2024
3ef8813
Correctly handle NKShare's "canEdit" in share options view
claucambra Mar 4, 2024
e2b62e4
Add fields as parameters to save in sharecontroller
claucambra Mar 4, 2024
08917a9
Make save button functional in share view
claucambra Mar 4, 2024
f136304
Use a sharecontroller in shareviewcontroller
claucambra Mar 4, 2024
249dd02
Reload data source on share saving
claucambra Mar 4, 2024
5702b16
Implement more logging in sharecontroller
claucambra Mar 4, 2024
a7de8ed
Fix crash on reloading share table view data source
claucambra Mar 4, 2024
30b4509
Deselect table view or shares after reload to reset UI
claucambra Mar 4, 2024
9d6db4f
Add views to present an error in the share view controller
claucambra Mar 4, 2024
24ce9a1
Add method to show error in data source ui delegate
claucambra Mar 4, 2024
f1d3798
Add method to dismiss error in share view controller via dismiss button
claucambra Mar 4, 2024
69dfe59
Present error for updating share in file provider UI
claucambra Mar 4, 2024
4aaaf5b
Show error in share table view data source if received one in fetch
claucambra Mar 4, 2024
7e3769c
Blend in-window contents in share view loading overlay
claucambra Mar 4, 2024
41f229c
Add PermissionValues to NKShare extension
claucambra Mar 5, 2024
49450d5
Add convenience property to nkshare extension to see if sharees can e…
claucambra Mar 5, 2024
e52d6df
Properly handle permissions in shareoptionsview
claucambra Mar 5, 2024
8b285a7
Add deletion capability to sharecontroller
claucambra Mar 5, 2024
a4551b2
Improve design of save and delete buttons in share view controller
claucambra Mar 5, 2024
ff305ec
Implement deletion functionality for share options view
claucambra Mar 5, 2024
2085a12
Remove unused outlets in tableitemview
claucambra Mar 5, 2024
15f03d6
Add button to create new share in share view
claucambra Mar 5, 2024
3a58fbe
Add a popupbutton to share options vie to select type of share
claucambra Mar 5, 2024
e25bebc
Add static method to create shares in ShareController
claucambra Mar 5, 2024
8d3b101
Make item's server relative path public in sharetableviewdatasource
claucambra Mar 5, 2024
000fe02
Nilify itemServerRelativePath upon loading item in table view data so…
claucambra Mar 5, 2024
0ceb6a9
Add additional options to share controller creation method
claucambra Mar 6, 2024
e1997bd
Add "createMode" toggle to share options view, start building for use…
claucambra Mar 6, 2024
131973b
Make create button in share view controller show options view and tog…
claucambra Mar 6, 2024
4029458
Connect different share type popup button menu items to outlets in sh…
claucambra Mar 6, 2024
70cb2bd
Make share options view capable of creating or updating view upon cli…
claucambra Mar 6, 2024
a763725
Adjust share options view title depending on create mode
claucambra Mar 6, 2024
83ed6ea
Change deleteButton to a cancel button when in creation mode
claucambra Mar 6, 2024
54f3822
Have specific cancel behaviour in shareoptionsview on delete if in cr…
claucambra Mar 6, 2024
c5d57cd
Add a text field for relevant shareWith in ShareOptionsView
claucambra Mar 6, 2024
31a9db9
Correctly treat share recipient text field in the share options view …
claucambra Mar 6, 2024
d0195e6
Properly handle failure state when creating new share in share option…
claucambra Mar 6, 2024
d12cdeb
Reset newly added fields in ShareOptionsView correctly
claucambra Mar 6, 2024
4be8bac
Adapt visibility of password field upon toggling password checkbox
claucambra Mar 6, 2024
f1adfcf
Adapt visibility of expiration date field upon toggling checkbox
claucambra Mar 6, 2024
b237066
Adapt visibility of note recipient text field upon toggling checkbox
claucambra Mar 12, 2024
2d0cdb3
Add ShareCapabilities struct
claucambra Mar 13, 2024
15651f6
Restructure ShareCapabilities
claucambra Mar 13, 2024
1e811fe
Add initialiser from dictionary for EmailCapabilities
claucambra Mar 13, 2024
3ffcd6d
Add init for public link capabilities
claucambra Mar 18, 2024
8039fcd
Add init for ShareCapabilities
claucambra Mar 18, 2024
cfd8c00
Fetch sharing capabilities in ShareTableViewDataSource
claucambra Mar 18, 2024
3bfbb38
Do not bother fetching shares if sharing is disabled on server
claucambra Mar 18, 2024
b074d19
Extract conversion of picked menu item in share type picker into NKSh…
claucambra Mar 18, 2024
b7541fc
Update reset to make sure it also resets min and max dates in date pi…
claucambra Mar 18, 2024
ce1bf89
Setup the fields in share options view when creating a new form accor…
claucambra Mar 18, 2024
3bb6f43
Update form layout according to picked type when picked type changed
claucambra Mar 18, 2024
7be5541
Fix password capabilities for public link capabilities
claucambra Mar 18, 2024
4930304
Fix ShareCapabilities parsing
claucambra Mar 18, 2024
3e7cde6
Fix default states around passwords for share options view
claucambra Mar 18, 2024
f7dba3e
Add more debug logging to sharecapabilities
claucambra Mar 18, 2024
4d3e630
Add method to ShareTableViewDataSource to fetch the given item's meta…
claucambra Mar 19, 2024
65db197
Check if the given item is shareable before fetching shares
claucambra Mar 19, 2024
9621ded
Ensure interpolated logging string in share table view data source is…
claucambra Mar 19, 2024
807371e
Fix scan path to retrieve item metadata in share table view data source
claucambra Mar 19, 2024
d2242ea
Fix letter used to identify shareability in sharetableviewdatasource
claucambra Mar 19, 2024
bab3b41
Fix options view disappearing when clicking create button in share vi…
claucambra Mar 19, 2024
1f3d636
Deduplicate error presentation in ShareTableViewDataSource
claucambra Mar 19, 2024
e54652b
Retry getting information from FileProviderExt if doing so has failed…
claucambra Mar 19, 2024
ca94b45
Add package dependency NextcloudCapabilitiesKit to NextcloudIntegration
claucambra Mar 19, 2024
d6e67a1
Add SuggestionsTextFieldKit dependency
claucambra Apr 2, 2024
74cea5e
Add basic shareesuggestionsdatasource
claucambra Apr 2, 2024
3012976
Add sharee fetcher method to shareesuggestionsdatasource
claucambra Apr 2, 2024
ad43c13
Add converter method fro nksharee to suggestion
claucambra Apr 2, 2024
c91d582
Update suggestions on inputString change in sharee suggestions data s…
claucambra Apr 2, 2024
798e060
Post suggestions changed notification in ShareeSuggestionsDataSource
claucambra Apr 3, 2024
07b6391
Improve logging in ShareeSuggestionsDataSource
claucambra Apr 3, 2024
db20e44
Use suggestions window controller in share options view
claucambra Apr 3, 2024
66f7723
Fix suggestion labels for sharees
claucambra Apr 6, 2024
4464f7e
Simplify configuration of text field delegate
claucambra Apr 6, 2024
395cf96
Fix SuggestionsTextFieldKit import
claucambra Apr 6, 2024
af2b2e7
Clean up TODO comments in file provider ui ext
claucambra Apr 6, 2024
1285b02
Set suggestionstextfieldkit to 1.0.0
claucambra Apr 6, 2024
cfda22c
Pin NextcloudKit version
claucambra Apr 6, 2024
beedbbb
Pin NextcloudCapabilitiesKit version
claucambra Apr 6, 2024
5070c37
Display shareWith in nkshare displaystring extension
claucambra Apr 6, 2024
3bdb1ca
Update description label in share view
claucambra Apr 6, 2024
1beb043
Add a "no shares" label if there are no shares available in share view
claucambra Apr 6, 2024
5e80827
Upgrade NextcloudCapabilitiesKit version
claucambra Apr 8, 2024
206d7cf
Allow SuggestionsTextFieldKit to use up to next major version
claucambra Apr 15, 2024
d066536
Set file provider extension target as a dependency of file provider u…
claucambra Apr 17, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 18 additions & 1 deletion shell_integration/MacOSX/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,20 @@ if(APPLE)
COMMENT building macOS File Provider extension
VERBATIM)

add_dependencies(mac_overlayplugin mac_fileproviderplugin nextcloud) # for the ownCloud.icns to be generated
add_custom_target( mac_fileprovideruiplugin ALL
xcodebuild ARCHS=${CMAKE_OSX_ARCHITECTURES} ONLY_ACTIVE_ARCH=NO
-project ${CMAKE_SOURCE_DIR}/shell_integration/MacOSX/NextcloudIntegration/NextcloudIntegration.xcodeproj
-target FileProviderUIExt -configuration ${XCODE_TARGET_CONFIGURATION} "SYMROOT=${CMAKE_CURRENT_BINARY_DIR}"
"OC_APPLICATION_EXECUTABLE_NAME=${APPLICATION_EXECUTABLE}"
"OC_APPLICATION_VENDOR=${APPLICATION_VENDOR}"
"OC_APPLICATION_NAME=${APPLICATION_NAME}"
"OC_APPLICATION_REV_DOMAIN=${APPLICATION_REV_DOMAIN}"
"OC_SOCKETAPI_TEAM_IDENTIFIER_PREFIX=${SOCKETAPI_TEAM_IDENTIFIER_PREFIX}"
DEPENDS mac_fileproviderplugin
COMMENT building macOS File Provider UI extension
VERBATIM)

add_dependencies(mac_overlayplugin mac_fileproviderplugin mac_fileprovideruiplugin nextcloud) # for the ownCloud.icns to be generated
else()
add_dependencies(mac_overlayplugin nextcloud) # for the ownCloud.icns to be generated
endif()
Expand All @@ -55,6 +68,10 @@ if(APPLE)
install(DIRECTORY ${OSX_PLUGINS_BINARY_DIR}/FileProviderExt.appex
DESTINATION ${OSX_PLUGINS_INSTALL_DIR}
USE_SOURCE_PERMISSIONS)

install(DIRECTORY ${OSX_PLUGINS_BINARY_DIR}/FileProviderUIExt.appex
DESTINATION ${OSX_PLUGINS_INSTALL_DIR}
USE_SOURCE_PERMISSIONS)
endif()
endif()
endif()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,12 +19,15 @@ extension Logger {

static let desktopClientConnection = Logger(
subsystem: subsystem, category: "desktopclientconnection")
static let fpUiExtensionService = Logger(subsystem: subsystem, category: "fpUiExtensionService")
static let enumeration = Logger(subsystem: subsystem, category: "enumeration")
static let fileProviderExtension = Logger(
subsystem: subsystem, category: "fileproviderextension")
static let fileTransfer = Logger(subsystem: subsystem, category: "filetransfer")
static let localFileOps = Logger(subsystem: subsystem, category: "localfileoperations")
static let ncFilesDatabase = Logger(subsystem: subsystem, category: "nextcloudfilesdatabase")
static let shares = Logger(subsystem: subsystem, category: "shares")
static let ncAccount = Logger(subsystem: subsystem, category: "ncAccount")
static let materialisedFileHandling = Logger(
subsystem: subsystem, category: "materialisedfilehandling"
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,8 @@ extension FileProviderExtension: NSFileProviderServicing {
) -> Progress {
Logger.desktopClientConnection.debug("Serving supported service sources")
let clientCommService = ClientCommunicationService(fpExtension: self)
let services = [clientCommService]
let fpuiExtService = FPUIExtensionServiceSource(fpExtension: self)
let services: [NSFileProviderServiceSource] = [clientCommService, fpuiExtService]
completionHandler(services, nil)
let progress = Progress()
progress.cancellationHandler = {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,12 @@
import FileProvider
import Foundation

let ncAccountDictUsernameKey = "usernameKey"
let ncAccountDictPasswordKey = "passwordKey"
let ncAccountDictNcKitAccountKey = "ncKitAccountKey"
let ncAccountDictServerUrlKey = "serverUrlKey"
let ncAccountDictDavFilesUrlKey = "davFilesUrlKey"

struct NextcloudAccount: Equatable {
static let webDavFilesUrlSuffix: String = "/remote.php/dav/files/"
let username, password, ncKitAccount, serverUrl, davFilesUrl: String
Expand All @@ -26,4 +32,31 @@ struct NextcloudAccount: Equatable {
self.serverUrl = serverUrl
davFilesUrl = serverUrl + NextcloudAccount.webDavFilesUrlSuffix + user
}

init?(dictionary: Dictionary<String, String>) {
guard let username = dictionary[ncAccountDictUsernameKey],
let password = dictionary[ncAccountDictPasswordKey],
let ncKitAccount = dictionary[ncAccountDictNcKitAccountKey],
let serverUrl = dictionary[ncAccountDictServerUrlKey],
let davFilesUrl = dictionary[ncAccountDictDavFilesUrlKey]
else {
return nil
}

self.username = username
self.password = password
self.ncKitAccount = ncKitAccount
self.serverUrl = serverUrl
self.davFilesUrl = davFilesUrl
}

func dictionary() -> Dictionary<String, String> {
return [
ncAccountDictUsernameKey: username,
ncAccountDictPasswordKey: password,
ncAccountDictNcKitAccountKey: ncKitAccount,
ncAccountDictServerUrlKey: serverUrl,
ncAccountDictDavFilesUrlKey: davFilesUrl
]
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
//
// FPUIExtensionCommunicationProtocol.swift
// FileProviderExt
//
// Created by Claudio Cambra on 21/2/24.
//

import FileProvider
import NextcloudKit

let fpUiExtensionServiceName = NSFileProviderServiceName(
"com.nextcloud.desktopclient.FPUIExtensionService"
)

@objc protocol FPUIExtensionService {
func credentials() async -> NSDictionary
func itemServerPath(identifier: NSFileProviderItemIdentifier) async -> NSString?
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
//
// FPUIExtensionCommunicationService.swift
// FileProviderExt
//
// Created by Claudio Cambra on 21/2/24.
//

import FileProvider
import Foundation
import NextcloudKit
import OSLog

class FPUIExtensionServiceSource: NSObject, NSFileProviderServiceSource, NSXPCListenerDelegate, FPUIExtensionService {
let listener = NSXPCListener.anonymous()
let serviceName = fpUiExtensionServiceName
let fpExtension: FileProviderExtension

init(fpExtension: FileProviderExtension) {
Logger.fpUiExtensionService.debug("Instantiating FPUIExtensionService service")
self.fpExtension = fpExtension
super.init()
}

func makeListenerEndpoint() throws -> NSXPCListenerEndpoint {
listener.delegate = self
listener.resume()
return listener.endpoint
}

func listener(
_ listener: NSXPCListener,
shouldAcceptNewConnection newConnection: NSXPCConnection
) -> Bool {
newConnection.exportedInterface = NSXPCInterface(with: FPUIExtensionService.self)
newConnection.exportedObject = self
newConnection.resume()
return true
}

//MARK: - FPUIExtensionService protocol methods

func credentials() async -> NSDictionary {
return (fpExtension.ncAccount?.dictionary() ?? [:]) as NSDictionary
}

func itemServerPath(identifier: NSFileProviderItemIdentifier) async -> NSString? {
let rawIdentifier = identifier.rawValue
Logger.shares.info("Fetching shares for item \(rawIdentifier, privacy: .public)")

guard let baseUrl = fpExtension.ncAccount?.davFilesUrl else {
Logger.shares.error("Could not fetch shares as ncAccount on parent extension is nil")
return nil
}

let dbManager = NextcloudFilesDatabaseManager.shared
guard let item = dbManager.itemMetadataFromFileProviderItemIdentifier(identifier) else {
Logger.shares.error("No item \(rawIdentifier, privacy: .public) in db, no shares.")
return nil
}

let completePath = item.serverUrl + "/" + item.fileName
return completePath.replacingOccurrences(of: baseUrl, with: "") as NSString
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
//
// DocumentActionViewController.swift
// FileProviderUIExt
//
// Created by Claudio Cambra on 20/2/24.
//

import FileProviderUI
import OSLog

class DocumentActionViewController: FPUIActionExtensionViewController {
var domain: NSFileProviderDomain {
guard let identifier = extensionContext.domainIdentifier else {
fatalError("not expected to be called with default domain")
}
return NSFileProviderDomain(
identifier: NSFileProviderDomainIdentifier(rawValue: identifier.rawValue),
displayName: ""
)
}

func prepare(childViewController: NSViewController) {
addChild(childViewController)
view.addSubview(childViewController.view)

NSLayoutConstraint.activate([
view.leadingAnchor.constraint(equalTo: childViewController.view.leadingAnchor),
view.trailingAnchor.constraint(equalTo: childViewController.view.trailingAnchor),
view.topAnchor.constraint(equalTo: childViewController.view.topAnchor),
view.bottomAnchor.constraint(equalTo: childViewController.view.bottomAnchor)
])
}

override func prepare(
forAction actionIdentifier: String, itemIdentifiers: [NSFileProviderItemIdentifier]
) {
Logger.actionViewController.info("Preparing for action: \(actionIdentifier)")

if actionIdentifier == "com.nextcloud.desktopclient.FileProviderUIExt.ShareAction" {
prepare(childViewController: ShareViewController(itemIdentifiers))
}

}

override func prepare(forError error: Error) {
Logger.actionViewController.info("Preparing for error: \(error.localizedDescription)")
}

override public func loadView() {
self.view = NSView()
}
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
//
// Logger+Extensions.swift
// FileProviderUIExt
//
// Created by Claudio Cambra on 21/2/24.
//

import OSLog

extension Logger {
private static var subsystem = Bundle.main.bundleIdentifier!

static let actionViewController = Logger(subsystem: subsystem, category: "actionViewController")
static let shareCapabilities = Logger(subsystem: subsystem, category: "shareCapabilities")
static let shareController = Logger(subsystem: subsystem, category: "shareController")
static let shareeDataSource = Logger(subsystem: subsystem, category: "shareeDataSource")
static let sharesDataSource = Logger(subsystem: subsystem, category: "sharesDataSource")
static let shareOptionsView = Logger(subsystem: subsystem, category: "shareOptionsView")
static let shareViewController = Logger(subsystem: subsystem, category: "shareViewController")
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,130 @@
//
// NKShare+Extensions.swift
// FileProviderUIExt
//
// Created by Claudio Cambra on 28/2/24.
//

import AppKit
import NextcloudKit

extension NKShare {
enum ShareType: Int {
case user = 0
case group = 1
case publicLink = 3
case email = 4
case federatedCloud = 6
case circle = 7
case talkConversation = 10
}

enum PermissionValues: Int {
case readShare = 1
case updateShare = 2
case createShare = 4
case deleteShare = 8
case shareShare = 16
case all = 31
}

var typeImage: NSImage? {
var image: NSImage?
switch shareType {
case ShareType.user.rawValue:
image = NSImage(
systemSymbolName: "person.circle.fill",
accessibilityDescription: "User share icon"
)
case ShareType.group.rawValue:
image = NSImage(
systemSymbolName: "person.2.circle.fill",
accessibilityDescription: "Group share icon"
)
case ShareType.publicLink.rawValue:
image = NSImage(
systemSymbolName: "link.circle.fill",
accessibilityDescription: "Public link share icon"
)
case ShareType.email.rawValue:
image = NSImage(
systemSymbolName: "envelope.circle.fill",
accessibilityDescription: "Email share icon"
)
case ShareType.federatedCloud.rawValue:
image = NSImage(
systemSymbolName: "cloud.circle.fill",
accessibilityDescription: "Federated cloud share icon"
)
case ShareType.circle.rawValue:
image = NSImage(
systemSymbolName: "circle.circle.fill",
accessibilityDescription: "Circle share icon"
)
case ShareType.talkConversation.rawValue:
image = NSImage(
systemSymbolName: "message.circle.fill",
accessibilityDescription: "Talk conversation share icon"
)
default:
return nil
}

var config = NSImage.SymbolConfiguration(textStyle: .body, scale: .large)
if #available(macOS 12.0, *) {
config = config.applying(
.init(paletteColors: [.controlBackgroundColor, .controlAccentColor])
)
}
return image?.withSymbolConfiguration(config)
}

var displayString: String {
if label != "" {
return label
}

switch shareType {
case ShareType.user.rawValue:
return "User share (\(shareWith))"
case ShareType.group.rawValue:
return "Group share (\(shareWith))"
case ShareType.publicLink.rawValue:
return "Public link share"
case ShareType.email.rawValue:
return "Email share (\(shareWith))"
case ShareType.federatedCloud.rawValue:
return "Federated cloud share (\(shareWith))"
case ShareType.circle.rawValue:
return "Circle share (\(shareWith))"
case ShareType.talkConversation.rawValue:
return "Talk conversation share (\(shareWith))"
default:
return "Unknown share"
}
}

var expirationDateString: String? {
guard let date = expirationDate else { return nil }
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "YYYY-MM-dd HH:mm:ss"
return dateFormatter.string(from: date as Date)
}

var shareesCanEdit: Bool {
get { (permissions & PermissionValues.updateShare.rawValue) != 0 }
set {
if newValue {
permissions |= NKShare.PermissionValues.updateShare.rawValue
} else {
permissions &= ~NKShare.PermissionValues.updateShare.rawValue
}
}
}

static func formattedDateString(date: Date) -> String {
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "YYYY-MM-dd HH:mm:ss"
return dateFormatter.string(from: date)
}
}
Loading
Loading