浏览代码

Merge pull request #2440 from nextcloud/fix/tags

Fix - Improvements
Marino Faggiana 1 年之前
父节点
当前提交
dee1297d50
共有 49 个文件被更改,包括 573 次插入1505 次删除
  1. 1 0
      .swiftlint.yml
  2. 24 29
      Brand/NCBrand.swift
  3. 6 5
      File Provider Extension/FileProviderData.swift
  4. 38 54
      Nextcloud.xcodeproj/project.pbxproj
  5. 0 54
      NextcloudTests/NCGlobalTests.swift
  6. 0 85
      NextcloudTests/ParallelWorkerTest.swift
  7. 0 136
      NextcloudTests/SharePermissionTest.swift
  8. 0 64
      NextcloudTests/UserAgentTests.swift
  9. 4 2
      Widget/Dashboard/DashboardData.swift
  10. 4 2
      Widget/Lockscreen/LockscreenData.swift
  11. 4 3
      iOSClient/AppDelegate.swift
  12. 0 10
      iOSClient/Data/NCDatabase.swift
  13. 0 75
      iOSClient/Data/NCElementsJSON.swift
  14. 136 0
      iOSClient/Data/NCManageDatabase+Capabilities.swift
  15. 15 13
      iOSClient/Data/NCManageDatabase+Metadata.swift
  16. 0 113
      iOSClient/Data/NCManageDatabase.swift
  17. 24 117
      iOSClient/Diagnostics/NCCapabilitiesView.swift
  18. 15 0
      iOSClient/Extensions/Data+Extension.swift
  19. 67 0
      iOSClient/Extensions/UILabel+Extension.swift
  20. 15 0
      iOSClient/Extensions/View+Extension.swift
  21. 3 3
      iOSClient/Main/Collection Common/NCCollectionViewCommon.swift
  22. 0 6
      iOSClient/Main/Collection Common/NCGridCell.swift
  23. 11 23
      iOSClient/Main/Collection Common/NCListCell.swift
  24. 86 45
      iOSClient/Main/Collection Common/NCListCell.xib
  25. 1 1
      iOSClient/Main/Collection Common/NCSelectableNavigationView.swift
  26. 0 457
      iOSClient/Main/Create cloud/NCCreateFormUploadAssets.swift
  27. 0 3
      iOSClient/Main/Create cloud/NCUploadAssets.swift
  28. 6 6
      iOSClient/Main/NCActionCenter.swift
  29. 0 6
      iOSClient/Main/NCCellProtocol.swift
  30. 3 12
      iOSClient/Main/NCPickerViewController.swift
  31. 3 4
      iOSClient/Menu/AppDelegate+Menu.swift
  32. 1 2
      iOSClient/Menu/NCCollectionViewCommon+Menu.swift
  33. 1 2
      iOSClient/Menu/UIViewController+Menu.swift
  34. 13 18
      iOSClient/More/NCMore.swift
  35. 37 0
      iOSClient/NCGlobal.swift
  36. 1 2
      iOSClient/Networking/E2EE/NCEndToEndMetadata.swift
  37. 1 3
      iOSClient/Networking/E2EE/NCNetworkingE2EE.swift
  38. 1 2
      iOSClient/Networking/NCNetworkingCheckRemoteUser.swift
  39. 12 20
      iOSClient/Networking/NCService.swift
  40. 2 6
      iOSClient/Scan document/NCUploadScanDocument.swift
  41. 1 85
      iOSClient/Settings/CCManageAccount.m
  42. 8 10
      iOSClient/Settings/NCManageE2EE.swift
  43. 10 8
      iOSClient/Settings/NCSettings.m
  44. 6 6
      iOSClient/Share/Advanced/NCShareCells.swift
  45. 1 1
      iOSClient/Share/NCShare+Helper.swift
  46. 1 2
      iOSClient/Share/NCShare.swift
  47. 6 1
      iOSClient/Share/NCSharePaging.swift
  48. 2 2
      iOSClient/Utility/CCUtility.m
  49. 3 7
      iOSClient/Utility/NCUtility.swift

+ 1 - 0
.swiftlint.yml

@@ -72,6 +72,7 @@ excluded:
   - iOSClient/Data/NCDataSource.swift
   - iOSClient/Data/NCDatabase.swift
   - iOSClient/Data/NCElementsJSON.swift
+  - iOSClient/Data/NCManageDatabase+Capabilities.swift
   - iOSClient/Data/NCManageDatabase+Account.swift
   - iOSClient/Data/NCManageDatabase+Activity.swift
   - iOSClient/Data/NCManageDatabase+Avatar.swift

+ 24 - 29
Brand/NCBrand.swift

@@ -251,46 +251,41 @@ class NCBrandColor: NSObject {
 
         if NCBrandOptions.shared.use_themingColor {
 
-            if let themingColor = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesThemingColor),
-               let themingColorElement = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesThemingColorElement),
-               let themingColorText = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesThemingColorText) {
-
-                self.themingColor = themingColor
-                self.themingColorElement = themingColorElement
-                self.themingColorText = themingColorText
-                
-                // COLOR
-                if themingColor.first == "#" {
-                    if let color = UIColor(hex: themingColor) {
-                        brand = color
-                    } else {
-                        brand = customer
-                    }
+            self.themingColor = NCGlobal.shared.capabilityThemingColor
+            self.themingColorElement = NCGlobal.shared.capabilityThemingColorElement
+            self.themingColorText = NCGlobal.shared.capabilityThemingColorText
+
+            // COLOR
+            if themingColor.first == "#" {
+                if let color = UIColor(hex: themingColor) {
+                    brand = color
                 } else {
                     brand = customer
                 }
+            } else {
+                brand = customer
+            }
 
-                // COLOR TEXT
-                if themingColorText.first == "#" {
-                    if let color = UIColor(hex: themingColorText) {
-                        brandText = color
-                    } else {
-                        brandText = customerText
-                    }
+            // COLOR TEXT
+            if themingColorText.first == "#" {
+                if let color = UIColor(hex: themingColorText) {
+                    brandText = color
                 } else {
                     brandText = customerText
                 }
+            } else {
+                brandText = customerText
+            }
 
-                // COLOR ELEMENT
-                if themingColorElement.first == "#" {
-                    if let color = UIColor(hex: themingColorElement) {
-                        brandElement = color
-                    } else {
-                        brandElement = brand
-                    }
+            // COLOR ELEMENT
+            if themingColorElement.first == "#" {
+                if let color = UIColor(hex: themingColorElement) {
+                    brandElement = color
                 } else {
                     brandElement = brand
                 }
+            } else {
+                brandElement = brand
             }
 
             if brandElement.isTooLight() {

+ 6 - 5
File Provider Extension/FileProviderData.swift

@@ -84,7 +84,6 @@ class fileProviderData: NSObject {
         if domain == nil {
 
             guard let activeAccount = NCManageDatabase.shared.getActiveAccount() else { return nil }
-            let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: activeAccount.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
 
             account = activeAccount.account
             user = activeAccount.user
@@ -92,7 +91,9 @@ class fileProviderData: NSObject {
             accountUrlBase = activeAccount.urlBase
             homeServerUrl = NCUtilityFileSystem.shared.getHomeServer(urlBase: activeAccount.urlBase, userId: activeAccount.userId)
 
-            NextcloudKit.shared.setup(account: activeAccount.account, user: activeAccount.user, userId: activeAccount.userId, password: CCUtility.getPassword(activeAccount.account), urlBase: activeAccount.urlBase, userAgent: CCUtility.getUserAgent(), nextcloudVersion: serverVersionMajor, delegate: NCNetworking.shared)
+            NCManageDatabase.shared.setCapabilities(account: account)
+
+            NextcloudKit.shared.setup(account: activeAccount.account, user: activeAccount.user, userId: activeAccount.userId, password: CCUtility.getPassword(activeAccount.account), urlBase: activeAccount.urlBase, userAgent: CCUtility.getUserAgent(), nextcloudVersion: NCGlobal.shared.capabilityServerVersionMajor, delegate: NCNetworking.shared)
             NCNetworking.shared.delegate = providerExtension as? NCNetworkingDelegate
 
             return tableAccount.init(value: activeAccount)
@@ -108,15 +109,15 @@ class fileProviderData: NSObject {
             let accountDomain = activeAccount.userId + " (" + host + ")"
             if accountDomain == domain!.identifier.rawValue {
 
-                let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: activeAccount.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-
                 account = activeAccount.account
                 user = activeAccount.user
                 userId = activeAccount.userId
                 accountUrlBase = activeAccount.urlBase
                 homeServerUrl = NCUtilityFileSystem.shared.getHomeServer(urlBase: activeAccount.urlBase, userId: activeAccount.userId)
 
-                NextcloudKit.shared.setup(account: activeAccount.account, user: activeAccount.user, userId: activeAccount.userId, password: CCUtility.getPassword(activeAccount.account), urlBase: activeAccount.urlBase, userAgent: CCUtility.getUserAgent(), nextcloudVersion: serverVersionMajor, delegate: NCNetworking.shared)
+                NCManageDatabase.shared.setCapabilities(account: account)
+
+                NextcloudKit.shared.setup(account: activeAccount.account, user: activeAccount.user, userId: activeAccount.userId, password: CCUtility.getPassword(activeAccount.account), urlBase: activeAccount.urlBase, userAgent: CCUtility.getUserAgent(), nextcloudVersion: NCGlobal.shared.capabilityServerVersionMajor, delegate: NCNetworking.shared)
                 NCNetworking.shared.delegate = providerExtension as? NCNetworkingDelegate
 
                 return tableAccount.init(value: activeAccount)

+ 38 - 54
Nextcloud.xcodeproj/project.pbxproj

@@ -29,8 +29,6 @@
 		AF2D7C7C2742556F00ADF566 /* NCShareLinkCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF2D7C7B2742556F00ADF566 /* NCShareLinkCell.swift */; };
 		AF2D7C7E2742559100ADF566 /* NCShareUserCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF2D7C7D2742559100ADF566 /* NCShareUserCell.swift */; };
 		AF36077127BFA4E8001A243D /* ParallelWorker.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF36077027BFA4E8001A243D /* ParallelWorker.swift */; };
-		AF36077627BFB019001A243D /* ParallelWorkerTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF36077527BFB019001A243D /* ParallelWorkerTest.swift */; };
-		AF3F909A28213BEA0048A93E /* UserAgentTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF3F909928213BEA0048A93E /* UserAgentTests.swift */; };
 		AF3FDCC22796ECC300710F60 /* NCTrash+CollectionView.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF3FDCC12796ECC300710F60 /* NCTrash+CollectionView.swift */; };
 		AF3FDCC32796F3FB00710F60 /* NCTrashListCell+NCTrashCellProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = F78ACD4821903F850088454D /* NCTrashListCell+NCTrashCellProtocol.swift */; };
 		AF4BF614275629E20081CEEF /* NCManageDatabase+Account.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF4BF613275629E20081CEEF /* NCManageDatabase+Account.swift */; };
@@ -47,7 +45,6 @@
 		AF4BF62127562B3F0081CEEF /* NCManageDatabase+Activity.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF4BF61D27562B3F0081CEEF /* NCManageDatabase+Activity.swift */; };
 		AF56C1DC2784856200D8BAE2 /* NCActivityCommentView.xib in Resources */ = {isa = PBXBuildFile; fileRef = AF56C1DB2784856200D8BAE2 /* NCActivityCommentView.xib */; };
 		AF68326A27BE65A90010BF0B /* NCMenuAction.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF68326927BE65A90010BF0B /* NCMenuAction.swift */; };
-		AF70C14D27F3484D00E13DF2 /* SharePermissionTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF70C14C27F3484D00E13DF2 /* SharePermissionTest.swift */; };
 		AF730AF827834B1400B7520E /* NCShare+NCCellDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF730AF727834B1400B7520E /* NCShare+NCCellDelegate.swift */; };
 		AF730AFA27843E4C00B7520E /* NCShareExtension+NCDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF730AF927843E4C00B7520E /* NCShareExtension+NCDelegate.swift */; };
 		AF7E504E27A2D8FF00B5E4AF /* UIBarButton+Extension.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF7E504D27A2D8FF00B5E4AF /* UIBarButton+Extension.swift */; };
@@ -57,7 +54,6 @@
 		AF817EF3274BC781009ED85B /* NCUserBaseUrl.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF817EF0274BC781009ED85B /* NCUserBaseUrl.swift */; };
 		AF817EF4274BC781009ED85B /* NCUserBaseUrl.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF817EF0274BC781009ED85B /* NCUserBaseUrl.swift */; };
 		AF8ED1FC2757821000B8DBC4 /* NextcloudTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF8ED1FB2757821000B8DBC4 /* NextcloudTests.swift */; };
-		AF8ED2032757822700B8DBC4 /* NCGlobalTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF8ED2022757822700B8DBC4 /* NCGlobalTests.swift */; };
 		AF93471227E2341B002537EE /* NCShare+Menu.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF93471127E2341B002537EE /* NCShare+Menu.swift */; };
 		AF93471927E2361E002537EE /* NCShareAdvancePermissionFooter.xib in Resources */ = {isa = PBXBuildFile; fileRef = AF93471427E2361E002537EE /* NCShareAdvancePermissionFooter.xib */; };
 		AF93471A27E2361E002537EE /* NCShareAdvancePermissionHeader.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF93471527E2361E002537EE /* NCShareAdvancePermissionHeader.swift */; };
@@ -213,10 +209,6 @@
 		F73B422C2476764F00A30FD3 /* NCNotification.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73B422A2476764F00A30FD3 /* NCNotification.swift */; };
 		F73CB3B222E072A000AD728E /* NCShareHeaderView.xib in Resources */ = {isa = PBXBuildFile; fileRef = F73CB3B122E072A000AD728E /* NCShareHeaderView.xib */; };
 		F73D11FA253C5F4800DF9BEC /* NCViewerNextcloudText.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = F73D11F9253C5F4800DF9BEC /* NCViewerNextcloudText.storyboard */; };
-		F73D5E47246DE09200DF6467 /* NCElementsJSON.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */; };
-		F73D5E48246DE09200DF6467 /* NCElementsJSON.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */; };
-		F73D5E49246DE09200DF6467 /* NCElementsJSON.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */; };
-		F73D5E4A246DE09200DF6467 /* NCElementsJSON.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */; };
 		F73F537F1E929C8500F8678D /* NCMore.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73F537E1E929C8500F8678D /* NCMore.swift */; };
 		F7434B3420E23FD700417916 /* NCDatabase.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7BAADB41ED5A87C00B7EAD4 /* NCDatabase.swift */; };
 		F7434B3620E23FE000417916 /* NCManageDatabase.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7BAADB51ED5A87C00B7EAD4 /* NCManageDatabase.swift */; };
@@ -238,7 +230,6 @@
 		F7490E7629882BF3009DCE94 /* NCUserBaseUrl.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF817EF0274BC781009ED85B /* NCUserBaseUrl.swift */; };
 		F7490E7729882C10009DCE94 /* UIColor+Extension.swift in Sources */ = {isa = PBXBuildFile; fileRef = F70CEF5523E9C7E50007035B /* UIColor+Extension.swift */; };
 		F7490E7829882C28009DCE94 /* NCUtility.swift in Sources */ = {isa = PBXBuildFile; fileRef = F70BFC7320E0FA7C00C67599 /* NCUtility.swift */; };
-		F7490E7929882C2F009DCE94 /* NCElementsJSON.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */; };
 		F7490E7E29882C6E009DCE94 /* NCManageDatabase+Account.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF4BF613275629E20081CEEF /* NCManageDatabase+Account.swift */; };
 		F7490E7F29882C73009DCE94 /* NCManageDatabase+Activity.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF4BF61D27562B3F0081CEEF /* NCManageDatabase+Activity.swift */; };
 		F7490E8029882C76009DCE94 /* NCManageDatabase+Avatar.swift in Sources */ = {isa = PBXBuildFile; fileRef = F749B650297B0F2400087535 /* NCManageDatabase+Avatar.swift */; };
@@ -254,7 +245,6 @@
 		F7490E8C29882D02009DCE94 /* CCUtility.m in Sources */ = {isa = PBXBuildFile; fileRef = F7053E3D1C639DF500741EA5 /* CCUtility.m */; };
 		F7490E8D29882F5B009DCE94 /* Custom.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = F700222B1EC479840080073F /* Custom.xcassets */; };
 		F7490E8E2988334A009DCE94 /* Localizable.strings in Resources */ = {isa = PBXBuildFile; fileRef = F7E70DE91A24DE4100E1B66A /* Localizable.strings */; };
-		F7490E902988F0C2009DCE94 /* NCCreateFormUploadAssets.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7490E8F2988F0C2009DCE94 /* NCCreateFormUploadAssets.swift */; };
 		F749B64A297B0CBB00087535 /* NCManageDatabase+Share.swift in Sources */ = {isa = PBXBuildFile; fileRef = F749B649297B0CBB00087535 /* NCManageDatabase+Share.swift */; };
 		F749B64B297B0CBB00087535 /* NCManageDatabase+Share.swift in Sources */ = {isa = PBXBuildFile; fileRef = F749B649297B0CBB00087535 /* NCManageDatabase+Share.swift */; };
 		F749B64C297B0CBB00087535 /* NCManageDatabase+Share.swift in Sources */ = {isa = PBXBuildFile; fileRef = F749B649297B0CBB00087535 /* NCManageDatabase+Share.swift */; };
@@ -313,6 +303,13 @@
 		F761856B29E98543006EB3B0 /* NCIntroViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = F761856729E98543006EB3B0 /* NCIntroViewController.swift */; };
 		F761856C29E98543006EB3B0 /* NCIntroCollectionViewCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = F761856829E98543006EB3B0 /* NCIntroCollectionViewCell.swift */; };
 		F761856D29E98543006EB3B0 /* NCIntroCollectionViewCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = F761856929E98543006EB3B0 /* NCIntroCollectionViewCell.xib */; };
+		F763D29D2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */; };
+		F763D29E2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */; };
+		F763D29F2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */; };
+		F763D2A02A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */; };
+		F763D2A12A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */; };
+		F763D2A22A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */; };
+		F763D2A32A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */; };
 		F7651A8A23A2A3F2001403D2 /* NCCreateFormUploadDocuments.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = F7651A8823A2A3F2001403D2 /* NCCreateFormUploadDocuments.storyboard */; };
 		F7651A8B23A2A3F2001403D2 /* NCCreateFormUploadDocuments.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7651A8923A2A3F2001403D2 /* NCCreateFormUploadDocuments.swift */; };
 		F765608F23BF813600765969 /* NCContentPresenter.swift in Sources */ = {isa = PBXBuildFile; fileRef = F765608E23BF813500765969 /* NCContentPresenter.swift */; };
@@ -409,7 +406,6 @@
 		F78302F928B4C3E600B84583 /* NCManageDatabase+Account.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF4BF613275629E20081CEEF /* NCManageDatabase+Account.swift */; };
 		F78302FA28B4C3EA00B84583 /* NCManageDatabase+Metadata.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF4BF61827562A4B0081CEEF /* NCManageDatabase+Metadata.swift */; };
 		F78302FB28B4C3EE00B84583 /* NCManageDatabase+Video.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7E98C1527E0D0FC001F9F19 /* NCManageDatabase+Video.swift */; };
-		F78302FC28B4C3F300B84583 /* NCElementsJSON.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */; };
 		F78302FD28B4C42B00B84583 /* NCUserBaseUrl.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF817EF0274BC781009ED85B /* NCUserBaseUrl.swift */; };
 		F78302FE28B4C44700B84583 /* NCBrand.swift in Sources */ = {isa = PBXBuildFile; fileRef = F76B3CCD1EAE01BD00921AC9 /* NCBrand.swift */; };
 		F78302FF28B4C45000B84583 /* NCUtilityFileSystem.swift in Sources */ = {isa = PBXBuildFile; fileRef = F74AF3A3247FB6AE00AC767B /* NCUtilityFileSystem.swift */; };
@@ -502,7 +498,6 @@
 		F7A8D73828F17E21008BBE1C /* NCManageDatabase+DashboardWidget.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7D68FCB28CB9051009139F3 /* NCManageDatabase+DashboardWidget.swift */; };
 		F7A8D73928F17E25008BBE1C /* NCManageDatabase+Metadata.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF4BF61827562A4B0081CEEF /* NCManageDatabase+Metadata.swift */; };
 		F7A8D73A28F17E28008BBE1C /* NCManageDatabase+Video.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7E98C1527E0D0FC001F9F19 /* NCManageDatabase+Video.swift */; };
-		F7A8D73B28F17E2C008BBE1C /* NCElementsJSON.swift in Sources */ = {isa = PBXBuildFile; fileRef = F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */; };
 		F7A8D73C28F181BC008BBE1C /* NCBrand.swift in Sources */ = {isa = PBXBuildFile; fileRef = F76B3CCD1EAE01BD00921AC9 /* NCBrand.swift */; };
 		F7A8D73D28F181D3008BBE1C /* NCUtilityFileSystem.swift in Sources */ = {isa = PBXBuildFile; fileRef = F74AF3A3247FB6AE00AC767B /* NCUtilityFileSystem.swift */; };
 		F7A8D73E28F181E2008BBE1C /* NCUserBaseUrl.swift in Sources */ = {isa = PBXBuildFile; fileRef = AF817EF0274BC781009ED85B /* NCUserBaseUrl.swift */; };
@@ -592,6 +587,7 @@
 		F7EDE509262DA9D600414FE6 /* NCSelectCommandViewSelect.xib in Resources */ = {isa = PBXBuildFile; fileRef = F7EDE508262DA9D600414FE6 /* NCSelectCommandViewSelect.xib */; };
 		F7EDE514262DC2CD00414FE6 /* NCSelectCommandViewSelect+CreateFolder.xib in Resources */ = {isa = PBXBuildFile; fileRef = F7EDE513262DC2CD00414FE6 /* NCSelectCommandViewSelect+CreateFolder.xib */; };
 		F7EDE51B262DD0C400414FE6 /* NCSelectCommandViewCopyMove.xib in Resources */ = {isa = PBXBuildFile; fileRef = F7EDE51A262DD0C400414FE6 /* NCSelectCommandViewCopyMove.xib */; };
+		F7EE66AD2A20B226009AE765 /* UILabel+Extension.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7EE66AC2A20B226009AE765 /* UILabel+Extension.swift */; };
 		F7EFA47825ADBA500083159A /* NCViewerProviderContextMenu.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7EFA47725ADBA500083159A /* NCViewerProviderContextMenu.swift */; };
 		F7EFC0C6256BC77700461AAD /* NCMoreUserCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = F7EFC0C5256BC77700461AAD /* NCMoreUserCell.xib */; };
 		F7EFC0CD256BF8DD00461AAD /* NCUserStatus.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7EFC0CC256BF8DD00461AAD /* NCUserStatus.swift */; };
@@ -719,15 +715,12 @@
 		AF2D7C7B2742556F00ADF566 /* NCShareLinkCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCShareLinkCell.swift; sourceTree = "<group>"; };
 		AF2D7C7D2742559100ADF566 /* NCShareUserCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCShareUserCell.swift; sourceTree = "<group>"; };
 		AF36077027BFA4E8001A243D /* ParallelWorker.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ParallelWorker.swift; sourceTree = "<group>"; };
-		AF36077527BFB019001A243D /* ParallelWorkerTest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ParallelWorkerTest.swift; sourceTree = "<group>"; };
-		AF3F909928213BEA0048A93E /* UserAgentTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UserAgentTests.swift; sourceTree = "<group>"; };
 		AF3FDCC12796ECC300710F60 /* NCTrash+CollectionView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCTrash+CollectionView.swift"; sourceTree = "<group>"; };
 		AF4BF613275629E20081CEEF /* NCManageDatabase+Account.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCManageDatabase+Account.swift"; sourceTree = "<group>"; };
 		AF4BF61827562A4B0081CEEF /* NCManageDatabase+Metadata.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCManageDatabase+Metadata.swift"; sourceTree = "<group>"; };
 		AF4BF61D27562B3F0081CEEF /* NCManageDatabase+Activity.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCManageDatabase+Activity.swift"; sourceTree = "<group>"; };
 		AF56C1DB2784856200D8BAE2 /* NCActivityCommentView.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = NCActivityCommentView.xib; sourceTree = "<group>"; };
 		AF68326927BE65A90010BF0B /* NCMenuAction.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCMenuAction.swift; sourceTree = "<group>"; };
-		AF70C14C27F3484D00E13DF2 /* SharePermissionTest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SharePermissionTest.swift; sourceTree = "<group>"; };
 		AF730AF727834B1400B7520E /* NCShare+NCCellDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCShare+NCCellDelegate.swift"; sourceTree = "<group>"; };
 		AF730AF927843E4C00B7520E /* NCShareExtension+NCDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCShareExtension+NCDelegate.swift"; sourceTree = "<group>"; };
 		AF7E504D27A2D8FF00B5E4AF /* UIBarButton+Extension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "UIBarButton+Extension.swift"; sourceTree = "<group>"; };
@@ -735,7 +728,6 @@
 		AF817EF0274BC781009ED85B /* NCUserBaseUrl.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCUserBaseUrl.swift; sourceTree = "<group>"; };
 		AF8ED1F92757821000B8DBC4 /* NextcloudTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = NextcloudTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; };
 		AF8ED1FB2757821000B8DBC4 /* NextcloudTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NextcloudTests.swift; sourceTree = "<group>"; };
-		AF8ED2022757822700B8DBC4 /* NCGlobalTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCGlobalTests.swift; sourceTree = "<group>"; };
 		AF93471127E2341B002537EE /* NCShare+Menu.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCShare+Menu.swift"; sourceTree = "<group>"; };
 		AF93471427E2361E002537EE /* NCShareAdvancePermissionFooter.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = NCShareAdvancePermissionFooter.xib; sourceTree = "<group>"; };
 		AF93471527E2361E002537EE /* NCShareAdvancePermissionHeader.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = NCShareAdvancePermissionHeader.swift; sourceTree = "<group>"; };
@@ -902,14 +894,12 @@
 		F73CB3B122E072A000AD728E /* NCShareHeaderView.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = NCShareHeaderView.xib; sourceTree = "<group>"; };
 		F73CB5771ED46807005F2A5A /* NCBridgeSwift.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = NCBridgeSwift.h; sourceTree = "<group>"; };
 		F73D11F9253C5F4800DF9BEC /* NCViewerNextcloudText.storyboard */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; path = NCViewerNextcloudText.storyboard; sourceTree = "<group>"; };
-		F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCElementsJSON.swift; sourceTree = "<group>"; };
 		F73F537E1E929C8500F8678D /* NCMore.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = NCMore.swift; sourceTree = "<group>"; };
 		F7421EAE2294044B00C4B7C1 /* Accelerate.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Accelerate.framework; path = System/Library/Frameworks/Accelerate.framework; sourceTree = SDKROOT; };
 		F7434B5F20E2440600417916 /* FileProviderExtension-Bridging-Header.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "FileProviderExtension-Bridging-Header.h"; sourceTree = "<group>"; };
 		F745B250222D871800346520 /* QRCodeReader.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = QRCodeReader.framework; path = Carthage/Build/iOS/QRCodeReader.framework; sourceTree = "<group>"; };
 		F745B252222D88AE00346520 /* NCLoginQRCode.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCLoginQRCode.swift; sourceTree = "<group>"; };
 		F747BA1E22354D2000971601 /* NCCreateFormUploadVoiceNote.storyboard */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.storyboard; path = NCCreateFormUploadVoiceNote.storyboard; sourceTree = "<group>"; };
-		F7490E8F2988F0C2009DCE94 /* NCCreateFormUploadAssets.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = NCCreateFormUploadAssets.swift; sourceTree = "<group>"; };
 		F749B649297B0CBB00087535 /* NCManageDatabase+Share.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCManageDatabase+Share.swift"; sourceTree = "<group>"; };
 		F749B650297B0F2400087535 /* NCManageDatabase+Avatar.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "NCManageDatabase+Avatar.swift"; sourceTree = "<group>"; };
 		F74AF3A3247FB6AE00AC767B /* NCUtilityFileSystem.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCUtilityFileSystem.swift; sourceTree = "<group>"; };
@@ -952,6 +942,7 @@
 		F761856729E98543006EB3B0 /* NCIntroViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = NCIntroViewController.swift; sourceTree = "<group>"; };
 		F761856829E98543006EB3B0 /* NCIntroCollectionViewCell.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = NCIntroCollectionViewCell.swift; sourceTree = "<group>"; };
 		F761856929E98543006EB3B0 /* NCIntroCollectionViewCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = NCIntroCollectionViewCell.xib; sourceTree = "<group>"; };
+		F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "NCManageDatabase+Capabilities.swift"; sourceTree = "<group>"; };
 		F7651A8823A2A3F2001403D2 /* NCCreateFormUploadDocuments.storyboard */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.storyboard; path = NCCreateFormUploadDocuments.storyboard; sourceTree = "<group>"; };
 		F7651A8923A2A3F2001403D2 /* NCCreateFormUploadDocuments.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = NCCreateFormUploadDocuments.swift; sourceTree = "<group>"; };
 		F765608623BF806C00765969 /* QuickLayout.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = QuickLayout.framework; path = Carthage/Build/iOS/QuickLayout.framework; sourceTree = "<group>"; };
@@ -1238,6 +1229,7 @@
 		F7EDE508262DA9D600414FE6 /* NCSelectCommandViewSelect.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = NCSelectCommandViewSelect.xib; sourceTree = "<group>"; };
 		F7EDE513262DC2CD00414FE6 /* NCSelectCommandViewSelect+CreateFolder.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = "NCSelectCommandViewSelect+CreateFolder.xib"; sourceTree = "<group>"; };
 		F7EDE51A262DD0C400414FE6 /* NCSelectCommandViewCopyMove.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = NCSelectCommandViewCopyMove.xib; sourceTree = "<group>"; };
+		F7EE66AC2A20B226009AE765 /* UILabel+Extension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "UILabel+Extension.swift"; sourceTree = "<group>"; };
 		F7EFA47725ADBA500083159A /* NCViewerProviderContextMenu.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCViewerProviderContextMenu.swift; sourceTree = "<group>"; };
 		F7EFC0C5256BC77700461AAD /* NCMoreUserCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = NCMoreUserCell.xib; sourceTree = "<group>"; };
 		F7EFC0CC256BF8DD00461AAD /* NCUserStatus.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NCUserStatus.swift; sourceTree = "<group>"; };
@@ -1410,10 +1402,6 @@
 		AF8ED1FA2757821000B8DBC4 /* NextcloudTests */ = {
 			isa = PBXGroup;
 			children = (
-				AF8ED2022757822700B8DBC4 /* NCGlobalTests.swift */,
-				AF36077527BFB019001A243D /* ParallelWorkerTest.swift */,
-				AF70C14C27F3484D00E13DF2 /* SharePermissionTest.swift */,
-				AF3F909928213BEA0048A93E /* UserAgentTests.swift */,
 				AF8ED1FB2757821000B8DBC4 /* NextcloudTests.swift */,
 			);
 			path = NextcloudTests;
@@ -1887,32 +1875,33 @@
 		F7A0D14E259229FA008F8A13 /* Extensions */ = {
 			isa = PBXGroup;
 			children = (
+				F7AC1CAF28AB94490032D99F /* Array+Extension.swift */,
+				F7817CF729801A3500FFBC65 /* Data+Extension.swift */,
+				AFCE353427E4ED5900FEA6C2 /* DateFormatter+Extension.swift */,
 				F70460512499061800BB98A7 /* NotificationCenter+MainThread.swift */,
 				F79B869A265E19D40085C0E0 /* NSMutableAttributedString+Extension.swift */,
 				F78071071EDAB65800EAFFF6 /* NSNotificationCenter+MainThread.h */,
 				F78071081EDAB65800EAFFF6 /* NSNotificationCenter+MainThread.m */,
+				F343A4BA2A1E734600DDA874 /* Optional+Extensions.swift */,
+				F343A4B22A1E01FF00DDA874 /* PHAsset+Extension.swift */,
 				F7A0D1342591FBC5008F8A13 /* String+Extension.swift */,
-				F7817CF729801A3500FFBC65 /* Data+Extension.swift */,
-				AFD3323F276A02C000F5AE02 /* UIApplication+Extension.swift */,
-				AFCE353227E4ED1900FEA6C2 /* UIToolbar+Extension.swift */,
 				AF1A9B6327D0CA1E00F17A9E /* UIAlertController+Extension.swift */,
-				AFCE353427E4ED5900FEA6C2 /* DateFormatter+Extension.swift */,
+				AFD3323F276A02C000F5AE02 /* UIApplication+Extension.swift */,
 				AF7E504D27A2D8FF00B5E4AF /* UIBarButton+Extension.swift */,
 				F70CEF5523E9C7E50007035B /* UIColor+Extension.swift */,
 				F79B645F26CA661600838ACA /* UIControl+Extension.swift */,
-				F7AC1CAF28AB94490032D99F /* Array+Extension.swift */,
 				F7F4F10F27ECDC4A008676F9 /* UIDevice+Extension.swift */,
-				F77BB747289985270090FC19 /* UITabBarController+Extension.swift */,
-				F77BB745289984CA0090FC19 /* UIViewController+Extension.swift */,
-				F77BB7492899857B0090FC19 /* UINavigationController+Extension.swift */,
 				F7F4F11127ECDC52008676F9 /* UIFont+Extension.swift */,
-				F7E41315294A19B300839300 /* UIView+Extension.swift */,
-				F7E8A390295DC5E0006CB2D0 /* View+Extension.swift */,
 				F713FEFE2472764000214AF6 /* UIImage+animatedGIF.h */,
 				F713FEFF2472764100214AF6 /* UIImage+animatedGIF.m */,
 				F7B7504A2397D38E004E13EC /* UIImage+Extension.swift */,
-				F343A4B22A1E01FF00DDA874 /* PHAsset+Extension.swift */,
-				F343A4BA2A1E734600DDA874 /* Optional+Extensions.swift */,
+				F77BB7492899857B0090FC19 /* UINavigationController+Extension.swift */,
+				F77BB747289985270090FC19 /* UITabBarController+Extension.swift */,
+				AFCE353227E4ED1900FEA6C2 /* UIToolbar+Extension.swift */,
+				F7E41315294A19B300839300 /* UIView+Extension.swift */,
+				F77BB745289984CA0090FC19 /* UIViewController+Extension.swift */,
+				F7E8A390295DC5E0006CB2D0 /* View+Extension.swift */,
+				F7EE66AC2A20B226009AE765 /* UILabel+Extension.swift */,
 			);
 			path = Extensions;
 			sourceTree = "<group>";
@@ -1976,11 +1965,11 @@
 			children = (
 				F7BAADB41ED5A87C00B7EAD4 /* NCDatabase.swift */,
 				F7C1EEA425053A9C00866ACC /* NCDataSource.swift */,
-				F73D5E46246DE09200DF6467 /* NCElementsJSON.swift */,
 				F7BAADB51ED5A87C00B7EAD4 /* NCManageDatabase.swift */,
 				AF4BF613275629E20081CEEF /* NCManageDatabase+Account.swift */,
 				AF4BF61D27562B3F0081CEEF /* NCManageDatabase+Activity.swift */,
 				F749B650297B0F2400087535 /* NCManageDatabase+Avatar.swift */,
+				F763D29C2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift */,
 				F7D68FCB28CB9051009139F3 /* NCManageDatabase+DashboardWidget.swift */,
 				F78A10BE29322E8A008499B8 /* NCManageDatabase+Directory.swift */,
 				F72FD3B4297ED49A00075D28 /* NCManageDatabase+E2EE.swift */,
@@ -2125,7 +2114,6 @@
 			isa = PBXGroup;
 			children = (
 				F769CA162965AB7C00039397 /* NCUploadAssets.swift */,
-				F7490E8F2988F0C2009DCE94 /* NCCreateFormUploadAssets.swift */,
 				F704B5E22430AA6F00632F5F /* NCCreateFormUploadConflict.storyboard */,
 				F704B5E42430AA8000632F5F /* NCCreateFormUploadConflict.swift */,
 				F704B5E82430C0B800632F5F /* NCCreateFormUploadConflictCell.swift */,
@@ -2962,7 +2950,6 @@
 				D575039F27146F93008DC9DC /* String+Extension.swift in Sources */,
 				F769CA1A2966EA3C00039397 /* ComponentView.swift in Sources */,
 				F757CC8829E7F88B00F31428 /* NCManageDatabase+Groupfolders.swift in Sources */,
-				F73D5E4A246DE09200DF6467 /* NCElementsJSON.swift in Sources */,
 				F79B646326CA661600838ACA /* UIControl+Extension.swift in Sources */,
 				F78A10C429322E8A008499B8 /* NCManageDatabase+Directory.swift in Sources */,
 				F75CA1482962F13700B01130 /* HUDView.swift in Sources */,
@@ -2972,6 +2959,7 @@
 				F7817CFF29802D1A00FFBC65 /* NCPushNotificationEncryption.m in Sources */,
 				F798F0EC2588060A000DAFFD /* UIColor+Extension.swift in Sources */,
 				F343A4B92A1E084400DDA874 /* PHAsset+Extension.swift in Sources */,
+				F763D2A32A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */,
 				F749B656297B0F2400087535 /* NCManageDatabase+Avatar.swift in Sources */,
 				F782FDC424E6933900666099 /* NCUtility.swift in Sources */,
 			);
@@ -2981,11 +2969,7 @@
 			isa = PBXSourcesBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
-				AF70C14D27F3484D00E13DF2 /* SharePermissionTest.swift in Sources */,
-				AF3F909A28213BEA0048A93E /* UserAgentTests.swift in Sources */,
-				AF36077627BFB019001A243D /* ParallelWorkerTest.swift in Sources */,
 				AF8ED1FC2757821000B8DBC4 /* NextcloudTests.swift in Sources */,
-				AF8ED2032757822700B8DBC4 /* NCGlobalTests.swift in Sources */,
 				F78E2D6C29AF02DB0024D4F3 /* Database.swift in Sources */,
 				F7817CFE29801A3500FFBC65 /* Data+Extension.swift in Sources */,
 			);
@@ -3004,6 +2988,7 @@
 				F7490E6E29882B56009DCE94 /* NCBrand.swift in Sources */,
 				F7490E8129882C79009DCE94 /* NCManageDatabase+DashboardWidget.swift in Sources */,
 				F7490E8629882C99009DCE94 /* NCUtilityFileSystem.swift in Sources */,
+				F763D2A22A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */,
 				F343A4C02A1E734600DDA874 /* Optional+Extensions.swift in Sources */,
 				F7490E8529882C8C009DCE94 /* NCManageDatabase+Video.swift in Sources */,
 				F7490E8C29882D02009DCE94 /* CCUtility.m in Sources */,
@@ -3017,7 +3002,6 @@
 				F7490E6C29882AEA009DCE94 /* String+Extension.swift in Sources */,
 				F7490E6B29882A92009DCE94 /* NCGlobal.swift in Sources */,
 				F7490E7529882BE2009DCE94 /* NCManageDatabase+Directory.swift in Sources */,
-				F7490E7929882C2F009DCE94 /* NCElementsJSON.swift in Sources */,
 				F7490E8729882CA8009DCE94 /* ThreadSafeDictionary.swift in Sources */,
 				F757CC8729E7F88B00F31428 /* NCManageDatabase+Groupfolders.swift in Sources */,
 				F7490E8229882C80009DCE94 /* NCManageDatabase+E2EE.swift in Sources */,
@@ -3031,7 +3015,6 @@
 			buildActionMask = 2147483647;
 			files = (
 				F7245925289BB59100474787 /* ThreadSafeDictionary.swift in Sources */,
-				F73D5E48246DE09200DF6467 /* NCElementsJSON.swift in Sources */,
 				F7EDE4E5262D7BBE00414FE6 /* NCSectionHeaderFooter.swift in Sources */,
 				F7BF9D852934CA21009EE9A6 /* NCManageDatabase+LayoutForView.swift in Sources */,
 				F79EC78926316AC4004E59D6 /* NCPopupViewController.swift in Sources */,
@@ -3076,6 +3059,7 @@
 				F7EDE4E0262D7BAF00414FE6 /* NCGridCell.swift in Sources */,
 				F7A76DC8256A71CD00119AB3 /* UIImage+Extension.swift in Sources */,
 				F7B8CD96261AF401007C1359 /* NCNetworkingChunkedUpload.swift in Sources */,
+				F763D2A02A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */,
 				F757CC8529E7F88B00F31428 /* NCManageDatabase+Groupfolders.swift in Sources */,
 				F7BAADC91ED5A87C00B7EAD4 /* NCDatabase.swift in Sources */,
 				F7817D0129802D5F00FFBC65 /* NCViewCertificateDetails.swift in Sources */,
@@ -3126,11 +3110,11 @@
 				F783030728B4C52800B84583 /* UIColor+Extension.swift in Sources */,
 				F783030028B4C45800B84583 /* NCGlobal.swift in Sources */,
 				F793E59D28B761E7005E4B02 /* NCNetworking.swift in Sources */,
-				F78302FC28B4C3F300B84583 /* NCElementsJSON.swift in Sources */,
 				F7BF9D832934CA21009EE9A6 /* NCManageDatabase+LayoutForView.swift in Sources */,
 				F757CC8329E7F88B00F31428 /* NCManageDatabase+Groupfolders.swift in Sources */,
 				F749B652297B0F2400087535 /* NCManageDatabase+Avatar.swift in Sources */,
 				F783030628B4C51E00B84583 /* String+Extension.swift in Sources */,
+				F763D29E2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */,
 				F77ED59328C9CEA000E24ED0 /* ToolbarWidgetProvider.swift in Sources */,
 				F72A17D828B221E300F3F159 /* DashboardWidgetView.swift in Sources */,
 				F77ED59528C9CEA400E24ED0 /* ToolbarWidgetView.swift in Sources */,
@@ -3158,6 +3142,7 @@
 				F771E3F720E239B500AFB62D /* FileProviderExtension+Actions.swift in Sources */,
 				F7245926289BB59300474787 /* ThreadSafeDictionary.swift in Sources */,
 				F76673F022C90434007ED366 /* FileProviderUtility.swift in Sources */,
+				F763D2A12A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */,
 				F7434B3420E23FD700417916 /* NCDatabase.swift in Sources */,
 				F757CC8629E7F88B00F31428 /* NCManageDatabase+Groupfolders.swift in Sources */,
 				F702F2D125EE5B5C008F8E80 /* NCGlobal.swift in Sources */,
@@ -3167,7 +3152,6 @@
 				F785EE9E2461A09900B3F945 /* NCNetworking.swift in Sources */,
 				F749B655297B0F2400087535 /* NCManageDatabase+Avatar.swift in Sources */,
 				F771E3D320E2392D00AFB62D /* FileProviderExtension.swift in Sources */,
-				F73D5E49246DE09200DF6467 /* NCElementsJSON.swift in Sources */,
 				F771E3D520E2392D00AFB62D /* FileProviderItem.swift in Sources */,
 				AF4BF616275629E20081CEEF /* NCManageDatabase+Account.swift in Sources */,
 				F343A4B72A1E084300DDA874 /* PHAsset+Extension.swift in Sources */,
@@ -3221,6 +3205,7 @@
 				AF935067276B84E700BD078F /* NCMenu+FloatingPanel.swift in Sources */,
 				F702F2CD25EE5B4F008F8E80 /* AppDelegate.swift in Sources */,
 				F769454022E9F077000A798A /* NCSharePaging.swift in Sources */,
+				F7EE66AD2A20B226009AE765 /* UILabel+Extension.swift in Sources */,
 				F78ACD4221903CE00088454D /* NCListCell.swift in Sources */,
 				F76D3CF12428B40E005DFA87 /* NCViewerPDFSearch.swift in Sources */,
 				F7245924289BB50C00474787 /* ThreadSafeDictionary.swift in Sources */,
@@ -3249,7 +3234,6 @@
 				F75A9EE623796C6F0044CFCE /* NCNetworking.swift in Sources */,
 				F758B460212C56A400515F55 /* NCScan.swift in Sources */,
 				F78ACD52219046DC0088454D /* NCSectionHeaderFooter.swift in Sources */,
-				F7490E902988F0C2009DCE94 /* NCCreateFormUploadAssets.swift in Sources */,
 				F710D2022405826100A6033D /* NCViewer+Menu.swift in Sources */,
 				F765E9CD295C585800A09ED8 /* NCUploadScanDocument.swift in Sources */,
 				F77A697D250A0FBC00FF1708 /* NCCollectionViewCommon+Menu.swift in Sources */,
@@ -3297,7 +3281,6 @@
 				AF93471A27E2361E002537EE /* NCShareAdvancePermissionHeader.swift in Sources */,
 				F7F878AE1FB9E3B900599E4F /* NCEndToEndMetadata.swift in Sources */,
 				3781B9B023DB2B7E006B4B1D /* AppDelegate+Menu.swift in Sources */,
-				F73D5E47246DE09200DF6467 /* NCElementsJSON.swift in Sources */,
 				F710D1F52405770F00A6033D /* NCViewerPDF.swift in Sources */,
 				F7B6B70427C4E7FA00A7F6EB /* NCScan+CollectionView.swift in Sources */,
 				F7C30DF6291BC0CA0017149B /* NCNetworkingE2EEUpload.swift in Sources */,
@@ -3376,6 +3359,7 @@
 				F75CA1472962F13700B01130 /* HUDView.swift in Sources */,
 				F7A48413297022E000BD1B49 /* ViewerQuickLook.swift in Sources */,
 				F77BB748289985270090FC19 /* UITabBarController+Extension.swift in Sources */,
+				F763D29D2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */,
 				F75AC2431F1F62450073EC19 /* NCManageAutoUploadFileName.swift in Sources */,
 				F7A7FA6329265CF4000603EF /* NCManageE2EE.swift in Sources */,
 				F7C7B489245EBA4100D93E60 /* NCViewerQuickLook.swift in Sources */,
@@ -3410,9 +3394,9 @@
 				F749B64C297B0CBB00087535 /* NCManageDatabase+Share.swift in Sources */,
 				F7A8D73F28F181EF008BBE1C /* NCGlobal.swift in Sources */,
 				F749B653297B0F2400087535 /* NCManageDatabase+Avatar.swift in Sources */,
+				F763D29F2A249C4500A3C901 /* NCManageDatabase+Capabilities.swift in Sources */,
 				F7A8D74328F1826F008BBE1C /* String+Extension.swift in Sources */,
 				F7A8D73728F17E1E008BBE1C /* NCManageDatabase+Account.swift in Sources */,
-				F7A8D73B28F17E2C008BBE1C /* NCElementsJSON.swift in Sources */,
 				F7817CFA29801A3500FFBC65 /* Data+Extension.swift in Sources */,
 				F7BF9D842934CA21009EE9A6 /* NCManageDatabase+LayoutForView.swift in Sources */,
 				F7A8D73C28F181BC008BBE1C /* NCBrand.swift in Sources */,
@@ -3986,7 +3970,7 @@
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
-				CURRENT_PROJECT_VERSION = 23;
+				CURRENT_PROJECT_VERSION = 0;
 				DEVELOPMENT_TEAM = NKUJUXUJ3B;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				ENABLE_TESTABILITY = YES;
@@ -4004,13 +3988,13 @@
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
 				INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2023 Nextcloud. All rights reserved.";
-				IPHONEOS_DEPLOYMENT_TARGET = 14.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 15.0;
 				LD_RUNPATH_SEARCH_PATHS = (
 					"$(inherited)",
 					"@executable_path/Frameworks",
 					"@executable_path/../../Frameworks",
 				);
-				MARKETING_VERSION = 4.8.1;
+				MARKETING_VERSION = 4.8.2;
 				ONLY_ACTIVE_ARCH = YES;
 				OTHER_LDFLAGS = "";
 				SDKROOT = iphoneos;
@@ -4049,7 +4033,7 @@
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
-				CURRENT_PROJECT_VERSION = 23;
+				CURRENT_PROJECT_VERSION = 0;
 				DEVELOPMENT_TEAM = NKUJUXUJ3B;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				ENABLE_TESTABILITY = YES;
@@ -4065,13 +4049,13 @@
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
 				INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2023 Nextcloud. All rights reserved.";
-				IPHONEOS_DEPLOYMENT_TARGET = 14.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 15.0;
 				LD_RUNPATH_SEARCH_PATHS = (
 					"$(inherited)",
 					"@executable_path/Frameworks",
 					"@executable_path/../../Frameworks",
 				);
-				MARKETING_VERSION = 4.8.1;
+				MARKETING_VERSION = 4.8.2;
 				ONLY_ACTIVE_ARCH = YES;
 				OTHER_LDFLAGS = "";
 				SDKROOT = iphoneos;

+ 0 - 54
NextcloudTests/NCGlobalTests.swift

@@ -1,54 +0,0 @@
-//
-//  NCGlobalTests.swift
-//  Nextcloud
-//
-//  Created by Henrik Storch on 01.12.21.
-//  Copyright © 2021 Henrik Storch. All rights reserved.
-//
-//  Author Henrik Storch <henrik.storch@nextcloud.com>
-//
-//  This program is free software: you can redistribute it and/or modify
-//  it under the terms of the GNU General Public License as published by
-//  the Free Software Foundation, either version 3 of the License, or
-//  (at your option) any later version.
-//
-//  This program is distributed in the hope that it will be useful,
-//  but WITHOUT ANY WARRANTY; without even the implied warranty of
-//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-//  GNU General Public License for more details.
-//
-//  You should have received a copy of the GNU General Public License
-//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
-//
-
-@testable import Nextcloud
-import XCTest
-
-class NCGlobalTests: XCTestCase {
-
-    func testSharedInatance() throws {
-        XCTAssertNotNil(NCGlobal.shared, "Shared instance should be initialized")
-    }
-
-    func testHashToInt() {
-        let emptyHash10 = NCGlobal.hashToInt(hash: "", maximum: 10)
-        let emptyHash2 = NCGlobal.hashToInt(hash: "", maximum: 2)
-        XCTAssertEqual(emptyHash10, 0, "Empty hash should be zero")
-        XCTAssertEqual(emptyHash10, emptyHash2, "Empty hashes should be the same")
-        let emptyHashA = NCGlobal.hashToInt(hash: "a", maximum: 10)
-        XCTAssertEqual(emptyHashA, 0, "Hash of 'a' mod 10 should be zero")
-        let emptyHash22 = NCGlobal.hashToInt(hash: "1ab", maximum: 100)
-        XCTAssertEqual(emptyHash22, 22, "Hash of '1ab' mod 100 should be 22")
-        let nonHexHash = NCGlobal.hashToInt(hash: "1qw&(*}", maximum: 10)
-        XCTAssertEqual(nonHexHash, 1, "Non hex characters should be ignored")
-    }
-
-    func testUsernameToColor() {
-        let color = NCGlobal.shared.usernameToColor("00000000")
-        let userColor = NCBrandColor.shared.userColors[0]
-        XCTAssertEqual(color, userColor, "Zero usercolor doesn't match")
-        let emptyColor = NCGlobal.shared.usernameToColor("")
-        let emptyUserColor = NCBrandColor.shared.userColors[12]
-        XCTAssertEqual(emptyColor, emptyUserColor, "Empty usercolor doesn't match")
-    }
-}

+ 0 - 85
NextcloudTests/ParallelWorkerTest.swift

@@ -1,85 +0,0 @@
-//
-//  ParallelWorkerTest.swift
-//  Nextcloud
-//
-//  Created by Henrik Storch on 18.02.22.
-//  Copyright © 2021 Henrik Storch. All rights reserved.
-//
-//  Author Henrik Storch <henrik.storch@nextcloud.com>
-//
-//  This program is free software: you can redistribute it and/or modify
-//  it under the terms of the GNU General Public License as published by
-//  the Free Software Foundation, either version 3 of the License, or
-//  (at your option) any later version.
-//
-//  This program is distributed in the hope that it will be useful,
-//  but WITHOUT ANY WARRANTY; without even the implied warranty of
-//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-//  GNU General Public License for more details.
-//
-//  You should have received a copy of the GNU General Public License
-//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
-//
-
-@testable import Nextcloud
-import XCTest
-
-class ParallelWorkerTest: XCTestCase {
-
-    func testWorkerComplete() throws {
-        let expectation = XCTestExpectation(description: "Worker executes all tasks")
-        let taskCount = 20
-        var tasksComplete = 0
-        let worker = ParallelWorker(n: 5, titleKey: nil, totalTasks: nil, hudView: nil)
-        for _ in 0..<taskCount {
-            worker.execute { completion in
-                tasksComplete += 1
-                completion()
-            }
-        }
-        worker.completeWork {
-            XCTAssertEqual(tasksComplete, taskCount)
-            if tasksComplete == taskCount {
-                expectation.fulfill()
-            }
-        }
-
-        let result = XCTWaiter.wait(for: [expectation], timeout: 5)
-        XCTAssertEqual(result, .completed)
-    }
-
-    func testWorkerOrder() throws {
-        let expectation = XCTestExpectation(description: "Worker executes work in sequence for n = 1")
-        let sortedArray = Array(0..<20)
-        var array: [Int] = []
-        let worker = ParallelWorker(n: 1, titleKey: nil, totalTasks: nil, hudView: nil)
-        for i in sortedArray {
-            worker.execute { completion in
-                DispatchQueue.main.asyncAfter(deadline: .now() + Double.random(in: 0...0.2)) {
-                    array.append(i)
-                    completion()
-                }
-            }
-        }
-        worker.completeWork {
-            XCTAssertEqual(sortedArray, array)
-            if sortedArray == array {
-                expectation.fulfill()
-            }
-        }
-        let result = XCTWaiter.wait(for: [expectation], timeout: 5)
-        XCTAssertEqual(result, .completed)
-    }
-
-    func testWorkerFailsWithoutCompletion() throws {
-        let expectation = XCTestExpectation(description: "Worker fails if completion isn't called")
-        expectation.isInverted = true
-        let worker = ParallelWorker(n: 5, titleKey: nil, totalTasks: nil, hudView: nil)
-        for _ in 0..<20 {
-            worker.execute { _ in }
-        }
-        worker.completeWork { expectation.fulfill() }
-        let result = XCTWaiter.wait(for: [expectation], timeout: 5)
-        XCTAssertEqual(result, .completed)
-    }
-}

+ 0 - 136
NextcloudTests/SharePermissionTest.swift

@@ -1,136 +0,0 @@
-//
-//  SharePermissionTest.swift
-//  Nextcloud
-//
-//  Created by Henrik Storch on 29.03.22.
-//  Copyright © 2021 Henrik Storch. All rights reserved.
-//
-//  Author Henrik Storch <henrik.storch@nextcloud.com>
-//
-//  This program is free software: you can redistribute it and/or modify
-//  it under the terms of the GNU General Public License as published by
-//  the Free Software Foundation, either version 3 of the License, or
-//  (at your option) any later version.
-//
-//  This program is distributed in the hope that it will be useful,
-//  but WITHOUT ANY WARRANTY; without even the implied warranty of
-//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-//  GNU General Public License for more details.
-//
-//  You should have received a copy of the GNU General Public License
-//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
-//
-
-@testable import Nextcloud
-import XCTest
-import NextcloudKit
-
-class SharePermissionTest: XCTestCase {
-    override func setUp() {
-        let json =
-        """
-        {"ocs":{"data":{"capabilities":{"files_sharing":{"default_permissions":31}}}}}
-        """.data(using: .utf8)!
-        NCManageDatabase.shared.addCapabilitiesJSon(json, account: "")
-    }
-
-    func testShareCellPermissionCell() throws {
-        let share = NCTableShareOptions(sharee: NKSharee(), metadata: tableMetadata(), password: nil)
-        let shareConfig = NCShareConfig(parentMetadata: tableMetadata(), share: share)
-
-        for row in 0..<shareConfig.permissions.count {
-            guard let cell = shareConfig.config(for: IndexPath(row: row, section: 0)) as? NCToggleCellConfig else {
-                XCTFail("Invalid share permission cell")
-                continue
-            }
-            XCTAssertFalse(cell.isOn(for: share))
-        }
-
-        let meta = tableMetadata()
-        meta.sharePermissionsCollaborationServices = 31
-        let fullShare = NCTableShareOptions(sharee: NKSharee(), metadata: meta, password: nil)
-        let shareFullConfig = NCShareConfig(parentMetadata: meta, share: fullShare)
-
-        for row in 0..<shareFullConfig.permissions.count {
-            guard let cell = shareConfig.config(for: IndexPath(row: row, section: 0)) as? NCToggleCellConfig else {
-                XCTFail("Invalid share permission cell")
-                continue
-            }
-            XCTAssertTrue(cell.isOn(for: fullShare))
-        }
-    }
-
-    func testSharePermission() throws {
-        XCTAssertTrue(NCLinkPermission.allowEdit.hasResharePermission(for: 15))
-        XCTAssertTrue(NCLinkPermission.allowEdit.hasResharePermission(for: 11))
-        XCTAssertTrue(NCLinkPermission.allowEdit.hasResharePermission(for: 7))
-        XCTAssertFalse(NCLinkPermission.allowEdit.hasResharePermission(for: 13))
-        XCTAssertFalse(NCLinkPermission.allowEdit.hasResharePermission(for: 1))
-
-        XCTAssertTrue(NCLinkPermission.viewOnly.hasResharePermission(for: 25))
-        XCTAssertTrue(NCLinkPermission.viewOnly.hasResharePermission(for: 17))
-        XCTAssertFalse(NCLinkPermission.viewOnly.hasResharePermission(for: 12))
-        XCTAssertFalse(NCLinkPermission.viewOnly.hasResharePermission(for: 2))
-
-        XCTAssertTrue(NCLinkPermission.fileDrop.hasResharePermission(for: 4))
-        XCTAssertFalse(NCLinkPermission.fileDrop.hasResharePermission(for: 27))
-
-        XCTAssertTrue(NCUserPermission.create.hasResharePermission(for: 4))
-        XCTAssertFalse(NCUserPermission.create.hasResharePermission(for: 27))
-
-        XCTAssertTrue(NCUserPermission.edit.hasResharePermission(for: 2))
-        XCTAssertFalse(NCUserPermission.edit.hasResharePermission(for: 29))
-
-        XCTAssertTrue(NCUserPermission.reshare.hasResharePermission(for: 16))
-        XCTAssertFalse(NCUserPermission.reshare.hasResharePermission(for: 15))
-    }
-
-    func testFileShare() throws {
-        let meta = tableMetadata()
-        meta.directory = false
-        let share = NCTableShareOptions.shareLink(metadata: meta, password: nil)
-        let fileConfig = NCShareConfig(parentMetadata: meta, share: share)
-        XCTAssertEqual(fileConfig.advanced, NCShareDetails.forLink)
-        XCTAssertEqual(fileConfig.permissions as? [NCLinkPermission], NCLinkPermission.forFile)
-
-        meta.directory = true
-        let folderConfig = NCShareConfig(parentMetadata: meta, share: share)
-        XCTAssertEqual(folderConfig.advanced, NCShareDetails.forLink)
-        XCTAssertEqual(folderConfig.permissions as? [NCLinkPermission], NCLinkPermission.forDirectory)
-    }
-
-    func testUserShare() throws {
-        let meta = tableMetadata()
-        meta.directory = false
-        let sharee = NKSharee()
-        let share = NCTableShareOptions(sharee: sharee, metadata: meta, password: nil)
-        let fileConfig = NCShareConfig(parentMetadata: meta, share: share)
-        XCTAssertEqual(fileConfig.advanced, NCShareDetails.forUser)
-        XCTAssertEqual(fileConfig.permissions as? [NCUserPermission], NCUserPermission.forFile)
-
-        meta.directory = true
-        let folderConfig = NCShareConfig(parentMetadata: meta, share: share)
-        XCTAssertEqual(folderConfig.advanced, NCShareDetails.forUser)
-        XCTAssertEqual(folderConfig.permissions as? [NCUserPermission], NCUserPermission.forDirectory)
-    }
-
-    func testResharePermission() throws {
-        let meta = tableMetadata()
-        let permissionReadShare = NCGlobal.shared.permissionShareShare + NCGlobal.shared.permissionReadShare
-        meta.sharePermissionsCollaborationServices = permissionReadShare
-        meta.directory = false
-        let share = NCTableShareOptions.shareLink(metadata: meta, password: nil)
-        let fileConfig = NCShareConfig(parentMetadata: meta, share: share)
-        XCTAssertEqual(fileConfig.resharePermission, meta.sharePermissionsCollaborationServices)
-        XCTAssertEqual(fileConfig.advanced, NCShareDetails.forLink)
-        XCTAssertEqual(fileConfig.permissions as? [NCLinkPermission], NCLinkPermission.forFile)
-
-        meta.directory = true
-        let sharee = NKSharee()
-        let folderShare = NCTableShareOptions(sharee: sharee, metadata: meta, password: nil)
-        let folderConfig = NCShareConfig(parentMetadata: meta, share: folderShare)
-        XCTAssertEqual(folderConfig.resharePermission, meta.sharePermissionsCollaborationServices)
-        XCTAssertEqual(folderConfig.advanced, NCShareDetails.forUser)
-        XCTAssertEqual(folderConfig.permissions as? [NCUserPermission], NCUserPermission.forDirectory)
-    }
-}

+ 0 - 64
NextcloudTests/UserAgentTests.swift

@@ -1,64 +0,0 @@
-//
-//  UserAgentTests.swift
-//  Nextcloud
-//
-//  Created by Henrik Storch on 03.05.22.
-//  Copyright © 2022 Henrik Storch. All rights reserved.
-//
-//  Author Henrik Storch <henrik.storch@nextcloud.com>
-//
-//  This program is free software: you can redistribute it and/or modify
-//  it under the terms of the GNU General Public License as published by
-//  the Free Software Foundation, either version 3 of the License, or
-//  (at your option) any later version.
-//
-//  This program is distributed in the hope that it will be useful,
-//  but WITHOUT ANY WARRANTY; without even the implied warranty of
-//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-//  GNU General Public License for more details.
-//
-//  You should have received a copy of the GNU General Public License
-//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
-//
-
-@testable import Nextcloud
-import XCTest
-
-class UserAgentTests: XCTestCase {
-    // https://github.com/nextcloud/server/blob/fc826e98115b510313ddacbf6fef4ce8d041e373/lib/public/IRequest.php#L83
-    let ncServerUARegex = "^Mozilla\\/5\\.0 \\(iOS\\) (ownCloud|Nextcloud)\\-iOS.*$"
-
-    // https://github.com/ProseMirror/prosemirror-view/blob/427d278aaaacde422ed1f2b8c84bb53337162775/src/browser.js#L18-L22
-    let proseMirrorWebKitUARegex = "\\bAppleWebKit\\/(\\d+)"
-    let proseMirroriOSUARegex = "Mobile\\/\\w+"
-
-    func testDefaultUserAgent() throws {
-        let userAgent: String = CCUtility.getUserAgent()
-        let match = try matches(for: ncServerUARegex, in: userAgent).first
-        XCTAssertNotNil(match)
-    }
-
-    func testTextUserAgent() throws {
-        let userAgent: String = NCUtility.shared.getCustomUserAgentNCText()
-        let match = try matches(for: ncServerUARegex, in: userAgent).first
-        XCTAssertNotNil(match)
-
-        let iOSMatch = try matches(for: proseMirroriOSUARegex, in: userAgent).first
-        XCTAssertNotNil(iOSMatch)
-
-        // https://github.com/ProseMirror/prosemirror-view/blob/8f246f320801f8e3cac92c97f71ac91e3e327f2f/src/input.js#L521-L522
-        let webKitMatch = try matches(for: proseMirrorWebKitUARegex, in: userAgent).first
-        XCTAssertNotNil(webKitMatch)
-        XCTAssertEqual(webKitMatch!.numberOfRanges, 2)
-        let versionRange = webKitMatch!.range(at: 1)
-        let versionString = userAgent[Range(versionRange, in: userAgent)!]
-        let webkitVersion = Int(versionString) ?? 0
-        XCTAssertGreaterThanOrEqual(webkitVersion, 604)
-    }
-
-    func matches(for regex: String, in text: String) throws -> [NSTextCheckingResult] {
-        let range = NSRange(location: 0, length: text.utf16.count)
-        let regex = try NSRegularExpression(pattern: regex)
-        return regex.matches(in: text, range: range)
-    }
-}

+ 4 - 2
Widget/Dashboard/DashboardData.swift

@@ -128,8 +128,10 @@ func getDashboardDataEntry(configuration: DashboardIntent?, isPreview: Bool, dis
     let result = NCManageDatabase.shared.getDashboardWidgetApplications(account: account.account).first
     let id: String = configuration?.applications?.identifier ?? (result?.id ?? "recommendations")
 
-    let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: account.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-    guard serverVersionMajor >= NCGlobal.shared.nextcloudVersion25 else {
+    // Capabilities
+    NCManageDatabase.shared.setCapabilities(account: account.account)
+
+    guard NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion25 else {
         return completion(DashboardDataEntry(date: Date(), datas: datasPlaceholder, dashboard: nil, buttons: nil, isPlaceholder: true, isEmpty: false, titleImage: UIImage(named: "widget")!, title: "Dashboard", footerImage: "xmark.icloud", footerText: NSLocalizedString("_widget_available_nc25_", comment: "")))
     }
         

+ 4 - 2
Widget/Lockscreen/LockscreenData.swift

@@ -55,8 +55,10 @@ func getLockscreenDataEntry(configuration: AccountIntent?, isPreview: Bool, fami
         return completion(LockscreenData(date: Date(), isPlaceholder: true, activity: "", link: URL(string: "https://")!, quotaRelative: 0, quotaUsed: "", quotaTotal: "", error: false))
     }
 
-    let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: account.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-    if serverVersionMajor < NCGlobal.shared.nextcloudVersion25 {
+    // Capabilities
+    NCManageDatabase.shared.setCapabilities(account: account.account)
+
+    if NCGlobal.shared.capabilityServerVersionMajor < NCGlobal.shared.nextcloudVersion25 {
         completion(LockscreenData(date: Date(), isPlaceholder: false, activity: NSLocalizedString("_widget_available_nc25_", comment: ""), link: URL(string: "https://")!, quotaRelative: 0, quotaUsed: "", quotaTotal: "", error: true))
     }
 

+ 4 - 3
iOSClient/AppDelegate.swift

@@ -576,9 +576,10 @@ class AppDelegate: UIResponder, UIApplicationDelegate, UNUserNotificationCenterD
         _ = NCActionCenter.shared
 
         NextcloudKit.shared.setup(account: account, user: user, userId: userId, password: password, urlBase: urlBase)
-        let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-        if serverVersionMajor > 0 {
-            NextcloudKit.shared.setup(nextcloudVersion: serverVersionMajor)
+        NCManageDatabase.shared.setCapabilities(account: account)
+
+        if NCGlobal.shared.capabilityServerVersionMajor > 0 {
+            NextcloudKit.shared.setup(nextcloudVersion: NCGlobal.shared.capabilityServerVersionMajor)
         }
 
         DispatchQueue.main.async {

+ 0 - 10
iOSClient/Data/NCDatabase.swift

@@ -30,16 +30,6 @@ protocol DateCompareable {
     var dateKey: Date { get }
 }
 
-class tableCapabilities: Object {
-
-    @objc dynamic var account = ""
-    @objc dynamic var jsondata: Data?
-
-    override static func primaryKey() -> String {
-        return "account"
-    }
-}
-
 class tableChunk: Object {
 
     @objc dynamic var account = ""

+ 0 - 75
iOSClient/Data/NCElementsJSON.swift

@@ -1,75 +0,0 @@
-//
-//  NCElementsJSON.swift
-//  Nextcloud
-//
-//  Created by Marino Faggiana on 14/05/2020.
-//  Copyright © 2020 Marino Faggiana. All rights reserved.
-//
-//  Author Marino Faggiana <marino.faggiana@nextcloud.com>
-//
-//  This program is free software: you can redistribute it and/or modify
-//  it under the terms of the GNU General Public License as published by
-//  the Free Software Foundation, either version 3 of the License, or
-//  (at your option) any later version.
-//
-//  This program is distributed in the hope that it will be useful,
-//  but WITHOUT ANY WARRANTY; without even the implied warranty of
-//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-//  GNU General Public License for more details.
-//
-//  You should have received a copy of the GNU General Public License
-//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
-//
-
-import UIKit
-
-@objc class NCElementsJSON: NSObject {
-    @objc static let shared: NCElementsJSON = {
-        let instance = NCElementsJSON()
-        return instance
-    }()
-
-    @objc public let capabilitiesVersionString: Array = ["ocs", "data", "version", "string"]
-    @objc public let capabilitiesVersionMajor: Array = ["ocs", "data", "version", "major"]
-
-    @objc public let capabilitiesFileSharingApiEnabled: Array = ["ocs", "data", "capabilities", "files_sharing", "api_enabled"]
-    @objc public let capabilitiesFileSharingPubPasswdEnforced: Array = ["ocs", "data", "capabilities", "files_sharing", "public", "password", "enforced"]
-    @objc public let capabilitiesFileSharingPubExpireDateEnforced: Array = ["ocs", "data", "capabilities", "files_sharing", "public", "expire_date", "enforced"]
-    @objc public let capabilitiesFileSharingPubExpireDateDays: Array = ["ocs", "data", "capabilities", "files_sharing", "public", "expire_date", "days"]
-    @objc public let capabilitiesFileSharingInternalExpireDateEnforced: Array = ["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_internal", "enforced"]
-    @objc public let capabilitiesFileSharingInternalExpireDateDays: Array = ["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_internal", "days"]
-    @objc public let capabilitiesFileSharingRemoteExpireDateEnforced: Array = ["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_remote", "enforced"]
-    @objc public let capabilitiesFileSharingRemoteExpireDateDays: Array = ["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_remote", "days"]
-    @objc public let capabilitiesFileSharingDefaultPermissions: Array = ["ocs", "data", "capabilities", "files_sharing", "default_permissions"]
-    @objc public let capabilitiesFileSharingSendPasswordMail: Array = ["ocs", "data", "capabilities", "files_sharing", "sharebymail", "send_password_by_mail"]
-
-    @objc public let capabilitiesThemingColor: Array = ["ocs", "data", "capabilities", "theming", "color"]
-    @objc public let capabilitiesThemingColorElement: Array = ["ocs", "data", "capabilities", "theming", "color-element"]
-    @objc public let capabilitiesThemingColorText: Array = ["ocs", "data", "capabilities", "theming", "color-text"]
-    @objc public let capabilitiesThemingName: Array = ["ocs", "data", "capabilities", "theming", "name"]
-    @objc public let capabilitiesThemingSlogan: Array = ["ocs", "data", "capabilities", "theming", "slogan"]
-
-    @objc public let capabilitiesWebDavRoot: Array = ["ocs", "data", "capabilities", "core", "webdav-root"]
-
-    @objc public let capabilitiesE2EEEnabled: Array = ["ocs", "data", "capabilities", "end-to-end-encryption", "enabled"]
-    @objc public let capabilitiesE2EEApiVersion: Array = ["ocs", "data", "capabilities", "end-to-end-encryption", "api-version"]
-
-    @objc public let capabilitiesExternalSites: Array = ["ocs", "data", "capabilities", "external"]
-
-    @objc public let capabilitiesRichdocumentsMimetypes: Array = ["ocs", "data", "capabilities", "richdocuments", "mimetypes"]
-
-    @objc public let capabilitiesActivity: Array = ["ocs", "data", "capabilities", "activity", "apiv2"]
-
-    @objc public let capabilitiesNotification: Array = ["ocs", "data", "capabilities", "notifications", "ocs-endpoints"]
-
-    @objc public let capabilitiesFilesUndelete: Array = ["ocs", "data", "capabilities", "files", "undelete"]
-    @objc public let capabilitiesFilesLockVersion: Array = ["ocs", "data", "capabilities", "files", "locking"] // NC 24
-    @objc public let capabilitiesFilesComments: Array = ["ocs", "data", "capabilities", "files", "comments"] // NC 20
-
-    @objc public let capabilitiesHWCEnabled: Array = ["ocs", "data", "capabilities", "handwerkcloud", "enabled"]
-
-    @objc public let capabilitiesUserStatusEnabled: Array = ["ocs", "data", "capabilities", "user_status", "enabled"]
-    @objc public let capabilitiesUserStatusSupportsEmoji: Array = ["ocs", "data", "capabilities", "user_status", "supports_emoji"]
-
-    @objc public let capabilitiesGroupfoldersEnabled: Array = ["ocs", "data", "capabilities", "groupfolders", "hasGroupFolders"]
-}

+ 136 - 0
iOSClient/Data/NCManageDatabase+Capabilities.swift

@@ -0,0 +1,136 @@
+//
+//  NCManageDatabase+Capabilities.swift
+//  Nextcloud
+//
+//  Created by Marino Faggiana on 29/05/23.
+//  Copyright © 2023 Marino Faggiana. All rights reserved.
+//
+//  Author Marino Faggiana <marino.faggiana@nextcloud.com>
+//
+//  This program is free software: you can redistribute it and/or modify
+//  it under the terms of the GNU General Public License as published by
+//  the Free Software Foundation, either version 3 of the License, or
+//  (at your option) any later version.
+//
+//  This program is distributed in the hope that it will be useful,
+//  but WITHOUT ANY WARRANTY; without even the implied warranty of
+//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+//  GNU General Public License for more details.
+//
+//  You should have received a copy of the GNU General Public License
+//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+//
+
+import Foundation
+import RealmSwift
+import NextcloudKit
+import SwiftyJSON
+
+class tableCapabilities: Object {
+
+    @objc dynamic var account = ""
+    @objc dynamic var jsondata: Data?
+
+    override static func primaryKey() -> String {
+        return "account"
+    }
+}
+
+extension NCManageDatabase {
+
+    func addCapabilitiesJSon(_ data: Data, account: String) {
+
+        let realm = try! Realm()
+
+        do {
+            try realm.write {
+                let addObject = tableCapabilities()
+
+                addObject.account = account
+                addObject.jsondata = data
+
+                realm.add(addObject, update: .all)
+            }
+        } catch let error {
+            NextcloudKit.shared.nkCommonInstance.writeLog("Could not write to database: \(error)")
+        }
+    }
+
+    func getCapabilities(account: String) -> Data? {
+
+        let realm = try! Realm()
+
+        guard let result = realm.objects(tableCapabilities.self).filter("account == %@", account).first else {
+            return nil
+        }
+
+        return result.jsondata
+    }
+
+    func setCapabilities(account: String, data: Data? = nil) {
+
+        let realm = try! Realm()
+        let json: JSON?
+
+        if let data = data {
+            json = JSON(data)
+        } else {
+            guard let result = realm.objects(tableCapabilities.self).filter("account == %@", account).first,
+                  let data = result.jsondata else {
+                return
+            }
+            json = JSON(data)
+        }
+
+        guard let json = json else { return }
+
+        NCGlobal.shared.capabilityServerVersion = json["ocs", "data", "version", "string"].stringValue
+        NCGlobal.shared.capabilityServerVersionMajor = json["ocs", "data", "version", "major"].intValue
+
+        NCGlobal.shared.capabilityFileSharingApiEnabled = json["ocs", "data", "capabilities", "files_sharing", "api_enabled"].boolValue
+        NCGlobal.shared.capabilityFileSharingPubPasswdEnforced = json["ocs", "data", "capabilities", "files_sharing", "public", "password", "enforced"].boolValue
+        NCGlobal.shared.capabilityFileSharingPubExpireDateEnforced = json["ocs", "data", "capabilities", "files_sharing", "public", "expire_date", "enforced"].boolValue
+        NCGlobal.shared.capabilityFileSharingPubExpireDateDays = json["ocs", "data", "capabilities", "files_sharing", "public", "expire_date", "days"].intValue
+        NCGlobal.shared.capabilityFileSharingInternalExpireDateEnforced = json["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_internal", "enforced"].boolValue
+        NCGlobal.shared.capabilityFileSharingInternalExpireDateDays = json["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_internal", "days"].intValue
+        NCGlobal.shared.capabilityFileSharingRemoteExpireDateEnforced = json["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_remote", "enforced"].boolValue
+        NCGlobal.shared.capabilityFileSharingRemoteExpireDateDays = json["ocs", "data", "capabilities", "files_sharing", "public", "expire_date_remote", "days"].intValue
+        NCGlobal.shared.capabilityFileSharingDefaultPermission = json["ocs", "data", "capabilities", "files_sharing", "default_permissions"].intValue
+
+        NCGlobal.shared.capabilityThemingColor = json["ocs", "data", "capabilities", "theming", "color"].stringValue
+        NCGlobal.shared.capabilityThemingColorElement = json["ocs", "data", "capabilities", "theming", "color-element"].stringValue
+        NCGlobal.shared.capabilityThemingColorText = json["ocs", "data", "capabilities", "theming", "color-text"].stringValue
+        NCGlobal.shared.capabilityThemingName = json["ocs", "data", "capabilities", "theming", "name"].stringValue
+        NCGlobal.shared.capabilityThemingSlogan = json["ocs", "data", "capabilities", "theming", "slogan"].stringValue
+
+        NCGlobal.shared.capabilityE2EEEnabled = json["ocs", "data", "capabilities", "end-to-end-encryption", "enabled"].boolValue
+        NCGlobal.shared.capabilityE2EEApiVersion = json["ocs", "data", "capabilities", "end-to-end-encryption", "api-version"].stringValue
+
+
+        NCGlobal.shared.capabilityRichdocumentsMimetypes.removeAll()
+        let mimetypes = json["ocs", "data", "capabilities", "richdocuments", "mimetypes"].arrayValue
+        for mimetype in mimetypes {
+            NCGlobal.shared.capabilityRichdocumentsMimetypes.append(mimetype.stringValue)
+        }
+
+        NCGlobal.shared.capabilityActivity.removeAll()
+        let activities = json["ocs", "data", "capabilities", "activity", "apiv2"].arrayValue
+        for activity in activities {
+            NCGlobal.shared.capabilityActivity.append(activity.stringValue)
+        }
+
+        NCGlobal.shared.capabilityNotification.removeAll()
+        let notifications = json["ocs", "data", "capabilities", "notifications", "ocs-endpoints"].arrayValue
+        for notify in notifications {
+            NCGlobal.shared.capabilityNotification.append(notify.stringValue)
+        }
+
+        NCGlobal.shared.capabilityFilesUndelete = json["ocs", "data", "capabilities", "files", "undelete"].boolValue
+        NCGlobal.shared.capabilityFilesLockVersion = json["ocs", "data", "capabilities", "files", "locking"].stringValue
+        NCGlobal.shared.capabilityFilesComments = json["ocs", "data", "capabilities", "files", "comments"].boolValue
+
+        NCGlobal.shared.capabilityUserStatusEnabled = json["ocs", "data", "capabilities", "user_status", "enabled"].boolValue
+        NCGlobal.shared.capabilityExternalSites = json["ocs", "data", "capabilities", "external"].exists()
+        NCGlobal.shared.capabilityGroupfoldersEnabled = json["ocs", "data", "capabilities", "groupfolders", "hasGroupFolders"].boolValue
+    }
+}

+ 15 - 13
iOSClient/Data/NCManageDatabase+Metadata.swift

@@ -198,19 +198,6 @@ extension tableMetadata {
         return directory && size == 0 && !e2eEncrypted && CCUtility.isEnd(toEndEnabled: account)
     }
 
-    var isSharable: Bool {
-        let sharing = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingApiEnabled, exists: false)
-        if !sharing { return false }
-        if !e2eEncrypted && !isDirectoryE2EE { return true }
-        let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-        if serverVersionMajor >= NCGlobal.shared.nextcloudVersion26 && directory {
-            // E2EE DIRECTORY SECURE FILE DROP (SHARE AVAILABLE)
-            return true
-        } else {
-            return false
-        }
-    }
-
     var isDirectoryUnsettableE2EE: Bool {
         return !isDirectoryE2EE && directory && size == 0 && e2eEncrypted && CCUtility.isEnd(toEndEnabled: account)
     }
@@ -246,6 +233,21 @@ extension tableMetadata {
     func canUnlock(as user: String) -> Bool {
         return !lock || (lockOwner == user && lockOwnerType == 0)
     }
+
+    /// Return if is sharable (temp)
+    // TODO: modifify for E2EE 2.0
+    func isSharable() -> Bool {
+        guard NCGlobal.shared.capabilityFileSharingApiEnabled else { return false }
+
+        if !e2eEncrypted && !isDirectoryE2EE {
+            return true
+        } else if NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion26 && directory {
+            // E2EE DIRECTORY SECURE FILE DROP (SHARE AVAILABLE)
+            return true
+        } else {
+            return false
+        }
+    }
 }
 
 extension NCManageDatabase {

+ 0 - 113
iOSClient/Data/NCManageDatabase.swift

@@ -25,7 +25,6 @@
 import UIKit
 import RealmSwift
 import NextcloudKit
-import SwiftyJSON
 import CoreMedia
 import Photos
 
@@ -252,118 +251,6 @@ class NCManageDatabase: NSObject {
         return object.isInvalidated
     }
 
-    // MARK: -
-    // MARK: Table Avatar
-
-    
-    // MARK: -
-    // MARK: Table Capabilities
-
-    func addCapabilitiesJSon(_ data: Data, account: String) {
-
-        let realm = try! Realm()
-
-        do {
-            try realm.write {
-                let addObject = tableCapabilities()
-
-                addObject.account = account
-                addObject.jsondata = data
-
-                realm.add(addObject, update: .all)
-            }
-        } catch let error {
-            NextcloudKit.shared.nkCommonInstance.writeLog("Could not write to database: \(error)")
-        }
-    }
-
-    func getCapabilities(account: String) -> String? {
-
-        let realm = try! Realm()
-
-        guard let result = realm.objects(tableCapabilities.self).filter("account == %@", account).first else {
-            return nil
-        }
-        guard let jsondata = result.jsondata else {
-            return nil
-        }
-
-        let json = JSON(jsondata)
-
-        return json.rawString()?.replacingOccurrences(of: "\\/", with: "/")
-    }
-
-    @objc func getCapabilitiesServerString(account: String, elements: [String]) -> String? {
-
-        let realm = try! Realm()
-
-        guard let result = realm.objects(tableCapabilities.self).filter("account == %@", account).first else {
-            return nil
-        }
-        guard let jsondata = result.jsondata else {
-            return nil
-        }
-
-        let json = JSON(jsondata)
-        return json[elements].string
-    }
-
-    func getCapabilitiesServerInt(account: String, elements: [String]) -> Int {
-
-        let realm = try! Realm()
-
-        guard let result = realm.objects(tableCapabilities.self).filter("account == %@", account).first,
-              let jsondata = result.jsondata else {
-            return 0
-        }
-
-        let json = JSON(jsondata)
-        return json[elements].intValue
-    }
-
-    @objc func getCapabilitiesServerBool(account: String, elements: [String], exists: Bool) -> Bool {
-
-        let realm = try! Realm()
-
-        guard let result = realm.objects(tableCapabilities.self).filter("account == %@", account).first else {
-            return false
-        }
-        guard let jsondata = result.jsondata else {
-            return false
-        }
-
-        let json = JSON(jsondata)
-        if exists {
-            return json[elements].exists()
-        } else {
-            return json[elements].boolValue
-        }
-    }
-
-    func getCapabilitiesServerArray(account: String, elements: [String]) -> [String]? {
-
-        let realm = try! Realm()
-        var resultArray: [String] = []
-
-        guard let result = realm.objects(tableCapabilities.self).filter("account == %@", account).first else {
-            return nil
-        }
-        guard let jsondata = result.jsondata else {
-            return nil
-        }
-
-        let json = JSON(jsondata)
-
-        if let results = json[elements].array {
-            for result in results {
-                resultArray.append(result.string ?? "")
-            }
-            return resultArray
-        }
-
-        return nil
-    }
-
     // MARK: -
     // MARK: Table Chunk
 

+ 24 - 117
iOSClient/Diagnostics/NCCapabilitiesView.swift

@@ -31,7 +31,6 @@ class NCCapabilitiesViewOO: ObservableObject {
     }
 
     @Published var capabililies: [Capability] = []
-    @Published var json = "Lorem ipsum dolor sit amet.\nEa voluptas aperiam aut inventore saepe in tenetur modi.\nCum sint tempore sed maiores quos aut quaerat deleniti.\nQui beatae quia qui repellat sunt in Quis libero aut quidem porro non explicabo tenetur et natus doloribus non voluptatum consequatur.\n"
     @Published var homeServer = ""
 
     init() {
@@ -43,120 +42,34 @@ class NCCapabilitiesViewOO: ObservableObject {
             homeServer = "https://cloud.nextcloud.com/remote.php.dav/files/marino/"
         } else {
             guard let activeAccount = NCManageDatabase.shared.getActiveAccount() else { return }
-            homeServer = NCUtilityFileSystem.shared.getHomeServer(urlBase: activeAccount.urlBase, userId: activeAccount.userId) + "/"
-            getCapabilities(account: activeAccount.account)
-        }
-    }
-
-    func getCapabilities(account: String) {
-
-        NextcloudKit.shared.getCapabilities { account, data, error in
-            if error == .success, let data = data {
-                NCManageDatabase.shared.addCapabilitiesJSon(data, account: account)
-                let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-                if serverVersionMajor >= NCGlobal.shared.nextcloudVersion18 {
-                    NextcloudKit.shared.NCTextObtainEditorDetails { account, editors, creators, _, error in
-                        if error == .success {
-                            NCManageDatabase.shared.addDirectEditing(account: account, editors: editors, creators: creators)
-                            self.updateCapabilities(account: account)
-                        }
+            var textEditor = false
+            var onlyofficeEditors = false
+
+            capabililies.append(Capability(text: "File sharing", image: UIImage(named: "share")!.resizeImage(size: CGSize(width: 25, height: 25))!, available: NCGlobal.shared.capabilityFileSharingApiEnabled))
+            capabililies.append(Capability(text: "External site", image: UIImage(systemName: "network")!, available: NCGlobal.shared.capabilityExternalSites))
+            capabililies.append(Capability(text: "End-to-End Encryption", image: UIImage(systemName: "lock")!, available: NCGlobal.shared.capabilityE2EEEnabled))
+            capabililies.append(Capability(text: "Activity", image: UIImage(systemName: "bolt")!, available: !NCGlobal.shared.capabilityActivity.isEmpty))
+            capabililies.append(Capability(text: "Notification", image: UIImage(systemName: "bell")!, available: !NCGlobal.shared.capabilityNotification.isEmpty))
+            capabililies.append(Capability(text: "Deleted files", image: UIImage(systemName: "trash")!, available: NCGlobal.shared.capabilityFilesUndelete))
+
+            if let editors = NCManageDatabase.shared.getDirectEditingEditors(account: activeAccount.account) {
+                for editor in editors {
+                    if editor.editor == NCGlobal.shared.editorText {
+                        textEditor = true
+                    } else if editor.editor == NCGlobal.shared.editorOnlyoffice {
+                        onlyofficeEditors = true
                     }
-                } else {
-                    self.updateCapabilities(account: account)
                 }
-            } else {
-                self.updateCapabilities(account: account)
             }
-        }
-
-        updateCapabilities(account: account)
-    }
-
-    func updateCapabilities(account: String) {
+            capabililies.append(Capability(text: "Text", image: UIImage(systemName: "doc.text")!, available: textEditor))
+            capabililies.append(Capability(text: "ONLYOFFICE", image: UIImage(named: "onlyoffice")!.resizeImage(size: CGSize(width: 25, height: 25))!, available: onlyofficeEditors))
+            capabililies.append(Capability(text: "Collabora", image: UIImage(named: "collabora")!.resizeImage(size: CGSize(width: 25, height: 25))!, available: !NCGlobal.shared.capabilityRichdocumentsMimetypes.isEmpty))
+            capabililies.append(Capability(text: "User Status", image: UIImage(systemName: "moon")!, available: NCGlobal.shared.capabilityUserStatusEnabled))
+            capabililies.append(Capability(text: "Comments", image: UIImage(systemName: "ellipsis.bubble")!, available: NCGlobal.shared.capabilityFilesComments))
+            capabililies.append(Capability(text: "Lock file", image: UIImage(systemName: "lock")!, available: !NCGlobal.shared.capabilityFilesLockVersion.isEmpty))
+            capabililies.append(Capability(text: "Group folders", image: UIImage(systemName: "person.2")!, available: NCGlobal.shared.capabilityGroupfoldersEnabled))
 
-        var available: Bool = false
-
-        capabililies.removeAll()
-        json = ""
-
-        // FILE SHARING
-        available = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingApiEnabled, exists: false)
-        capabililies.append(Capability(text: "File sharing", image: UIImage(named: "share")!.resizeImage(size: CGSize(width: 25, height: 25))!, available: available))
-
-        // EXTERNAL SITE
-        available = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesExternalSites, exists: true)
-        capabililies.append(Capability(text: "External site", image: UIImage(systemName: "network")!, available: available))
-
-        // E2EE
-        available = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesE2EEEnabled, exists: false)
-        capabililies.append(Capability(text: "End-to-End Encryption", image: UIImage(systemName: "lock")!, available: available))
-
-        // ACTIVITY
-        if NCManageDatabase.shared.getCapabilitiesServerArray(account: account, elements: NCElementsJSON.shared.capabilitiesActivity) == nil {
-            available = false
-        } else {
-            available = true
-        }
-        capabililies.append(Capability(text: "Activity", image: UIImage(systemName: "bolt")!, available: available))
-
-        // NOTIFICATION
-        if NCManageDatabase.shared.getCapabilitiesServerArray(account: account, elements: NCElementsJSON.shared.capabilitiesNotification) == nil {
-            available = false
-        } else {
-            available = true
-        }
-        capabililies.append(Capability(text: "Notification", image: UIImage(systemName: "bell")!, available: available))
-
-        // DELETE FILES
-        available = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFilesUndelete, exists: false)
-        capabililies.append(Capability(text: "Deleted files", image: UIImage(systemName: "trash")!, available: available))
-
-        // TEXT - ONLYOFFICE
-        var textEditor = false
-        var onlyofficeEditors = false
-        if let editors = NCManageDatabase.shared.getDirectEditingEditors(account: account) {
-            for editor in editors {
-                if editor.editor == NCGlobal.shared.editorText {
-                    textEditor = true
-                } else if editor.editor == NCGlobal.shared.editorOnlyoffice {
-                    onlyofficeEditors = true
-                }
-            }
-        }
-        capabililies.append(Capability(text: "Text", image: UIImage(named: "text")!.resizeImage(size: CGSize(width: 25, height: 25))!, available: textEditor))
-        capabililies.append(Capability(text: "ONLYOFFICE", image: UIImage(named: "onlyoffice")!.resizeImage(size: CGSize(width: 25, height: 25))!, available: onlyofficeEditors))
-
-        // COLLABORA
-        if NCManageDatabase.shared.getCapabilitiesServerArray(account: account, elements: NCElementsJSON.shared.capabilitiesRichdocumentsMimetypes) == nil {
-            available = false
-        } else {
-            available = true
-        }
-        capabililies.append(Capability(text: "Collabora", image: UIImage(named: "collabora")!.resizeImage(size: CGSize(width: 25, height: 25))!, available: available))
-
-        // USER STATUS
-        available = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesUserStatusEnabled, exists: false)
-        capabililies.append(Capability(text: "User Status", image: UIImage(systemName: "moon")!, available: available))
-
-        // COMMENTS
-        available = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFilesComments, exists: false)
-        capabililies.append(Capability(text: "Comments", image: UIImage(systemName: "ellipsis.bubble")!, available: available))
-
-        // LOCK FILE
-        let hasLockCapability = NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesFilesLockVersion) >= 1
-        if hasLockCapability {
-            available = false
-        } else {
-            available = true
-        }
-        capabililies.append(Capability(text: "Lock file", image: UIImage(systemName: "lock")!, available: available))
-
-        // GROUP FOLDERS
-        available = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesGroupfoldersEnabled, exists: false)
-        capabililies.append(Capability(text: "Group folders", image: UIImage(systemName: "person.2")!, available: available))
-
-        if let json = NCManageDatabase.shared.getCapabilities(account: account) {
-            self.json = json
+            homeServer = NCUtilityFileSystem.shared.getHomeServer(urlBase: activeAccount.urlBase, userId: activeAccount.userId) + "/"
         }
     }
 }
@@ -183,12 +96,6 @@ struct NCCapabilitiesView: View {
                 Section {
                     CapabilityName(text: capabilitiesViewOO.homeServer, image: Image(uiImage: UIImage(systemName: "house")!))
                 }
-                Section {
-                    ScrollView(.horizontal) {
-                        Text(capabilitiesViewOO.json)
-                            .font(.system(size: 12))
-                    }
-                }
             }
         }
         .frame(maxWidth: .infinity, alignment: .top)

+ 15 - 0
iOSClient/Extensions/Data+Extension.swift

@@ -38,4 +38,19 @@ extension Data {
             print("Error: \(error.localizedDescription)")
         }
     }
+
+    func jsonToString() -> String {
+        do {
+            let json = try JSONSerialization.jsonObject(with: self, options: [])
+            let data = try JSONSerialization.data(withJSONObject: json, options: .prettyPrinted)
+            guard let jsonString = String(data: data, encoding: .utf8) else {
+                print("Inavlid data")
+                return ""
+            }
+            return jsonString
+        } catch {
+            print("Error: \(error.localizedDescription)")
+        }
+        return ""
+    }
 }

+ 67 - 0
iOSClient/Extensions/UILabel+Extension.swift

@@ -0,0 +1,67 @@
+//
+//  UILabel+Extension.swift
+//  Nextcloud
+//
+//  Created by Marino Faggiana on 26/05/23.
+//  Copyright © 2023 Marino Faggiana. All rights reserved.
+//
+//  Author Marino Faggiana <marino.faggiana@nextcloud.com>
+//
+//  This program is free software: you can redistribute it and/or modify
+//  it under the terms of the GNU General Public License as published by
+//  the Free Software Foundation, either version 3 of the License, or
+//  (at your option) any later version.
+//
+//  This program is distributed in the hope that it will be useful,
+//  but WITHOUT ANY WARRANTY; without even the implied warranty of
+//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+//  GNU General Public License for more details.
+//
+//  You should have received a copy of the GNU General Public License
+//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+//
+
+import UIKit
+
+//
+// https://stackoverflow.com/questions/67317975/how-can-i-make-a-padded-uilabel-with-rounded-border-in-ios
+//
+@IBDesignable class PaddedAndBorderedLabel: UILabel {
+
+    @IBInspectable var topInset: CGFloat = 5.0
+    @IBInspectable var bottomInset: CGFloat = 5.0
+    @IBInspectable var leftInset: CGFloat = 7.0
+    @IBInspectable var rightInset: CGFloat = 7.0
+    @IBInspectable var borderColor: UIColor = UIColor.black
+    @IBInspectable var borderWidth: CGFloat = 1
+    @IBInspectable var cornerRadius: CGFloat = 5
+
+    override func drawText(in rect: CGRect) {
+        let insets = UIEdgeInsets(top: topInset, left: leftInset, bottom: bottomInset, right: rightInset)
+        super.drawText(in: rect.inset(by: insets))
+    }
+
+    override var intrinsicContentSize: CGSize {
+        let size = super.intrinsicContentSize
+        return CGSize(width: size.width + leftInset + rightInset,
+              height: size.height + topInset + bottomInset)
+    }
+
+    override func textRect(forBounds bounds: CGRect,
+                           limitedToNumberOfLines n: Int) -> CGRect {
+        let b = bounds
+        let UIEI = UIEdgeInsets(top: topInset, left: leftInset, bottom: bottomInset, right: rightInset)
+        let tr = b.inset(by: UIEI)
+        let ctr = super.textRect(forBounds: tr, limitedToNumberOfLines: 0)
+        // that line of code MUST be LAST in this function, NOT first
+        return ctr
+    }
+
+    override func draw(_ rect: CGRect) {
+        layer.borderColor = borderColor.cgColor
+        layer.borderWidth = borderWidth
+        layer.cornerRadius = cornerRadius
+        layer.masksToBounds = true
+        super.draw(rect)
+    }
+}

+ 15 - 0
iOSClient/Extensions/View+Extension.swift

@@ -5,6 +5,21 @@
 //  Created by Marino Faggiana on 29/12/22.
 //  Copyright © 2022 Marino Faggiana. All rights reserved.
 //
+//  Author Marino Faggiana <marino.faggiana@nextcloud.com>
+//
+//  This program is free software: you can redistribute it and/or modify
+//  it under the terms of the GNU General Public License as published by
+//  the Free Software Foundation, either version 3 of the License, or
+//  (at your option) any later version.
+//
+//  This program is distributed in the hope that it will be useful,
+//  but WITHOUT ANY WARRANTY; without even the implied warranty of
+//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+//  GNU General Public License for more details.
+//
+//  You should have received a copy of the GNU General Public License
+//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
+//
 
 import SwiftUI
 

+ 3 - 3
iOSClient/Main/Collection Common/NCCollectionViewCommon.swift

@@ -981,8 +981,7 @@ class NCCollectionViewCommon: UIViewController, UIGestureRecognizerDelegate, UIS
         self.refreshControl.beginRefreshing()
         self.collectionView.reloadData()
 
-        let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-        if serverVersionMajor >= NCGlobal.shared.nextcloudVersion20 {
+        if NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion20 {
             NCNetworking.shared.unifiedSearchFiles(userBaseUrl: appDelegate, literal: literalSearch) { account, searchProviders in
                 self.providers = searchProviders
                 self.searchResults = []
@@ -1658,7 +1657,8 @@ extension NCCollectionViewCommon: UICollectionViewDataSource {
 
         // ** IMPORT MUST BE AT THE END **
         //
-        if !metadata.isSharable {
+
+        if !metadata.isSharable() {
             cell.hideButtonShare(true)
         }
         

+ 0 - 6
iOSClient/Main/Collection Common/NCGridCell.swift

@@ -22,7 +22,6 @@
 //
 
 import UIKit
-import TagListView
 
 class NCGridCell: UICollectionViewCell, UIGestureRecognizerDelegate, NCCellProtocol, NCTrashCellProtocol {
 
@@ -36,7 +35,6 @@ class NCGridCell: UICollectionViewCell, UIGestureRecognizerDelegate, NCCellProto
     @IBOutlet weak var buttonMore: UIButton!
     @IBOutlet weak var imageVisualEffect: UIVisualEffectView!
     @IBOutlet weak var progressView: UIProgressView!
-    var tagListView: TagListView?
 
     internal var objectId = ""
     private var user = ""
@@ -84,10 +82,6 @@ class NCGridCell: UICollectionViewCell, UIGestureRecognizerDelegate, NCCellProto
         get { return imageFavorite }
         set { imageFavorite = newValue }
     }
-    var cellTagListView: TagListView? {
-        get { return nil}
-        set { tagListView = nil }
-    }
 
     override func awakeFromNib() {
         super.awakeFromNib()

+ 11 - 23
iOSClient/Main/Collection Common/NCListCell.swift

@@ -22,7 +22,6 @@
 //
 
 import UIKit
-import TagListView
 
 class NCListCell: UICollectionViewCell, UIGestureRecognizerDelegate, NCCellProtocol {
 
@@ -39,14 +38,14 @@ class NCListCell: UICollectionViewCell, UIGestureRecognizerDelegate, NCCellProto
     @IBOutlet weak var buttonMore: UIButton!
     @IBOutlet weak var progressView: UIProgressView!
     @IBOutlet weak var separator: UIView!
+    @IBOutlet weak var tag0: UILabel!
+    @IBOutlet weak var tag1: UILabel!
 
     @IBOutlet weak var imageItemLeftConstraint: NSLayoutConstraint!
     @IBOutlet weak var separatorHeightConstraint: NSLayoutConstraint!
     @IBOutlet weak var titleTrailingConstraint: NSLayoutConstraint!
     @IBOutlet weak var infoTrailingConstraint: NSLayoutConstraint!
 
-    @IBOutlet weak var tagListView: TagListView!
-
     private var objectId = ""
     private var user = ""
 
@@ -108,11 +107,7 @@ class NCListCell: UICollectionViewCell, UIGestureRecognizerDelegate, NCCellProto
         get { return separator }
         set { separator = newValue }
     }
-    var cellTagListView: TagListView? {
-        get { return tagListView}
-        set { tagListView = newValue }
-    }
- 
+
     override func awakeFromNib() {
         super.awakeFromNib()
 
@@ -284,26 +279,19 @@ class NCListCell: UICollectionViewCell, UIGestureRecognizerDelegate, NCCellProto
     }
 
     func setTags(tags: [String]) {
-        tagListView.removeAllTags()
         if tags.isEmpty {
-            tagListView.isHidden = true
+            tag0.isHidden = true
+            tag1.isHidden = true
             labelInfo.isHidden = false
         } else {
-            tagListView.isHidden = false
+            tag0.isHidden = false
+            tag1.isHidden = true
             labelInfo.isHidden = true
             if let tag = tags.first {
-                tagListView.addTag(tag)
-                if UIDevice.current.userInterfaceIdiom == .pad {
-                    if tags.count >= 2 {
-                        tagListView.addTag(tags[1])
-                    }
-                    if tags.count > 2 {
-                        tagListView.addTag("+\(tags.count-2)")
-                    }
-                } else {
-                    if tags.count > 1 {
-                        tagListView.addTag("+\(tags.count-1)")
-                    }
+                tag0.text = tag
+                if tags.count > 1 {
+                    tag1.isHidden = false
+                    tag1.text = "+\(tags.count-1)"
                 }
             }
         }

+ 86 - 45
iOSClient/Main/Collection Common/NCListCell.xib

@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="21701" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
-    <device id="retina4_7" orientation="landscape" appearance="light"/>
+    <device id="retina6_0" orientation="landscape" appearance="light"/>
     <dependencies>
         <deployment identifier="iOS"/>
         <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="21678"/>
@@ -19,78 +19,54 @@
                 <autoresizingMask key="autoresizingMask"/>
                 <subviews>
                     <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFill" translatesAutoresizingMaskIntoConstraints="NO" id="w2m-Vw-hpd" userLabel="ImageItem">
-                        <rect key="frame" x="10" y="54" width="40" height="40"/>
+                        <rect key="frame" x="57" y="43.666666666666664" width="40" height="39.999999999999993"/>
                         <constraints>
                             <constraint firstAttribute="height" constant="40" id="Dpd-Xj-z4U"/>
                             <constraint firstAttribute="width" constant="40" id="v0e-MW-EeE"/>
                         </constraints>
                     </imageView>
                     <imageView userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="7Q9-Tv-9yo" userLabel="imageStatus">
-                        <rect key="frame" x="5" y="84" width="15" height="15"/>
+                        <rect key="frame" x="52" y="73.666666666666671" width="15" height="15"/>
                         <constraints>
                             <constraint firstAttribute="width" constant="15" id="f8p-9B-Rgw"/>
                             <constraint firstAttribute="height" constant="15" id="ndy-wW-xdL"/>
                         </constraints>
                     </imageView>
                     <imageView userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="C4K-Nv-phA" userLabel="imageFavorite">
-                        <rect key="frame" x="40" y="49" width="15" height="15"/>
+                        <rect key="frame" x="87" y="38.666666666666664" width="15" height="15"/>
                         <constraints>
                             <constraint firstAttribute="width" constant="15" id="hXC-b9-Q2V"/>
                             <constraint firstAttribute="height" constant="15" id="mPH-zc-eH5"/>
                         </constraints>
                     </imageView>
                     <imageView userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="AyA-hP-r6w" userLabel="imageSelect">
-                        <rect key="frame" x="10" y="61.5" width="25" height="25"/>
+                        <rect key="frame" x="57" y="51" width="25" height="25"/>
                         <constraints>
                             <constraint firstAttribute="width" constant="25" id="bIF-gu-6Jj"/>
                             <constraint firstAttribute="height" constant="25" id="nJa-oj-gcQ"/>
                         </constraints>
                     </imageView>
                     <imageView userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="H4E-G2-C1H" userLabel="imageLocal">
-                        <rect key="frame" x="40" y="84" width="15" height="15"/>
+                        <rect key="frame" x="87" y="73.666666666666671" width="15" height="15"/>
                         <constraints>
                             <constraint firstAttribute="width" constant="15" id="BEs-Rd-5Ov"/>
                             <constraint firstAttribute="height" constant="15" id="N8h-3R-JpE"/>
                         </constraints>
                     </imageView>
                     <label opaque="NO" userInteractionEnabled="NO" tag="101" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Label" lineBreakMode="middleTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="UtT-L6-mgW" userLabel="labelTitle">
-                        <rect key="frame" x="60" y="13" width="519" height="18"/>
+                        <rect key="frame" x="107" y="13" width="425" height="18"/>
                         <fontDescription key="fontDescription" type="system" pointSize="15"/>
                         <color key="textColor" red="0.0" green="0.0" blue="0.0" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
                         <nil key="highlightedColor"/>
                     </label>
                     <label opaque="NO" userInteractionEnabled="NO" tag="102" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Label" lineBreakMode="middleTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="AXX-71-9Q6" userLabel="labelInfo">
-                        <rect key="frame" x="60" y="120" width="519" height="15"/>
+                        <rect key="frame" x="107" y="120" width="425" height="15"/>
                         <fontDescription key="fontDescription" type="system" pointSize="12"/>
                         <color key="textColor" red="0.59999999999999998" green="0.59999999999999998" blue="0.59999999999999998" alpha="1" colorSpace="calibratedRGB"/>
                         <nil key="highlightedColor"/>
                     </label>
-                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="z1r-ZA-ft8" customClass="TagListView" customModule="TagListView">
-                        <rect key="frame" x="60" y="124" width="519" height="15"/>
-                        <color key="backgroundColor" systemColor="systemBackgroundColor"/>
-                        <constraints>
-                            <constraint firstAttribute="height" constant="15" id="9NQ-gM-wQ6"/>
-                        </constraints>
-                        <userDefinedRuntimeAttributes>
-                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
-                                <real key="value" value="8"/>
-                            </userDefinedRuntimeAttribute>
-                            <userDefinedRuntimeAttribute type="number" keyPath="borderWidth">
-                                <real key="value" value="1"/>
-                            </userDefinedRuntimeAttribute>
-                            <userDefinedRuntimeAttribute type="color" keyPath="textColor">
-                                <color key="value" systemColor="systemGrayColor"/>
-                            </userDefinedRuntimeAttribute>
-                            <userDefinedRuntimeAttribute type="color" keyPath="tagBackgroundColor">
-                                <color key="value" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
-                            </userDefinedRuntimeAttribute>
-                            <userDefinedRuntimeAttribute type="color" keyPath="borderColor">
-                                <color key="value" systemColor="systemGray5Color"/>
-                            </userDefinedRuntimeAttribute>
-                        </userDefinedRuntimeAttributes>
-                    </view>
                     <button opaque="NO" alpha="0.29999999999999999" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="system" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="o4u-0K-Qpt" userLabel="buttonShare">
-                        <rect key="frame" x="584" y="45" width="40" height="58"/>
+                        <rect key="frame" x="537" y="34.666666666666664" width="40" height="57.999999999999993"/>
                         <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
                         <constraints>
                             <constraint firstAttribute="height" constant="58" id="WOg-y5-5UA"/>
@@ -101,14 +77,14 @@
                         </connections>
                     </button>
                     <imageView userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="jc6-Vg-TaS" userLabel="imageShared">
-                        <rect key="frame" x="589" y="59" width="30" height="30"/>
+                        <rect key="frame" x="542" y="48.666666666666664" width="30" height="29.999999999999993"/>
                         <constraints>
                             <constraint firstAttribute="height" constant="30" id="Cvy-nZ-zyD"/>
                             <constraint firstAttribute="width" constant="30" id="jfe-Fg-vA8"/>
                         </constraints>
                     </imageView>
                     <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="system" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="yhy-xd-w5C" userLabel="buttonMore">
-                        <rect key="frame" x="629" y="44" width="40" height="60"/>
+                        <rect key="frame" x="582" y="33.666666666666664" width="40" height="59.999999999999993"/>
                         <constraints>
                             <constraint firstAttribute="width" constant="40" id="ZgH-mI-l2k"/>
                             <constraint firstAttribute="height" constant="60" id="woC-64-Tyc"/>
@@ -118,29 +94,87 @@
                         </connections>
                     </button>
                     <imageView userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="dgL-g5-Nkc" userLabel="imageMore">
-                        <rect key="frame" x="636.5" y="61.5" width="25" height="25"/>
+                        <rect key="frame" x="589.66666666666663" y="51" width="25" height="25"/>
                         <constraints>
                             <constraint firstAttribute="width" constant="25" id="05P-NL-pd8"/>
                             <constraint firstAttribute="height" constant="25" id="Jet-eo-x1M"/>
                         </constraints>
                     </imageView>
                     <progressView hidden="YES" opaque="NO" contentMode="scaleToFill" verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="m2p-oJ-j15">
-                        <rect key="frame" x="60" y="137" width="519" height="4"/>
+                        <rect key="frame" x="107" y="116" width="425" height="4"/>
                     </progressView>
                     <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="Egg-cb-EhZ" userLabel="separator">
-                        <rect key="frame" x="50" y="147" width="619" height="1"/>
+                        <rect key="frame" x="97" y="126" width="525" height="1"/>
                         <color key="backgroundColor" white="0.0" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
                         <color key="tintColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
                         <constraints>
                             <constraint firstAttribute="height" constant="1" id="G5S-67-boG"/>
                         </constraints>
                     </view>
+                    <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="tag0" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="qnc-hI-Z9r" customClass="PaddedAndBorderedLabel" customModule="Nextcloud" customModuleProvider="target">
+                        <rect key="frame" x="107" y="101.66666666666667" width="36" height="16.333333333333329"/>
+                        <fontDescription key="fontDescription" type="system" pointSize="12"/>
+                        <color key="textColor" systemColor="systemGrayColor"/>
+                        <nil key="highlightedColor"/>
+                        <userDefinedRuntimeAttributes>
+                            <userDefinedRuntimeAttribute type="number" keyPath="bottomInset">
+                                <real key="value" value="1"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="leftInset">
+                                <real key="value" value="5"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="rightInset">
+                                <real key="value" value="5"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="color" keyPath="borderColor">
+                                <color key="value" systemColor="systemGray5Color"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="borderWidth">
+                                <real key="value" value="1"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                <real key="value" value="8"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="topInset">
+                                <real key="value" value="1"/>
+                            </userDefinedRuntimeAttribute>
+                        </userDefinedRuntimeAttributes>
+                    </label>
+                    <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="tag1" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="jUe-8q-VJd" customClass="PaddedAndBorderedLabel" customModule="Nextcloud" customModuleProvider="target">
+                        <rect key="frame" x="148" y="101.66666666666667" width="34" height="16.333333333333329"/>
+                        <fontDescription key="fontDescription" type="system" pointSize="12"/>
+                        <color key="textColor" systemColor="systemGrayColor"/>
+                        <nil key="highlightedColor"/>
+                        <userDefinedRuntimeAttributes>
+                            <userDefinedRuntimeAttribute type="number" keyPath="bottomInset">
+                                <real key="value" value="1"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="leftInset">
+                                <real key="value" value="5"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="rightInset">
+                                <real key="value" value="5"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="color" keyPath="borderColor">
+                                <color key="value" systemColor="systemGray5Color"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="borderWidth">
+                                <real key="value" value="1"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                <real key="value" value="8"/>
+                            </userDefinedRuntimeAttribute>
+                            <userDefinedRuntimeAttribute type="number" keyPath="topInset">
+                                <real key="value" value="1"/>
+                            </userDefinedRuntimeAttribute>
+                        </userDefinedRuntimeAttributes>
+                    </label>
                 </subviews>
             </view>
             <viewLayoutGuide key="safeArea" id="Gu8-oz-zWa"/>
             <constraints>
+                <constraint firstItem="jUe-8q-VJd" firstAttribute="centerY" secondItem="qnc-hI-Z9r" secondAttribute="centerY" id="2Z4-Yh-1lR"/>
                 <constraint firstItem="Gu8-oz-zWa" firstAttribute="trailing" secondItem="m2p-oJ-j15" secondAttribute="trailing" constant="90" id="2zI-li-v77"/>
-                <constraint firstItem="Gu8-oz-zWa" firstAttribute="trailing" secondItem="z1r-ZA-ft8" secondAttribute="trailing" constant="90" id="467-SN-bxI"/>
                 <constraint firstItem="H4E-G2-C1H" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" constant="-10" id="6fN-Jc-WID"/>
                 <constraint firstItem="Gu8-oz-zWa" firstAttribute="bottom" secondItem="Egg-cb-EhZ" secondAttribute="bottom" id="81D-sw-EaX"/>
                 <constraint firstItem="AXX-71-9Q6" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" constant="10" id="Bxx-kv-KT3"/>
@@ -149,19 +183,21 @@
                 <constraint firstItem="Egg-cb-EhZ" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" id="JCm-UU-Pxu"/>
                 <constraint firstItem="dgL-g5-Nkc" firstAttribute="centerY" secondItem="yhy-xd-w5C" secondAttribute="centerY" id="OMy-Cu-HAx"/>
                 <constraint firstItem="UtT-L6-mgW" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" constant="10" id="PQ8-0b-fLa"/>
-                <constraint firstItem="z1r-ZA-ft8" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" constant="10" id="RJQ-ha-NSq"/>
                 <constraint firstItem="AyA-hP-r6w" firstAttribute="leading" secondItem="Gu8-oz-zWa" secondAttribute="leading" constant="10" id="RYl-cO-cCN"/>
                 <constraint firstItem="Gu8-oz-zWa" firstAttribute="bottom" secondItem="m2p-oJ-j15" secondAttribute="bottom" constant="7" id="SYv-gc-ahx"/>
                 <constraint firstItem="C4K-Nv-phA" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" constant="-10" id="Sof-wy-toF"/>
                 <constraint firstItem="Gu8-oz-zWa" firstAttribute="trailing" secondItem="UtT-L6-mgW" secondAttribute="trailing" constant="90" id="Tq4-bB-YMV"/>
                 <constraint firstItem="H4E-G2-C1H" firstAttribute="top" secondItem="w2m-Vw-hpd" secondAttribute="bottom" constant="-10" id="UWI-r9-vcA"/>
                 <constraint firstItem="dgL-g5-Nkc" firstAttribute="centerX" secondItem="yhy-xd-w5C" secondAttribute="centerX" id="VSJ-7R-Srk"/>
+                <constraint firstItem="Gu8-oz-zWa" firstAttribute="bottom" secondItem="qnc-hI-Z9r" secondAttribute="bottom" constant="9" id="XTs-Qg-kiX"/>
                 <constraint firstItem="7Q9-Tv-9yo" firstAttribute="top" secondItem="w2m-Vw-hpd" secondAttribute="bottom" constant="-10" id="XbB-4a-WpA"/>
                 <constraint firstItem="yhy-xd-w5C" firstAttribute="centerY" secondItem="Gu8-oz-zWa" secondAttribute="centerY" id="ZO7-Ny-L3I"/>
                 <constraint firstItem="m2p-oJ-j15" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" constant="10" id="Zyr-qM-9qP"/>
                 <constraint firstAttribute="bottom" secondItem="AXX-71-9Q6" secondAttribute="bottom" constant="13" id="d06-sn-I3Y"/>
                 <constraint firstItem="jc6-Vg-TaS" firstAttribute="centerX" secondItem="o4u-0K-Qpt" secondAttribute="centerX" id="fAq-0d-u57"/>
+                <constraint firstItem="jUe-8q-VJd" firstAttribute="leading" secondItem="qnc-hI-Z9r" secondAttribute="trailing" constant="5" id="jMG-V1-hgF"/>
                 <constraint firstItem="Gu8-oz-zWa" firstAttribute="trailing" secondItem="Egg-cb-EhZ" secondAttribute="trailing" id="k8f-bU-D6I"/>
+                <constraint firstItem="qnc-hI-Z9r" firstAttribute="leading" secondItem="w2m-Vw-hpd" secondAttribute="trailing" constant="10" id="l6K-6H-QIr"/>
                 <constraint firstItem="w2m-Vw-hpd" firstAttribute="leading" secondItem="Gu8-oz-zWa" secondAttribute="leading" constant="10" id="mBb-ff-7HD"/>
                 <constraint firstItem="w2m-Vw-hpd" firstAttribute="leading" secondItem="7Q9-Tv-9yo" secondAttribute="trailing" constant="-10" id="mon-aq-gcP"/>
                 <constraint firstItem="UtT-L6-mgW" firstAttribute="top" secondItem="Gu8-oz-zWa" secondAttribute="top" constant="13" id="nrY-2F-QZ2"/>
@@ -170,7 +206,6 @@
                 <constraint firstItem="Gu8-oz-zWa" firstAttribute="trailing" secondItem="yhy-xd-w5C" secondAttribute="trailing" id="s2S-RP-cw5"/>
                 <constraint firstItem="AyA-hP-r6w" firstAttribute="centerY" secondItem="Gu8-oz-zWa" secondAttribute="centerY" id="sJp-0x-bdC"/>
                 <constraint firstItem="Gu8-oz-zWa" firstAttribute="trailing" secondItem="o4u-0K-Qpt" secondAttribute="trailing" constant="45" id="tOD-Sd-Uhy"/>
-                <constraint firstAttribute="bottom" secondItem="z1r-ZA-ft8" secondAttribute="bottom" constant="9" id="wfc-n7-tCT"/>
                 <constraint firstItem="jc6-Vg-TaS" firstAttribute="centerY" secondItem="o4u-0K-Qpt" secondAttribute="centerY" id="xnq-6u-TXH"/>
             </constraints>
             <size key="customSize" width="719" height="146"/>
@@ -191,16 +226,22 @@
                 <outlet property="progressView" destination="m2p-oJ-j15" id="yFv-KS-nEy"/>
                 <outlet property="separator" destination="Egg-cb-EhZ" id="uhq-Nc-z8K"/>
                 <outlet property="separatorHeightConstraint" destination="G5S-67-boG" id="B6g-qe-MTb"/>
-                <outlet property="tagListView" destination="z1r-ZA-ft8" id="3mW-9T-7Bm"/>
+                <outlet property="tag0" destination="qnc-hI-Z9r" id="6jJ-lV-0ck"/>
+                <outlet property="tag1" destination="jUe-8q-VJd" id="Wcm-rS-rEd"/>
                 <outlet property="titleTrailingConstraint" destination="Tq4-bB-YMV" id="v4n-j5-ZWT"/>
             </connections>
             <point key="canvasLocation" x="128.18590704647679" y="198.40000000000001"/>
         </collectionViewCell>
     </objects>
+    <designables>
+        <designable name="jUe-8q-VJd">
+            <size key="intrinsicContentSize" width="34" height="16.333333333333336"/>
+        </designable>
+        <designable name="qnc-hI-Z9r">
+            <size key="intrinsicContentSize" width="36" height="16.333333333333336"/>
+        </designable>
+    </designables>
     <resources>
-        <systemColor name="systemBackgroundColor">
-            <color white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
-        </systemColor>
         <systemColor name="systemGray5Color">
             <color red="0.89803921568627454" green="0.89803921568627454" blue="0.91764705882352937" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
         </systemColor>

+ 1 - 1
iOSClient/Main/Collection Common/NCSelectableNavigationView.swift

@@ -128,7 +128,7 @@ extension NCSelectableNavigationView where Self: UIViewController {
 
         actions.append(.openInAction(selectedMetadatas: selectedMetadatas, viewController: self, completion: tapSelect))
 
-        if !isAnyFolder, canUnlock, NCManageDatabase.shared.getCapabilitiesServerInt(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesFilesLockVersion) >= 1 {
+        if !isAnyFolder, canUnlock, !NCGlobal.shared.capabilityFilesLockVersion.isEmpty {
             actions.append(.lockUnlockFiles(shouldLock: !isAnyLocked, metadatas: selectedMetadatas, completion: tapSelect))
         }
 

+ 0 - 457
iOSClient/Main/Create cloud/NCCreateFormUploadAssets.swift

@@ -1,457 +0,0 @@
-//
-//  NCCreateFormUploadAssets.swift
-//  Nextcloud
-//
-//  Created by Marino Faggiana on 14/11/2018.
-//  Copyright © 2018 Marino Faggiana. All rights reserved.
-//
-//  Author Marino Faggiana <marino.faggiana@nextcloud.com>
-//
-//  This program is free software: you can redistribute it and/or modify
-//  it under the terms of the GNU General Public License as published by
-//  the Free Software Foundation, either version 3 of the License, or
-//  (at your option) any later version.
-//
-//  This program is distributed in the hope that it will be useful,
-//  but WITHOUT ANY WARRANTY; without even the implied warranty of
-//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-//  GNU General Public License for more details.
-//
-//  You should have received a copy of the GNU General Public License
-//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
-//
-
-import UIKit
-import Queuer
-import NextcloudKit
-import XLForm
-import Photos
-
-class NCCreateFormUploadAssets: XLFormViewController, NCSelectDelegate {
-
-    var serverUrl: String = ""
-    var titleServerUrl: String?
-    var assets: [PHAsset] = []
-    var cryptated: Bool = false
-    var session: String = ""
-    let requestOptions = PHImageRequestOptions()
-    var imagePreview: UIImage?
-    let targetSizeImagePreview = CGSize(width: 100, height: 100)
-    let appDelegate = UIApplication.shared.delegate as! AppDelegate
-
-    var cellBackgoundColor = UIColor.secondarySystemGroupedBackground
-
-    // MARK: - View Life Cycle
-
-    convenience init(serverUrl: String, assets: [PHAsset], cryptated: Bool, session: String) {
-
-        self.init()
-
-        if serverUrl == NCUtilityFileSystem.shared.getHomeServer(urlBase: appDelegate.urlBase, userId: appDelegate.userId) {
-            titleServerUrl = "/"
-        } else {
-            if let tableDirectory = NCManageDatabase.shared.getTableDirectory(predicate: NSPredicate(format: "account == %@ AND serverUrl == %@", appDelegate.account, serverUrl)) {
-                if let metadata = NCManageDatabase.shared.getMetadataFromOcId(tableDirectory.ocId) {
-                    titleServerUrl = metadata.fileNameView
-                } else { titleServerUrl = (serverUrl as NSString).lastPathComponent }
-            } else { titleServerUrl = (serverUrl as NSString).lastPathComponent }
-        }
-
-        self.serverUrl = serverUrl
-        self.assets = assets
-        self.cryptated = cryptated
-        self.session = session
-
-        requestOptions.resizeMode = PHImageRequestOptionsResizeMode.exact
-        requestOptions.deliveryMode = PHImageRequestOptionsDeliveryMode.highQualityFormat
-        requestOptions.isSynchronous = true
-    }
-
-    override func viewDidLoad() {
-
-        super.viewDidLoad()
-
-        self.title = NSLocalizedString("_upload_photos_videos_", comment: "")
-
-        view.backgroundColor = .systemGroupedBackground
-        tableView.backgroundColor = .systemGroupedBackground
-        cellBackgoundColor = .secondarySystemGroupedBackground
-
-        self.navigationItem.leftBarButtonItem = UIBarButtonItem(title: NSLocalizedString("_cancel_", comment: ""), style: UIBarButtonItem.Style.plain, target: self, action: #selector(cancel))
-        self.navigationItem.rightBarButtonItem = UIBarButtonItem(title: NSLocalizedString("_save_", comment: ""), style: UIBarButtonItem.Style.plain, target: self, action: #selector(save))
-
-        self.tableView.separatorStyle = UITableViewCell.SeparatorStyle.none
-
-        if assets.count == 1 && assets[0].mediaType == PHAssetMediaType.image {
-            PHImageManager.default().requestImage(for: assets[0], targetSize: targetSizeImagePreview, contentMode: PHImageContentMode.aspectFill, options: requestOptions, resultHandler: { image, _ in
-                self.imagePreview = image
-            })
-        }
-
-        initializeForm()
-        reloadForm()
-    }
-
-    // MARK: XLForm
-
-    func initializeForm() {
-
-        let form: XLFormDescriptor = XLFormDescriptor() as XLFormDescriptor
-        form.rowNavigationOptions = XLFormRowNavigationOptions.stopDisableRow
-
-        var section: XLFormSectionDescriptor
-        var row: XLFormRowDescriptor
-
-        // Section: Destination Folder
-
-        section = XLFormSectionDescriptor.formSection(withTitle: NSLocalizedString("_save_path_", comment: ""))
-        form.addFormSection(section)
-
-        row = XLFormRowDescriptor(tag: "ButtonDestinationFolder", rowType: XLFormRowDescriptorTypeButton, title: self.titleServerUrl)
-        row.action.formSelector = #selector(changeDestinationFolder(_:))
-        row.cellConfig["backgroundColor"] = cellBackgoundColor
-
-        row.cellConfig["imageView.image"] = UIImage(named: "folder")!.image(color: NCBrandColor.shared.brandElement, size: 25)
-        row.cellConfig["textLabel.textAlignment"] = NSTextAlignment.right.rawValue
-        row.cellConfig["textLabel.font"] = UIFont.systemFont(ofSize: 15.0)
-        row.cellConfig["textLabel.textColor"] = UIColor.label
-
-        section.addFormRow(row)
-
-        // User folder Autoupload
-        row = XLFormRowDescriptor(tag: "useFolderAutoUpload", rowType: XLFormRowDescriptorTypeBooleanSwitch, title: NSLocalizedString("_use_folder_auto_upload_", comment: ""))
-        row.value = 0
-        row.cellConfig["backgroundColor"] = cellBackgoundColor
-
-        row.cellConfig["textLabel.font"] = UIFont.systemFont(ofSize: 15.0)
-        row.cellConfig["textLabel.textColor"] = UIColor.label
-
-        section.addFormRow(row)
-
-        // Use Sub folder
-        row = XLFormRowDescriptor(tag: "useSubFolder", rowType: XLFormRowDescriptorTypeBooleanSwitch, title: NSLocalizedString("_autoupload_create_subfolder_", comment: ""))
-        let activeAccount = NCManageDatabase.shared.getActiveAccount()
-        if activeAccount?.autoUploadCreateSubfolder == true {
-            row.value = 1
-        } else {
-            row.value = 0
-        }
-        row.hidden = "$\("useFolderAutoUpload") == 0"
-
-        row.cellConfig["textLabel.font"] = UIFont.systemFont(ofSize: 15.0)
-        row.cellConfig["textLabel.textColor"] = UIColor.label
-
-        section.addFormRow(row)
-
-        // Section Mode filename
-
-        section = XLFormSectionDescriptor.formSection(withTitle: NSLocalizedString("_mode_filename_", comment: ""))
-        form.addFormSection(section)
-
-        // Maintain the original fileName
-
-        row = XLFormRowDescriptor(tag: "maintainOriginalFileName", rowType: XLFormRowDescriptorTypeBooleanSwitch, title: NSLocalizedString("_maintain_original_filename_", comment: ""))
-        row.value = CCUtility.getOriginalFileName(NCGlobal.shared.keyFileNameOriginal)
-        row.cellConfig["backgroundColor"] = cellBackgoundColor
-
-        row.cellConfig["textLabel.font"] = UIFont.systemFont(ofSize: 15.0)
-        row.cellConfig["textLabel.textColor"] = UIColor.label
-
-        section.addFormRow(row)
-
-        // Add File Name Type
-
-        row = XLFormRowDescriptor(tag: "addFileNameType", rowType: XLFormRowDescriptorTypeBooleanSwitch, title: NSLocalizedString("_add_filenametype_", comment: ""))
-        row.value = CCUtility.getFileNameType(NCGlobal.shared.keyFileNameType)
-        row.hidden = "$\("maintainOriginalFileName") == 1"
-        row.cellConfig["backgroundColor"] = cellBackgoundColor
-
-        row.cellConfig["textLabel.font"] = UIFont.systemFont(ofSize: 15.0)
-        row.cellConfig["textLabel.textColor"] = UIColor.label
-
-        section.addFormRow(row)
-
-        // Section: Rename File Name
-
-        section = XLFormSectionDescriptor.formSection(withTitle: NSLocalizedString("_filename_", comment: ""))
-        form.addFormSection(section)
-
-        row = XLFormRowDescriptor(tag: "maskFileName", rowType: XLFormRowDescriptorTypeText, title: (NSLocalizedString("_filename_", comment: "")))
-        let fileNameMask: String = CCUtility.getFileNameMask(NCGlobal.shared.keyFileNameMask)
-        if fileNameMask.count > 0 {
-            row.value = fileNameMask
-        }
-        row.hidden = "$\("maintainOriginalFileName") == 1"
-        row.cellConfig["backgroundColor"] = cellBackgoundColor
-
-        row.cellConfig["textLabel.font"] = UIFont.systemFont(ofSize: 15.0)
-        row.cellConfig["textLabel.textColor"] = UIColor.label
-
-        row.cellConfig["textField.textAlignment"] = NSTextAlignment.right.rawValue
-        row.cellConfig["textField.font"] = UIFont.systemFont(ofSize: 15.0)
-        row.cellConfig["textField.textColor"] = UIColor.label
-
-        section.addFormRow(row)
-
-        // Section: Preview File Name
-
-        row = XLFormRowDescriptor(tag: "previewFileName", rowType: XLFormRowDescriptorTypeTextView, title: "")
-        row.height = 180
-        row.disabled = true
-        row.cellConfig["backgroundColor"] = cellBackgoundColor
-
-        row.cellConfig["textView.backgroundColor"] = cellBackgoundColor
-        row.cellConfig["textView.font"] = UIFont.systemFont(ofSize: 14.0)
-        row.cellConfig["textView.textColor"] = UIColor.label
-
-        section.addFormRow(row)
-
-        self.form = form
-    }
-
-    override func formRowDescriptorValueHasChanged(_ formRow: XLFormRowDescriptor!, oldValue: Any!, newValue: Any!) {
-
-        super.formRowDescriptorValueHasChanged(formRow, oldValue: oldValue, newValue: newValue)
-
-        if formRow.tag == "useFolderAutoUpload" {
-
-            if (formRow.value! as AnyObject).boolValue  == true {
-
-                let buttonDestinationFolder: XLFormRowDescriptor  = self.form.formRow(withTag: "ButtonDestinationFolder")!
-                buttonDestinationFolder.hidden = true
-
-            } else {
-
-                let buttonDestinationFolder: XLFormRowDescriptor  = self.form.formRow(withTag: "ButtonDestinationFolder")!
-                buttonDestinationFolder.hidden = false
-            }
-        } else if formRow.tag == "useSubFolder" {
-
-            if (formRow.value! as AnyObject).boolValue  == true {
-
-            } else {
-
-            }
-        } else if formRow.tag == "maintainOriginalFileName" {
-            CCUtility.setOriginalFileName((formRow.value! as AnyObject).boolValue, key: NCGlobal.shared.keyFileNameOriginal)
-            self.reloadForm()
-        } else if formRow.tag == "addFileNameType" {
-            CCUtility.setFileNameType((formRow.value! as AnyObject).boolValue, key: NCGlobal.shared.keyFileNameType)
-            self.reloadForm()
-        } else if formRow.tag == "maskFileName" {
-
-            let fileName = formRow.value as? String
-
-            self.form.delegate = nil
-
-            if let fileName = fileName {
-                formRow.value = CCUtility.removeForbiddenCharactersServer(fileName)
-            }
-
-            self.form.delegate = self
-
-            let previewFileName: XLFormRowDescriptor  = self.form.formRow(withTag: "previewFileName")!
-            previewFileName.value = self.previewFileName(valueRename: formRow.value as? String)
-
-            // reload cell
-            if fileName != nil {
-
-                if newValue as! String != formRow.value as! String {
-
-                    self.reloadFormRow(formRow)
-
-                    let error = NKError(errorCode: NCGlobal.shared.errorCharactersForbidden, errorDescription: "_forbidden_characters_")
-                    NCContentPresenter.shared.showInfo(error: error)
-                }
-            }
-
-            self.reloadFormRow(previewFileName)
-        }
-    }
-
-    func reloadForm() {
-
-        self.form.delegate = nil
-
-        let buttonDestinationFolder: XLFormRowDescriptor  = self.form.formRow(withTag: "ButtonDestinationFolder")!
-        buttonDestinationFolder.title = self.titleServerUrl
-
-        let maskFileName: XLFormRowDescriptor = self.form.formRow(withTag: "maskFileName")!
-        let previewFileName: XLFormRowDescriptor  = self.form.formRow(withTag: "previewFileName")!
-        previewFileName.value = self.previewFileName(valueRename: maskFileName.value as? String)
-
-        self.tableView.reloadData()
-        self.form.delegate = self
-    }
-
-    // MARK: - Action
-
-    func dismissSelect(serverUrl: String?, metadata: tableMetadata?, type: String, items: [Any], overwrite: Bool, copy: Bool, move: Bool) {
-
-        if serverUrl != nil {
-
-            self.serverUrl = serverUrl!
-
-            if serverUrl == NCUtilityFileSystem.shared.getHomeServer(urlBase: appDelegate.urlBase, userId: appDelegate.userId) {
-                self.titleServerUrl = "/"
-            } else {
-                if let tableDirectory = NCManageDatabase.shared.getTableDirectory(predicate: NSPredicate(format: "account == %@ AND serverUrl == %@", appDelegate.account, self.serverUrl)) {
-                    if let metadata = NCManageDatabase.shared.getMetadataFromOcId(tableDirectory.ocId) {
-                        titleServerUrl = metadata.fileNameView
-                    } else { titleServerUrl = (self.serverUrl as NSString).lastPathComponent }
-                } else { titleServerUrl = (self.serverUrl as NSString).lastPathComponent }
-            }
-
-            // Update
-            let row: XLFormRowDescriptor  = self.form.formRow(withTag: "ButtonDestinationFolder")!
-            row.title = self.titleServerUrl
-            self.updateFormRow(row)
-        }
-    }
-
-    @objc func save() {
-
-        DispatchQueue.global().async {
-
-            let useFolderPhotoRow: XLFormRowDescriptor  = self.form.formRow(withTag: "useFolderAutoUpload")!
-            let useSubFolderRow: XLFormRowDescriptor  = self.form.formRow(withTag: "useSubFolder")!
-            var useSubFolder: Bool = false
-            var metadatasNOConflict: [tableMetadata] = []
-            var metadatasUploadInConflict: [tableMetadata] = []
-            let autoUploadPath = NCManageDatabase.shared.getAccountAutoUploadPath(urlBase: self.appDelegate.urlBase, userId: self.appDelegate.userId, account: self.appDelegate.account)
-
-            if (useFolderPhotoRow.value! as AnyObject).boolValue == true {
-                self.serverUrl = NCManageDatabase.shared.getAccountAutoUploadPath(urlBase: self.appDelegate.urlBase, userId: self.appDelegate.userId, account: self.appDelegate.account)
-                useSubFolder = (useSubFolderRow.value! as AnyObject).boolValue
-            }
-
-            if autoUploadPath == self.serverUrl {
-                if !NCNetworking.shared.createFolder(assets: self.assets, selector: NCGlobal.shared.selectorUploadFile, useSubFolder: useSubFolder, account: self.appDelegate.account, urlBase: self.appDelegate.urlBase, userId: self.appDelegate.userId, withPush: false) {
-                    
-                    let error = NKError(errorCode: NCGlobal.shared.errorInternalError, errorDescription: "_error_createsubfolders_upload_")
-                    NCContentPresenter.shared.showError(error: error)
-                    return
-                }
-            }
-
-            for asset in self.assets {
-
-                var serverUrl = self.serverUrl
-                var livePhoto: Bool = false
-                let creationDate = asset.creationDate ?? Date()
-                let fileName = CCUtility.createFileName(asset.originalFilename as String, fileDate: creationDate, fileType: asset.mediaType, keyFileName: NCGlobal.shared.keyFileNameMask, keyFileNameType: NCGlobal.shared.keyFileNameType, keyFileNameOriginal: NCGlobal.shared.keyFileNameOriginal, forcedNewFileName: false)!
-
-                if asset.mediaSubtypes.contains(.photoLive) && CCUtility.getLivePhoto() {
-                    livePhoto = true
-                }
-
-                if useSubFolder {
-                    let dateFormatter = DateFormatter()
-                    dateFormatter.dateFormat = "yyyy"
-                    let yearString = dateFormatter.string(from: creationDate)
-                    dateFormatter.dateFormat = "MM"
-                    let monthString = dateFormatter.string(from: creationDate)
-                    serverUrl = autoUploadPath + "/" + yearString + "/" + monthString
-                }
-
-                // Check if is in upload
-                let isRecordInSessions = NCManageDatabase.shared.getAdvancedMetadatas(predicate: NSPredicate(format: "account == %@ AND serverUrl == %@ AND fileName == %@ AND session != ''", self.appDelegate.account, serverUrl, fileName), sorted: "fileName", ascending: false)
-                if isRecordInSessions.count > 0 { continue }
-
-                let metadataForUpload = NCManageDatabase.shared.createMetadata(account: self.appDelegate.account, user: self.appDelegate.user, userId: self.appDelegate.userId, fileName: fileName, fileNameView: fileName, ocId: NSUUID().uuidString, serverUrl: serverUrl, urlBase: self.appDelegate.urlBase, url: "", contentType: "", isLivePhoto: livePhoto)
-
-                metadataForUpload.assetLocalIdentifier = asset.localIdentifier
-                metadataForUpload.session = self.session
-                metadataForUpload.sessionSelector = NCGlobal.shared.selectorUploadFile
-                metadataForUpload.status = NCGlobal.shared.metadataStatusWaitUpload
-
-                if let result = NCManageDatabase.shared.getMetadataConflict(account: self.appDelegate.account, serverUrl: serverUrl, fileNameView: fileName) {
-                    metadataForUpload.fileName = result.fileName
-                    metadatasUploadInConflict.append(metadataForUpload)
-                } else {
-                    metadatasNOConflict.append(metadataForUpload)
-                }
-            }
-
-            // Verify if file(s) exists
-            if metadatasUploadInConflict.count > 0 {
-
-                DispatchQueue.main.asyncAfter(deadline: .now() + 0.4) {
-                    if let conflict = UIStoryboard(name: "NCCreateFormUploadConflict", bundle: nil).instantiateInitialViewController() as? NCCreateFormUploadConflict {
-
-                        conflict.serverUrl = self.serverUrl
-                        conflict.metadatasNOConflict = metadatasNOConflict
-                        conflict.metadatasUploadInConflict = metadatasUploadInConflict
-                        conflict.delegate = self.appDelegate
-
-                        self.appDelegate.window?.rootViewController?.present(conflict, animated: true, completion: nil)
-                    }
-                }
-
-            } else {
-                NCNetworkingProcessUpload.shared.createProcessUploads(metadatas: metadatasNOConflict, completion: { _ in })
-            }
-
-            DispatchQueue.main.async {self.dismiss(animated: true, completion: nil)  }
-        }
-    }
-
-    @objc func cancel() {
-
-        self.dismiss(animated: true, completion: nil)
-    }
-
-    // MARK: - Utility
-
-    func previewFileName(valueRename: String?) -> String {
-
-        var returnString: String = ""
-        let asset = assets[0]
-        let creationDate = asset.creationDate ?? Date()
-
-        if CCUtility.getOriginalFileName(NCGlobal.shared.keyFileNameOriginal) {
-
-            return (NSLocalizedString("_filename_", comment: "") + ": " + (asset.originalFilename as String))
-
-        } else if let valueRename = valueRename {
-
-            let valueRenameTrimming = valueRename.trimmingCharacters(in: CharacterSet.whitespacesAndNewlines)
-
-            if valueRenameTrimming.count > 0 {
-
-                self.form.delegate = nil
-                CCUtility.setFileNameMask(valueRename, key: NCGlobal.shared.keyFileNameMask)
-                self.form.delegate = self
-
-                returnString = CCUtility.createFileName(asset.originalFilename as String, fileDate: creationDate, fileType: asset.mediaType, keyFileName: NCGlobal.shared.keyFileNameMask, keyFileNameType: NCGlobal.shared.keyFileNameType, keyFileNameOriginal: NCGlobal.shared.keyFileNameOriginal, forcedNewFileName: false)
-
-            } else {
-
-                CCUtility.setFileNameMask("", key: NCGlobal.shared.keyFileNameMask)
-                returnString = CCUtility.createFileName(asset.originalFilename as String, fileDate: creationDate, fileType: asset.mediaType, keyFileName: nil, keyFileNameType: NCGlobal.shared.keyFileNameType, keyFileNameOriginal: NCGlobal.shared.keyFileNameOriginal, forcedNewFileName: false)
-            }
-
-        } else {
-
-            CCUtility.setFileNameMask("", key: NCGlobal.shared.keyFileNameMask)
-            returnString = CCUtility.createFileName(asset.originalFilename as String, fileDate: creationDate, fileType: asset.mediaType, keyFileName: nil, keyFileNameType: NCGlobal.shared.keyFileNameType, keyFileNameOriginal: NCGlobal.shared.keyFileNameOriginal, forcedNewFileName: false)
-        }
-
-        return String(format: NSLocalizedString("_preview_filename_", comment: ""), "MM, MMM, DD, YY, YYYY, HH, hh, mm, ss, ampm") + ":" + "\n\n" + returnString
-    }
-
-    @objc func changeDestinationFolder(_ sender: XLFormRowDescriptor) {
-
-        self.deselectFormRow(sender)
-
-        let storyboard = UIStoryboard(name: "NCSelect", bundle: nil)
-        let navigationController = storyboard.instantiateInitialViewController() as! UINavigationController
-        let viewController = navigationController.topViewController as! NCSelect
-
-        viewController.delegate = self
-        viewController.typeOfCommandView = .selectCreateFolder
-        viewController.includeDirectoryE2EEncryption = true
-
-        self.present(navigationController, animated: true, completion: nil)
-    }
-}

+ 0 - 3
iOSClient/Main/Create cloud/NCUploadAssets.swift

@@ -28,7 +28,6 @@ import Mantis
 import Photos
 import QuickLook
 
-@available(iOS 15, *)
 class NCHostingUploadAssetsView: NSObject {
 
     func makeShipDetailsUI(assets: [TLPHAsset], serverUrl: String, userBaseUrl: NCUserBaseUrl) -> UIViewController {
@@ -146,7 +145,6 @@ class NCUploadAssets: NSObject, ObservableObject, NCCreateFormUploadConflictDele
 
 // MARK: - View
 
-@available(iOS 15, *)
 struct UploadAssetsView: View {
 
     @State private var fileName: String = CCUtility.getFileNameMask(NCGlobal.shared.keyFileNameMask)
@@ -580,7 +578,6 @@ struct UploadAssetsView: View {
 
 // MARK: - Preview
 
-@available(iOS 15, *)
 struct UploadAssetsView_Previews: PreviewProvider {
     static var previews: some View {
         if let appDelegate = UIApplication.shared.delegate as? AppDelegate {

+ 6 - 6
iOSClient/Main/NCActionCenter.swift

@@ -204,20 +204,23 @@ class NCActionCenter: NSObject, UIDocumentInteractionControllerDelegate, NCSelec
 
                 let shareNavigationController = UIStoryboard(name: "NCShare", bundle: nil).instantiateInitialViewController() as? UINavigationController
                 let shareViewController = shareNavigationController?.topViewController as? NCSharePaging
-                let activity = NCManageDatabase.shared.getCapabilitiesServerArray(account: metadata.account, elements: NCElementsJSON.shared.capabilitiesActivity)
 
                 for value in NCBrandOptions.NCInfoPagingTab.allCases {
                     pages.append(value)
                 }
 
-                if activity == nil, let idx = pages.firstIndex(of: .activity) {
+                if NCGlobal.shared.capabilityActivity.isEmpty, let idx = pages.firstIndex(of: .activity) {
                     pages.remove(at: idx)
                 }
-                if !metadata.isSharable, let idx = pages.firstIndex(of: .sharing) {
+                if !metadata.isSharable(), let idx = pages.firstIndex(of: .sharing) {
                     pages.remove(at: idx)
                 }
+
                 (pages, page) = NCApplicationHandle().filterPages(pages: pages, page: page, metadata: metadata)
 
+                shareViewController?.pages = pages
+                shareViewController?.metadata = metadata
+
                 if pages.contains(page) {
                     shareViewController?.page = page
                 } else if let page = pages.first {
@@ -226,9 +229,6 @@ class NCActionCenter: NSObject, UIDocumentInteractionControllerDelegate, NCSelec
                     return
                 }
 
-                shareViewController?.pages = pages
-                shareViewController?.metadata = metadata
-
                 shareNavigationController?.modalPresentationStyle = .formSheet
                 if let shareNavigationController = shareNavigationController {
                     viewController.present(shareNavigationController, animated: true, completion: nil)

+ 0 - 6
iOSClient/Main/NCCellProtocol.swift

@@ -22,7 +22,6 @@
 //
 
 import UIKit
-import TagListView
 
 protocol NCCellProtocol {
 
@@ -40,7 +39,6 @@ protocol NCCellProtocol {
     var fileSharedImage: UIImageView? { get set }
     var fileMoreImage: UIImageView? { get set }
     var cellSeparatorView: UIView? { get set }
-    var cellTagListView: TagListView? { get set }
 
     func titleInfoTrailingDefault()
     func titleInfoTrailingFull()
@@ -107,10 +105,6 @@ extension NCCellProtocol {
         get { return nil }
         set {}
     }
-    var cellTagListView: TagListView? {
-        get { return nil }
-        set {}
-    }
 
     func titleInfoTrailingDefault() {}
     func titleInfoTrailingFull() {}

+ 3 - 12
iOSClient/Main/NCPickerViewController.swift

@@ -46,18 +46,9 @@ class NCPhotosPickerViewController: NSObject {
 
         self.openPhotosPickerViewController { assets in
             if !assets.isEmpty {
-                if #available(iOS 15, *) {
-                    let vc = NCHostingUploadAssetsView().makeShipDetailsUI(assets: assets, serverUrl: self.appDelegate.activeServerUrl, userBaseUrl: self.appDelegate)
-                    DispatchQueue.main.asyncAfter(deadline: .now() + 0.4) {
-                        viewController.present(vc, animated: true, completion: nil)
-                    }
-                } else {
-                    let assets = assets.compactMap { $0.phAsset }
-                    let vc = NCCreateFormUploadAssets(serverUrl: self.appDelegate.activeServerUrl, assets: assets, cryptated: false, session: NCNetworking.shared.sessionIdentifierBackground)
-                    let navigationController = UINavigationController(rootViewController: vc)
-                    DispatchQueue.main.asyncAfter(deadline: .now() + 0.4) {
-                        viewController.present(navigationController, animated: true, completion: nil)
-                    }
+                let vc = NCHostingUploadAssetsView().makeShipDetailsUI(assets: assets, serverUrl: self.appDelegate.activeServerUrl, userBaseUrl: self.appDelegate)
+                DispatchQueue.main.asyncAfter(deadline: .now() + 0.4) {
+                    viewController.present(vc, animated: true, completion: nil)
                 }
             }
         }

+ 3 - 4
iOSClient/Menu/AppDelegate+Menu.swift

@@ -37,7 +37,6 @@ extension AppDelegate {
         let directEditingCreators = NCManageDatabase.shared.getDirectEditingCreators(account: appDelegate.account)
         let isDirectoryE2EE = NCUtility.shared.isDirectoryE2EE(serverUrl: appDelegate.activeServerUrl, userBase: appDelegate)
         let directory = NCManageDatabase.shared.getTableDirectory(predicate: NSPredicate(format: "account == %@ AND serverUrl == %@", appDelegate.account, appDelegate.activeServerUrl))
-        let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
         let serverUrlHome = NCUtilityFileSystem.shared.getHomeServer(urlBase: appDelegate.urlBase, userId: appDelegate.userId)
 
 
@@ -148,7 +147,7 @@ extension AppDelegate {
             actions.append(.seperator(order: 0))
         }
 
-        if serverVersionMajor >= NCGlobal.shared.nextcloudVersion18 && directory?.richWorkspace == nil && !isDirectoryE2EE && NextcloudKit.shared.isNetworkReachable() {
+        if NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion18 && directory?.richWorkspace == nil && !isDirectoryE2EE && NextcloudKit.shared.isNetworkReachable() {
             actions.append(
                 NCMenuAction(
                     title: NSLocalizedString("_add_folder_info_", comment: ""), icon: UIImage(named: "addFolderInfo")!.image(color: UIColor.systemGray, size: 50), action: { _ in
@@ -234,8 +233,8 @@ extension AppDelegate {
             )
         }
 
-        if let richdocumentsMimetypes = NCManageDatabase.shared.getCapabilitiesServerArray(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesRichdocumentsMimetypes) {
-            if richdocumentsMimetypes.count > 0 &&  NextcloudKit.shared.isNetworkReachable() && !isDirectoryE2EE {
+        if !NCGlobal.shared.capabilityRichdocumentsMimetypes.isEmpty {
+            if NextcloudKit.shared.isNetworkReachable() && !isDirectoryE2EE {
                 actions.append(
                     NCMenuAction(
                         title: NSLocalizedString("_create_new_document_", comment: ""), icon: UIImage(named: "create_file_document")!, action: { _ in

+ 1 - 2
iOSClient/Menu/NCCollectionViewCommon+Menu.swift

@@ -140,8 +140,7 @@ extension NCCollectionViewCommon {
         //
         // LOCK / UNLOCK
         //
-        let hasLockCapability = NCManageDatabase.shared.getCapabilitiesServerInt(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesFilesLockVersion) >= 1
-        if !metadata.directory, metadata.canUnlock(as: appDelegate.userId), hasLockCapability {
+        if !metadata.directory, metadata.canUnlock(as: appDelegate.userId), !NCGlobal.shared.capabilityFilesLockVersion.isEmpty {
             actions.append(NCMenuAction.lockUnlockFiles(shouldLock: !metadata.lock, metadatas: [metadata], order: 30))
         }
 

+ 1 - 2
iOSClient/Menu/UIViewController+Menu.swift

@@ -62,8 +62,7 @@ extension UIViewController {
     func showProfileMenu(userId: String) {
 
         guard let appDelegate = UIApplication.shared.delegate as? AppDelegate else { return }
-        let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
-        guard serverVersionMajor >= NCGlobal.shared.nextcloudVersion23 else { return }
+        guard NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion23 else { return }
 
         NextcloudKit.shared.getHovercard(for: userId) { account, card, _, _ in
             guard let card = card, account == appDelegate.account else { return }

+ 13 - 18
iOSClient/More/NCMore.swift

@@ -88,7 +88,6 @@ class NCMore: UIViewController, UITableViewDelegate, UITableViewDataSource {
 
         var item = NKExternalSite()
         var quota: String = ""
-        let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
 
         // Clear
         functionMenu.removeAll()
@@ -131,8 +130,7 @@ class NCMore: UIViewController, UITableViewDelegate, UITableViewDataSource {
         functionMenu.append(item)
 
         // ITEM : Shares
-        let isFilesSharingEnabled = NCManageDatabase.shared.getCapabilitiesServerBool(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesFileSharingApiEnabled, exists: false)
-        if isFilesSharingEnabled {
+        if NCGlobal.shared.capabilityFileSharingApiEnabled {
             item = NKExternalSite()
             item.name = "_list_shares_"
             item.icon = "share"
@@ -150,8 +148,7 @@ class NCMore: UIViewController, UITableViewDelegate, UITableViewDataSource {
         functionMenu.append(item)
 
         // ITEM : Groupfolders
-        let hasAccessibleGroupFolders = NCManageDatabase.shared.getCapabilitiesServerBool(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesGroupfoldersEnabled, exists: false)
-        if hasAccessibleGroupFolders {
+        if NCGlobal.shared.capabilityGroupfoldersEnabled {
             item = NKExternalSite()
             item.name = "_group_folders_"
             item.icon = "person.2"
@@ -168,7 +165,7 @@ class NCMore: UIViewController, UITableViewDelegate, UITableViewDataSource {
         functionMenu.append(item)
 
         // ITEM : Trash
-        if serverVersionMajor >= NCGlobal.shared.nextcloudVersion15 {
+        if NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion15 {
             item = NKExternalSite()
             item.name = "_trash_view_"
             item.icon = "trash"
@@ -358,18 +355,16 @@ class NCMore: UIViewController, UITableViewDelegate, UITableViewDataSource {
             cell.backgroundColor = .secondarySystemGroupedBackground
             cell.accessoryType = UITableViewCell.AccessoryType.disclosureIndicator
 
-            if NCManageDatabase.shared.getCapabilitiesServerBool(account: appDelegate.account, elements: NCElementsJSON.shared.capabilitiesUserStatusEnabled, exists: false) {
-                if let account = NCManageDatabase.shared.getAccount(predicate: NSPredicate(format: "account == %@", appDelegate.account)) {
-                    let status = NCUtility.shared.getUserStatus(userIcon: account.userStatusIcon, userStatus: account.userStatusStatus, userMessage: account.userStatusMessage)
-                    cell.icon.image = status.onlineStatus
-                    cell.status.text = status.statusMessage
-                    cell.status.textColor = .label
-                    cell.status.trailingBuffer = cell.status.frame.width
-                    if cell.status.labelShouldScroll() {
-                        cell.status.tapToScroll = true
-                    } else {
-                        cell.status.tapToScroll = false
-                    }
+            if NCGlobal.shared.capabilityUserStatusEnabled, let account = NCManageDatabase.shared.getAccount(predicate: NSPredicate(format: "account == %@", appDelegate.account)) {
+                let status = NCUtility.shared.getUserStatus(userIcon: account.userStatusIcon, userStatus: account.userStatusStatus, userMessage: account.userStatusMessage)
+                cell.icon.image = status.onlineStatus
+                cell.status.text = status.statusMessage
+                cell.status.textColor = .label
+                cell.status.trailingBuffer = cell.status.frame.width
+                if cell.status.labelShouldScroll() {
+                    cell.status.tapToScroll = true
+                } else {
+                    cell.status.tapToScroll = false
                 }
             }
             

+ 37 - 0
iOSClient/NCGlobal.swift

@@ -22,6 +22,7 @@
 //
 
 import UIKit
+import SwiftyJSON
 
 class NCGlobal: NSObject {
     @objc static let shared: NCGlobal = {
@@ -404,4 +405,40 @@ class NCGlobal: NSObject {
     let configuration_disable_manage_account                    = "disable_manage_account"
     let configuration_disable_more_external_site                = "disable_more_external_site"
     let configuration_disable_openin_file                       = "disable_openin_file"
+
+    // CAPABILITIES
+    //
+    var capabilityServerVersionMajor: Int                       = 0
+    @objc var capabilityServerVersion: String                   = ""
+    
+    var capabilityFileSharingApiEnabled: Bool                   = false
+    var capabilityFileSharingPubPasswdEnforced: Bool            = false
+    var capabilityFileSharingPubExpireDateEnforced: Bool        = false
+    var capabilityFileSharingPubExpireDateDays: Int             = 0
+    var capabilityFileSharingInternalExpireDateEnforced: Bool   = false
+    var capabilityFileSharingInternalExpireDateDays: Int        = 0
+    var capabilityFileSharingRemoteExpireDateEnforced: Bool     = false
+    var capabilityFileSharingRemoteExpireDateDays: Int          = 0
+    var capabilityFileSharingDefaultPermission: Int             = 0
+
+    var capabilityThemingColor: String                          = ""
+    var capabilityThemingColorElement: String                   = ""
+    var capabilityThemingColorText: String                      = ""
+    @objc var capabilityThemingName: String                     = ""
+    @objc var capabilityThemingSlogan: String                   = ""
+
+    @objc var capabilityE2EEEnabled: Bool                       = false
+    @objc var capabilityE2EEApiVersion: String                  = ""
+
+    var capabilityRichdocumentsMimetypes: [String]              = []
+    var capabilityActivity: [String]                            = []
+    var capabilityNotification: [String]                        = []
+
+    var capabilityFilesUndelete: Bool                           = false
+    var capabilityFilesLockVersion: String                      = ""    // NC 24
+    var capabilityFilesComments: Bool                           = false // NC 20
+
+    @objc var capabilityUserStatusEnabled: Bool                 = false
+    var capabilityExternalSites: Bool                           = false
+    var capabilityGroupfoldersEnabled: Bool                     = false // NC27
 }

+ 1 - 2
iOSClient/Networking/E2EE/NCEndToEndMetadata.swift

@@ -202,7 +202,6 @@ class NCEndToEndMetadata: NSObject {
             return (0, "", NKError(errorCode: NCGlobal.shared.errorE2EE, errorDescription: "Error decoding JSON"))
         }
 
-        let versionE2EE = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesE2EEApiVersion) ?? ""
         data.printJson()
 
         let decoder = JSONDecoder()
@@ -212,7 +211,7 @@ class NCEndToEndMetadata: NSObject {
         } else if (try? decoder.decode(E2eeV12.self, from: data)) != nil {
             return decoderMetadataV12(json, serverUrl: serverUrl, account: account, urlBase: urlBase, userId: userId, ownerId: ownerId)
         } else {
-            return (0, "", NKError(errorCode: NCGlobal.shared.errorInternalError, errorDescription: "Server E2EE version " + versionE2EE + ", not compatible"))
+            return (0, "", NKError(errorCode: NCGlobal.shared.errorInternalError, errorDescription: "Server E2EE version " + NCGlobal.shared.capabilityE2EEApiVersion + ", not compatible"))
         }
     }
 

+ 1 - 3
iOSClient/Networking/E2EE/NCNetworkingE2EE.swift

@@ -33,9 +33,7 @@ class NCNetworkingE2EE: NSObject {
 
     func isE2EEVersionWriteable(account: String) -> NKError? {
 
-        let versionE2EE = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesE2EEApiVersion) ?? ""
-
-        if NCGlobal.shared.e2eeReadVersions.last == versionE2EE {
+        if NCGlobal.shared.e2eeReadVersions.last == NCGlobal.shared.capabilityE2EEApiVersion {
             return nil
         }
         

+ 1 - 2
iOSClient/Networking/NCNetworkingCheckRemoteUser.swift

@@ -27,7 +27,6 @@ class NCNetworkingCheckRemoteUser {
 
     func checkRemoteUser(account: String, error: NKError) {
 
-        let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
         guard let tableAccount = NCManageDatabase.shared.getAccount(predicate: NSPredicate(format: "account == %@", account)) else {
             return
         }
@@ -40,7 +39,7 @@ class NCNetworkingCheckRemoteUser {
 
         // -----------------------
 
-        if serverVersionMajor >= NCGlobal.shared.nextcloudVersion17 {
+        if NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion17 {
 
             let token = CCUtility.getPassword(account)!
             if token.isEmpty {

+ 12 - 20
iOSClient/Networking/NCService.swift

@@ -177,34 +177,30 @@ class NCService: NSObject {
                 return
             }
 
+            data.printJson()
+            
             NCManageDatabase.shared.addCapabilitiesJSon(data, account: account)
-            let serverVersionMajor = NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesVersionMajor)
+            NCManageDatabase.shared.setCapabilities(account: account, data: data)
 
             // Setup communication
-            if serverVersionMajor > 0 {
-                NextcloudKit.shared.setup(nextcloudVersion: serverVersionMajor)
+            if NCGlobal.shared.capabilityServerVersionMajor > 0 {
+                NextcloudKit.shared.setup(nextcloudVersion: NCGlobal.shared.capabilityServerVersionMajor)
             }
 
             // Theming
-            let themingColorNew = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesThemingColor)
-            let themingColorElementNew = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesThemingColorElement)
-            let themingColorTextNew = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesThemingColorText)
-            if themingColorNew != NCBrandColor.shared.themingColor || themingColorElementNew != NCBrandColor.shared.themingColorElement || themingColorTextNew != NCBrandColor.shared.themingColorText {
+            if NCGlobal.shared.capabilityThemingColor != NCBrandColor.shared.themingColor || NCGlobal.shared.capabilityThemingColorElement != NCBrandColor.shared.themingColorElement || NCGlobal.shared.capabilityThemingColorText != NCBrandColor.shared.themingColorText {
                 NCBrandColor.shared.settingThemingColor(account: account)
             }
 
             // Sharing & Comments
-            let isFilesSharingEnabled = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingApiEnabled, exists: false)
-            let comments = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFilesComments, exists: false)
-            let activity = NCManageDatabase.shared.getCapabilitiesServerArray(account: account, elements: NCElementsJSON.shared.capabilitiesActivity)
-            if !isFilesSharingEnabled && !comments && activity == nil {
+            if !NCGlobal.shared.capabilityFileSharingApiEnabled && !NCGlobal.shared.capabilityFilesComments && NCGlobal.shared.capabilityActivity.isEmpty {
                 self.appDelegate.disableSharesView = true
             } else {
                 self.appDelegate.disableSharesView = false
             }
 
             // Text direct editor detail
-            if serverVersionMajor >= NCGlobal.shared.nextcloudVersion18 {
+            if NCGlobal.shared.capabilityServerVersionMajor >= NCGlobal.shared.nextcloudVersion18 {
                 let options = NKRequestOptions(queue: NextcloudKit.shared.nkCommonInstance.backgroundQueue)
                 NextcloudKit.shared.NCTextObtainEditorDetails(options: options) { account, editors, creators, data, error in
                     if error == .success && account == self.appDelegate.account {
@@ -214,8 +210,7 @@ class NCService: NSObject {
             }
 
             // External file Server
-            let isExternalSitesServerEnabled = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesExternalSites, exists: true)
-            if isExternalSitesServerEnabled {
+            if NCGlobal.shared.capabilityExternalSites {
                 NextcloudKit.shared.getExternalSite(options: options) { account, externalSites, data, error in
                     if error == .success && account == self.appDelegate.account {
                         NCManageDatabase.shared.deleteExternalSites(account: account)
@@ -229,8 +224,7 @@ class NCService: NSObject {
             }
 
             // User Status
-            let userStatus = NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesUserStatusEnabled, exists: false)
-            if userStatus {
+            if NCGlobal.shared.capabilityUserStatusEnabled {
                 NextcloudKit.shared.getUserStatus(options: options) { account, clearAt, icon, message, messageId, messageIsPredefined, status, statusIsUserDefined, userId, data, error in
                     if error == .success && account == self.appDelegate.account && userId == self.appDelegate.userId {
                         NCManageDatabase.shared.setAccountUserStatus(userStatusClearAt: clearAt, userStatusIcon: icon, userStatusMessage: message, userStatusMessageId: messageId, userStatusMessageIsPredefined: messageIsPredefined, userStatusStatus: status, userStatusStatusIsUserDefined: statusIsUserDefined, account: account)
@@ -239,10 +233,8 @@ class NCService: NSObject {
             }
 
             // Added UTI for Collabora
-            if let richdocumentsMimetypes = NCManageDatabase.shared.getCapabilitiesServerArray(account: account, elements: NCElementsJSON.shared.capabilitiesRichdocumentsMimetypes) {
-                for mimeType in richdocumentsMimetypes {
-                    NextcloudKit.shared.nkCommonInstance.addInternalTypeIdentifier(typeIdentifier: mimeType, classFile: NKCommon.TypeClassFile.document.rawValue, editor: NCGlobal.shared.editorCollabora, iconName: NKCommon.TypeIconFile.document.rawValue, name: "document")
-                }
+            for mimeType in NCGlobal.shared.capabilityRichdocumentsMimetypes {
+                NextcloudKit.shared.nkCommonInstance.addInternalTypeIdentifier(typeIdentifier: mimeType, classFile: NKCommon.TypeClassFile.document.rawValue, editor: NCGlobal.shared.editorCollabora, iconName: NKCommon.TypeIconFile.document.rawValue, name: "document")
             }
 
             // Added UTI for ONLYOFFICE & Text

+ 2 - 6
iOSClient/Scan document/NCUploadScanDocument.swift

@@ -452,9 +452,7 @@ struct UploadScanDocumentView: View {
                         }
                     }
                     .complexModifier { view in
-                        if #available(iOS 15, *) {
-                            view.listRowSeparator(.hidden)
-                        }
+                        view.listRowSeparator(.hidden)
                     }
 
                     VStack(spacing: 20) {
@@ -499,9 +497,7 @@ struct UploadScanDocumentView: View {
                             .frame(maxWidth: .infinity, minHeight: geo.size.height / 2)
                     }
                     .complexModifier { view in
-                        if #available(iOS 15, *) {
-                            view.listRowSeparator(.hidden)
-                        }
+                        view.listRowSeparator(.hidden)
                     }
                 }
                 HUDView(showHUD: $uploadScanDocument.showHUD, textLabel: NSLocalizedString("_wait_", comment: ""), image: "doc.badge.arrow.up")

+ 1 - 85
iOSClient/Settings/CCManageAccount.m

@@ -103,7 +103,7 @@
         
         // Set user status
         
-        BOOL userStatus = [[NCManageDatabase shared] getCapabilitiesServerBoolWithAccount:activeAccount.account elements:NCElementsJSON.shared.capabilitiesUserStatusEnabled exists:false];
+        BOOL userStatus = [[NCGlobal shared] capabilityUserStatusEnabled];
         if (userStatus) {
             row = [XLFormRowDescriptor formRowDescriptorWithTag:@"setUserStatus" rowType:XLFormRowDescriptorTypeButton title:NSLocalizedString(@"_set_user_status_", nil)];
             row.cellConfigAtConfigure[@"backgroundColor"] = UIColor.secondarySystemGroupedBackgroundColor;
@@ -257,90 +257,6 @@
         [section addFormRow:row];
     }
     
-    // Section : THIRT PART -------------------------------------------
-    BOOL isHandwerkcloudEnabled = [[NCManageDatabase shared] getCapabilitiesServerBoolWithAccount:activeAccount.account elements:NCElementsJSON.shared.capabilitiesHWCEnabled exists:false];
-    if (isHandwerkcloudEnabled) {
-
-        section = [XLFormSectionDescriptor formSectionWithTitle:NSLocalizedString(@"_user_job_", nil)];
-        [form addFormSection:section];
-        
-        // Business Type
-        row = [XLFormRowDescriptor formRowDescriptorWithTag:@"userbusinesstype" rowType:XLFormRowDescriptorTypeInfo title:NSLocalizedString(@"_user_businesstype_", nil)];
-        row.cellConfigAtConfigure[@"backgroundColor"] = UIColor.secondarySystemGroupedBackgroundColor;
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"textLabel.font"];
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"detailTextLabel.font"];
-        [row.cellConfig setObject:UIColor.labelColor forKey:@"textLabel.textColor"];
-        [row.cellConfig setObject:[[UIImage imageNamed:@"businesstype"] imageWithColor:UIColor.systemGrayColor size:25] forKey:@"imageView.image"];
-        row.value = activeAccount.businessType;
-        [section addFormRow:row];
-        
-        // Business Size
-        row = [XLFormRowDescriptor formRowDescriptorWithTag:@"userbusinesssize" rowType:XLFormRowDescriptorTypeInfo title:NSLocalizedString(@"_user_businesssize_", nil)];
-        row.cellConfigAtConfigure[@"backgroundColor"] = UIColor.secondarySystemGroupedBackgroundColor;
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"textLabel.font"];
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"detailTextLabel.font"];
-        [row.cellConfig setObject:UIColor.labelColor forKey:@"textLabel.textColor"];
-        [row.cellConfig setObject:[[UIImage imageNamed:@"users"] imageWithColor:UIColor.systemGrayColor size:25] forKey:@"imageView.image"];
-        row.value = activeAccount.businessSize;
-        [section addFormRow:row];
-        
-        // Role
-        row = [XLFormRowDescriptor formRowDescriptorWithTag:@"userrole" rowType:XLFormRowDescriptorTypeInfo title:NSLocalizedString(@"_user_role_", nil)];
-        row.cellConfigAtConfigure[@"backgroundColor"] = UIColor.secondarySystemGroupedBackgroundColor;
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"textLabel.font"];
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"detailTextLabel.font"];
-        [row.cellConfig setObject:UIColor.labelColor forKey:@"textLabel.textColor"];
-        [row.cellConfig setObject:[[UIImage imageNamed:@"role"] imageWithColor:UIColor.systemGrayColor size:25] forKey:@"imageView.image"];
-        if ([activeAccount.role isEqualToString:@"owner"]) row.value = NSLocalizedString(@"_user_owner_", nil);
-        else if ([activeAccount.role isEqualToString:@"employee"]) row.value = NSLocalizedString(@"_user_employee_", nil);
-        else if ([activeAccount.role isEqualToString:@"contractor"]) row.value = NSLocalizedString(@"_user_contractor_", nil);
-        else row.value = @"";
-        [section addFormRow:row];
-        
-        // Company
-        row = [XLFormRowDescriptor formRowDescriptorWithTag:@"usercompany" rowType:XLFormRowDescriptorTypeInfo title:NSLocalizedString(@"_user_company_", nil)];
-        row.cellConfigAtConfigure[@"backgroundColor"] = UIColor.secondarySystemGroupedBackgroundColor;
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"textLabel.font"];
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"detailTextLabel.font"];
-        [row.cellConfig setObject:UIColor.labelColor forKey:@"textLabel.textColor"];
-        [row.cellConfig setObject:[[UIImage imageNamed:@"company"] imageWithColor:UIColor.systemGrayColor size:25] forKey:@"imageView.image"];
-        row.value = activeAccount.organisation;
-        [section addFormRow:row];
-    
-        if (activeAccount.hcIsTrial) {
-        
-            section = [XLFormSectionDescriptor formSectionWithTitle:NSLocalizedString(@"_trial_", nil)];
-            [form addFormSection:section];
-            
-            row = [XLFormRowDescriptor formRowDescriptorWithTag:@"trial" rowType:XLFormRowDescriptorTypeInfo title:NSLocalizedString(@"_trial_expired_day_", nil)];
-            row.cellConfigAtConfigure[@"backgroundColor"] = UIColor.secondarySystemGroupedBackgroundColor;
-            [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"textLabel.font"];
-            [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"detailTextLabel.font"];
-            [row.cellConfig setObject:[UIColor redColor] forKey:@"textLabel.textColor"];
-            [row.cellConfig setObject:[UIColor redColor] forKey:@"detailTextLabel.textColor"];
-            [row.cellConfig setObject:[[UIImage imageNamed:@"timer"] imageWithColor:UIColor.systemGrayColor size:25] forKey:@"imageView.image"];
-            NSInteger numberOfDays = activeAccount.hcTrialRemainingSec / (24*3600);
-            row.value = [@(numberOfDays) stringValue];
-            [section addFormRow:row];
-        }
-    
-        section = [XLFormSectionDescriptor formSection];
-        [form addFormSection:section];
-        
-        // Edit profile
-        row = [XLFormRowDescriptor formRowDescriptorWithTag:@"editUserProfile" rowType:XLFormRowDescriptorTypeButton title:NSLocalizedString(@"_user_editprofile_", nil)];
-        row.cellConfigAtConfigure[@"backgroundColor"] = UIColor.secondarySystemGroupedBackgroundColor;
-        [row.cellConfig setObject:[UIFont systemFontOfSize:15.0] forKey:@"textLabel.font"];
-        [row.cellConfig setObject:[[UIImage imageNamed:@"editUserProfile"] imageWithColor:UIColor.systemGrayColor size:25] forKey:@"imageView.image"];
-        [row.cellConfig setObject:@(NSTextAlignmentLeft) forKey:@"textLabel.textAlignment"];
-        [row.cellConfig setObject:UIColor.labelColor forKey:@"textLabel.textColor"];
-#if defined(HC)
-        row.action.viewControllerClass = [HCEditProfile class];
-#endif
-        if (accounts.count == 0) row.disabled = @YES;
-        [section addFormRow:row];
-    }
-    
     self.tableView.showsVerticalScrollIndicator = NO;
     self.form = form;
     

+ 8 - 10
iOSClient/Settings/NCManageE2EE.swift

@@ -164,15 +164,13 @@ struct NCViewE2EE: View {
 
     var body: some View {
 
-        let versionE2EE = NCManageDatabase.shared.getCapabilitiesServerString(account: account, elements: NCElementsJSON.shared.capabilitiesE2EEApiVersion) ?? ""
-
         VStack {
 
             if manageE2EE.isEndToEndEnabled {
 
                 List {
 
-                    Section(header: Text(""), footer: Text(manageE2EE.statusOfService + "\n\n" + "End-to-End Encryption " + versionE2EE)) {
+                    Section(header: Text(""), footer: Text(manageE2EE.statusOfService + "\n\n" + "End-to-End Encryption " + NCGlobal.shared.capabilityE2EEApiVersion)) {
                         Label {
                             Text(NSLocalizedString("_e2e_settings_activated_", comment: ""))
                         } icon: {
@@ -196,10 +194,10 @@ struct NCViewE2EE: View {
                     }
                     .contentShape(Rectangle())
                     .onTapGesture {
-                        if CCUtility.getPasscode().isEmpty {
-                            NCContentPresenter.shared.showInfo(error: NKError(errorCode: 0, errorDescription: "_e2e_settings_lock_not_active_"))
-                        } else {
+                        if let passcode = CCUtility.getPasscode(), !passcode.isEmpty {
                             manageE2EE.requestPasscodeType("readPassphrase")
+                        } else {
+                            NCContentPresenter.shared.showInfo(error: NKError(errorCode: 0, errorDescription: "_e2e_settings_lock_not_active_"))
                         }
                     }
 
@@ -216,10 +214,10 @@ struct NCViewE2EE: View {
                     }
                     .contentShape(Rectangle())
                     .onTapGesture {
-                        if CCUtility.getPasscode().isEmpty {
-                            NCContentPresenter.shared.showInfo(error: NKError(errorCode: 0, errorDescription: "_e2e_settings_lock_not_active_"))
-                        } else {
+                        if let passcode = CCUtility.getPasscode(), !passcode.isEmpty {
                             manageE2EE.requestPasscodeType("removeLocallyEncryption")
+                        } else {
+                            NCContentPresenter.shared.showInfo(error: NKError(errorCode: 0, errorDescription: "_e2e_settings_lock_not_active_"))
                         }
                     }
 
@@ -232,7 +230,7 @@ struct NCViewE2EE: View {
 
                 List {
 
-                    Section(header: Text(""), footer:Text(manageE2EE.statusOfService + "\n\n" + "End-to-End Encryption " + versionE2EE)) {
+                    Section(header: Text(""), footer:Text(manageE2EE.statusOfService + "\n\n" + "End-to-End Encryption " + NCGlobal.shared.capabilityE2EEApiVersion)) {
                         HStack {
                             Label {
                                 Text(NSLocalizedString("_e2e_settings_start_", comment: ""))

+ 10 - 8
iOSClient/Settings/NCSettings.m

@@ -38,6 +38,10 @@
     AppDelegate *appDelegate;
     TOPasscodeViewController *passcodeViewController;
     TOPasscodeSettingsViewController *passcodeSettingsViewController;
+
+    NSString *versionServer;
+    NSString *themingName;
+    NSString *themingSlogan;
 }
 @end
 
@@ -117,8 +121,8 @@
 
     // Section : E2EEncryption --------------------------------------------------------------
 
-    BOOL isE2EEEnabled = [[NCManageDatabase shared] getCapabilitiesServerBoolWithAccount:appDelegate.account elements:NCElementsJSON.shared.capabilitiesE2EEEnabled exists:false];
-    NSString *versionE2EE = [[NCManageDatabase shared] getCapabilitiesServerStringWithAccount:appDelegate.account elements:NCElementsJSON.shared.capabilitiesE2EEApiVersion];
+    BOOL isE2EEEnabled = [[NCGlobal shared] capabilityE2EEEnabled];
+    NSString *versionE2EE = [[NCGlobal shared] capabilityE2EEApiVersion];
 
     if (isE2EEEnabled == YES && [NCGlobal.shared.e2eeReadVersions containsObject:versionE2EE]) {
 
@@ -220,6 +224,10 @@
     [super viewWillAppear:animated];
     
     appDelegate.activeViewController = self;
+
+    versionServer = [[NCGlobal shared] capabilityServerVersion];
+    themingName = [[NCGlobal shared] capabilityThemingName];
+    themingSlogan = [[NCGlobal shared] capabilityThemingSlogan];
 }
 
 #pragma mark - NotificationCenter
@@ -454,15 +462,9 @@
     } else if (section == 2 && !NCBrandOptions.shared.disable_mobileconfig) {
         sectionName = NSLocalizedString(@"_calendar_contacts_footer_", nil);
     } else if (section == numSections) {
-        NSString *versionServer = [[NCManageDatabase shared] getCapabilitiesServerStringWithAccount:appDelegate.account elements:NCElementsJSON.shared.capabilitiesVersionString];
-        NSString *themingName = [[NCManageDatabase shared] getCapabilitiesServerStringWithAccount:appDelegate.account elements:NCElementsJSON.shared.capabilitiesThemingName];
-        NSString *themingSlogan = [[NCManageDatabase shared] getCapabilitiesServerStringWithAccount:appDelegate.account elements:NCElementsJSON.shared.capabilitiesThemingSlogan];
-
         NSString *versionNextcloud = [NSString stringWithFormat:[NCBrandOptions shared].textCopyrightNextcloudServer, versionServer];
         NSString *versionNextcloudiOS = [NSString stringWithFormat:[NCBrandOptions shared].textCopyrightNextcloudiOS, [[NCUtility shared] getVersionAppWithBuild:true]];
-
         NSString *nameSlogan = [NSString stringWithFormat:@"%@ - %@", themingName, themingSlogan];
-
         sectionName = [NSString stringWithFormat:@"\n%@\n\n%@\n%@", versionNextcloudiOS, versionNextcloud, nameSlogan];
     }
     return sectionName;

+ 6 - 6
iOSClient/Share/Advanced/NCShareCells.swift

@@ -322,15 +322,15 @@ class NCShareDateCell: UITableViewCell {
         case NCShareCommon.shared.SHARE_TYPE_LINK,
             NCShareCommon.shared.SHARE_TYPE_EMAIL,
             NCShareCommon.shared.SHARE_TYPE_GUEST:
-            return NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingPubExpireDateEnforced, exists: false)
+            return NCGlobal.shared.capabilityFileSharingPubExpireDateEnforced
         case NCShareCommon.shared.SHARE_TYPE_USER,
             NCShareCommon.shared.SHARE_TYPE_GROUP,
             NCShareCommon.shared.SHARE_TYPE_CIRCLE,
             NCShareCommon.shared.SHARE_TYPE_ROOM:
-            return NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingInternalExpireDateEnforced, exists: false)
+            return NCGlobal.shared.capabilityFileSharingInternalExpireDateEnforced
         case NCShareCommon.shared.SHARE_TYPE_REMOTE,
             NCShareCommon.shared.SHARE_TYPE_REMOTE_GROUP:
-            return NCManageDatabase.shared.getCapabilitiesServerBool(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingRemoteExpireDateEnforced, exists: false)
+            return NCGlobal.shared.capabilityFileSharingRemoteExpireDateEnforced
         default:
             return false
         }
@@ -341,15 +341,15 @@ class NCShareDateCell: UITableViewCell {
         case NCShareCommon.shared.SHARE_TYPE_LINK,
             NCShareCommon.shared.SHARE_TYPE_EMAIL,
             NCShareCommon.shared.SHARE_TYPE_GUEST:
-            return NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingPubExpireDateDays)
+            return NCGlobal.shared.capabilityFileSharingPubExpireDateDays
         case NCShareCommon.shared.SHARE_TYPE_USER,
             NCShareCommon.shared.SHARE_TYPE_GROUP,
             NCShareCommon.shared.SHARE_TYPE_CIRCLE,
             NCShareCommon.shared.SHARE_TYPE_ROOM:
-            return NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingInternalExpireDateDays)
+            return NCGlobal.shared.capabilityFileSharingInternalExpireDateDays
         case NCShareCommon.shared.SHARE_TYPE_REMOTE,
             NCShareCommon.shared.SHARE_TYPE_REMOTE_GROUP:
-            return NCManageDatabase.shared.getCapabilitiesServerInt(account: account, elements: NCElementsJSON.shared.capabilitiesFileSharingRemoteExpireDateDays)
+            return NCGlobal.shared.capabilityFileSharingRemoteExpireDateDays
         default:
             return 0
         }

+ 1 - 1
iOSClient/Share/NCShare+Helper.swift

@@ -79,7 +79,7 @@ class NCTableShareOptions: NCTableShareable {
         if metadata.e2eEncrypted {
             self.permissions = NCGlobal.shared.permissionCreateShare
         } else {
-            self.permissions = NCManageDatabase.shared.getCapabilitiesServerInt(account: metadata.account, elements: ["ocs", "data", "capabilities", "files_sharing", "default_permissions"]) & metadata.sharePermissionsCollaborationServices
+            self.permissions = NCGlobal.shared.capabilityFileSharingDefaultPermission & metadata.sharePermissionsCollaborationServices
         }
         self.shareType = shareType
         if let password = password {

+ 1 - 2
iOSClient/Share/NCShare.swift

@@ -195,8 +195,7 @@ class NCShare: UIViewController, NCShareNetworkingDelegate, NCSharePagingContent
     }
 
     func checkEnforcedPassword(shareType: Int, completion: @escaping (String?) -> Void) {
-        guard let metadata = self.metadata,
-              NCManageDatabase.shared.getCapabilitiesServerBool(account: metadata.account, elements: NCElementsJSON.shared.capabilitiesFileSharingPubPasswdEnforced, exists: false),
+        guard NCGlobal.shared.capabilityFileSharingPubPasswdEnforced,
               shareType == NCShareCommon.shared.SHARE_TYPE_LINK || shareType == NCShareCommon.shared.SHARE_TYPE_EMAIL
         else { return completion(nil) }
 

+ 6 - 1
iOSClient/Share/NCSharePaging.swift

@@ -89,7 +89,12 @@ class NCSharePaging: UIViewController {
 
         pagingViewController.dataSource = self
         pagingViewController.delegate = self
-        pagingViewController.select(index: page.rawValue)
+
+        if page.rawValue < pages.count {
+            pagingViewController.select(index: page.rawValue)
+        } else {
+            pagingViewController.select(index: 0)
+        }
 
         (pagingViewController.view as? NCSharePagingView)?.setupConstraints()
         pagingViewController.reloadMenu()

+ 2 - 2
iOSClient/Utility/CCUtility.m

@@ -364,8 +364,8 @@
 
 + (BOOL)isEndToEndEnabled:(NSString *)account
 {
-    BOOL isE2EEEnabled = [[NCManageDatabase shared] getCapabilitiesServerBoolWithAccount:account elements:NCElementsJSON.shared.capabilitiesE2EEEnabled exists:false];
-    NSString* versionE2EE = [[NCManageDatabase shared] getCapabilitiesServerStringWithAccount:account elements:NCElementsJSON.shared.capabilitiesE2EEApiVersion];
+    BOOL isE2EEEnabled = [[NCGlobal shared] capabilityE2EEEnabled];
+    NSString* versionE2EE = [[NCGlobal shared] capabilityE2EEApiVersion];
     
     NSString *certificate = [self getEndToEndCertificate:account];
     NSString *publicKey = [self getEndToEndPublicKey:account];

+ 3 - 7
iOSClient/Utility/NCUtility.swift

@@ -141,24 +141,20 @@ class NCUtility: NSObject {
             return false
         }
 
-        guard let richdocumentsMimetypes = NCManageDatabase.shared.getCapabilitiesServerArray(account: metadata.account, elements: NCElementsJSON.shared.capabilitiesRichdocumentsMimetypes) else {
-            return false
-        }
-
         // contentype
-        for richdocumentMimetype: String in richdocumentsMimetypes {
+        for richdocumentMimetype: String in NCGlobal.shared.capabilityRichdocumentsMimetypes {
             if richdocumentMimetype.contains(metadata.contentType) || metadata.contentType == "text/plain" {
                 return true
             }
         }
 
         // mimetype
-        if richdocumentsMimetypes.count > 0 && mimeType.components(separatedBy: ".").count > 2 {
+        if NCGlobal.shared.capabilityRichdocumentsMimetypes.count > 0 && mimeType.components(separatedBy: ".").count > 2 {
 
             let mimeTypeArray = mimeType.components(separatedBy: ".")
             let mimeType = mimeTypeArray[mimeTypeArray.count - 2] + "." + mimeTypeArray[mimeTypeArray.count - 1]
 
-            for richdocumentMimetype: String in richdocumentsMimetypes {
+            for richdocumentMimetype: String in NCGlobal.shared.capabilityRichdocumentsMimetypes {
                 if richdocumentMimetype.contains(mimeType) {
                     return true
                 }