Skip to content

Commit

Permalink
Merge pull request #480 from martenrebane/MOPPIOS-1289-2
Browse files Browse the repository at this point in the history
Fixed opening CAdES files
  • Loading branch information
Counter178 authored Mar 12, 2024
2 parents 91eb289 + a943d3c commit 185a9bc
Show file tree
Hide file tree
Showing 11 changed files with 225 additions and 41 deletions.
20 changes: 11 additions & 9 deletions MoppApp/MoppApp/ContainerActions.swift
Original file line number Diff line number Diff line change
Expand Up @@ -35,10 +35,8 @@ extension ContainerActions where Self: UIViewController {
let topSigningViewController = navController.viewControllers.last!

landingViewController.documentPicker.dismiss(animated: false, completion: nil)

if landingViewController.fileImportIntent == .openOrCreate && landingViewController.containerType == .asic && urls.count == 1 {
self.importDataFiles(with: urls, navController: navController, topSigningViewController: topSigningViewController, landingViewController: landingViewController, cleanup: cleanup, isEmptyFileImported: isEmptyFileImported, isSendingToSivaAgreed: true)
}

self.importDataFiles(with: urls, navController: navController, topSigningViewController: topSigningViewController, landingViewController: landingViewController, cleanup: cleanup, isEmptyFileImported: isEmptyFileImported, isSendingToSivaAgreed: true)
}

func importDataFiles(with urls: [URL], navController: UINavigationController, topSigningViewController: UIViewController, landingViewController: LandingViewController, cleanup: Bool, isEmptyFileImported: Bool, isSendingToSivaAgreed: Bool) {
Expand Down Expand Up @@ -82,16 +80,19 @@ extension ContainerActions where Self: UIViewController {
let isAsicOrPadesContainer = (ext.isAsicContainerExtension || ext == ContainerFormatPDF) &&
landingViewController.containerType == .asic
let isCdocContainer = ext.isCdocContainerExtension && landingViewController.containerType == .cdoc
if (isAsicOrPadesContainer || isCdocContainer) && urls.count == 1 {
if (urls.first?.pathExtension == "asics" || urls.first?.pathExtension == "scs") || SignatureUtil.isCades(signatures: SignatureUtil.getSignatures(filePath: urls.first!)) {
if (isAsicOrPadesContainer || isCdocContainer) && urls.count == 1 {
SiVaUtil.setIsSentToSiva(isSent: false)

if let firstUrl = urls.first, (firstUrl.pathExtension == "asics" || firstUrl.pathExtension == "scs") || MimeTypeExtractor.isCadesContainer(filePath: firstUrl) {
if self?.getTopViewController() is FileImportProgressViewController {
self?.dismiss(animated: true, completion: {
SiVaUtil.displaySendingToSiVaDialog { hasAgreed in
self?.openExistingContainer(with: urls.first!, cleanup: cleanup, isEmptyFileImported: isEmptyFileImported, isSendingToSivaAgreed: hasAgreed)
self?.openExistingContainer(with: firstUrl, cleanup: cleanup, isEmptyFileImported: isEmptyFileImported, isSendingToSivaAgreed: hasAgreed)
}
})
}
} else {
SiVaUtil.setIsSentToSiva(isSent: true)
self?.openExistingContainer(with: urls.first!, cleanup: cleanup, isEmptyFileImported: isEmptyFileImported, isSendingToSivaAgreed: isSendingToSivaAgreed)
}
} else {
Expand Down Expand Up @@ -150,8 +151,8 @@ extension ContainerActions where Self: UIViewController {
let forbiddenFileExtensions = ["ddoc", "asics", "scs"]
let fileURL = URL(fileURLWithPath: newFilePath)
let fileExtension = fileURL.pathExtension
let isSignedPDF = SiVaUtil.isDocumentSentToSiVa(fileUrl: fileURL)
if (forbiddenFileExtensions.contains(fileExtension) || isSignedPDF) {
let isSignedPDF = SiVaUtil.isSignedPDF(url: fileURL as CFURL)
if (forbiddenFileExtensions.contains(fileExtension) || isSignedPDF || MimeTypeExtractor.isCadesContainer(filePath: fileURL)) {
self.openContainer(url: url, newFilePath: newFilePath, fileName: fileName, landingViewController: landingViewController, navController: navController, isEmptyFileImported: isEmptyFileImported, isSendingToSivaAgreed: isSendingToSivaAgreed) { error in
failure(error)
}
Expand Down Expand Up @@ -189,6 +190,7 @@ extension ContainerActions where Self: UIViewController {
}

func openContainer(url: URL, newFilePath: String, fileName: String, landingViewController: LandingViewController, navController: UINavigationController?, isEmptyFileImported: Bool, isSendingToSivaAgreed: Bool, failure: @escaping ((_ error: NSError?) -> Void)) {
SiVaUtil.setIsSentToSiva(isSent: isSendingToSivaAgreed)
MoppLibContainerActions.sharedInstance().openContainer(withPath: newFilePath,
success: { (_ container: MoppLibContainer?) -> Void in
if container == nil {
Expand Down
10 changes: 7 additions & 3 deletions MoppApp/MoppApp/ContainerViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -244,8 +244,10 @@ class ContainerViewController : MoppViewController, ContainerActions, PreviewAct
if isAsicsContainer() && !isAsicsFileWarningSet {
handleAsicsContainerMessage()
}

checkIsCades(asicContainer: asicContainer)

if isAsicContainer {
checkIsCades(asicContainer: asicContainer)
}

if !isForPreview && isAsicContainer {
if isDdocOrAsicsContainer(containerPath: containerPath) || isEmptyFileWarningSet || isCades() {
Expand Down Expand Up @@ -675,7 +677,8 @@ extension ContainerViewController : UITableViewDataSource {
if signingContainerViewDelegate.getTimestampTokensCount() >= indexPath.row {
timestampToken = signingContainerViewDelegate.getTimestampToken(index: indexPath.row) as? MoppLibSignature ?? MoppLibSignature()

if (containerViewDelegate.getDataFileCount() == 1 && isSendingToSivaAgreed && !isLoadingNestedAsicsDone) {
if (containerViewDelegate.getDataFileCount() == 1 && isSendingToSivaAgreed &&
!isLoadingNestedAsicsDone && !MimeTypeExtractor.isCadesContainer(filePath: URL(fileURLWithPath: containerViewDelegate.getContainerPath()))) {
updateState(.loading)
let dataFile = containerViewDelegate.getDataFileDisplayName(index: 0) ?? ""
let containerFilePath = containerViewDelegate.getContainerPath()
Expand Down Expand Up @@ -773,6 +776,7 @@ extension ContainerViewController : UITableViewDataSource {
if pathExtension == "asics" || pathExtension == "scs" {
SiVaUtil.displaySendingToSiVaDialog { hasAgreed in
if hasAgreed {
SiVaUtil.setIsSentToSiva(isSent: hasAgreed)
self.openNestedContainer(containerFilePath: containerFilePath, dataFile: dataFile, destinationPath: destinationPath)
return
} else {
Expand Down
74 changes: 56 additions & 18 deletions MoppApp/MoppApp/MimeTypeExtractor.swift
Original file line number Diff line number Diff line change
Expand Up @@ -30,14 +30,32 @@ class MimeTypeExtractor {

private static let DEFAULT_MIMETYPE = "application/octet-stream"

// Check if file is zip format
private static func isZipFile(filePath: URL) -> Bool {
guard let fileHandle = FileHandle(forReadingAtPath: filePath.path) else { return false }
let fileData = fileHandle.readData(ofLength: 4)
let isZip = fileData.starts(with: [0x50, 0x4b, 0x03, 0x04])
do {
try fileHandle.close()
} catch (let zipError) {
printLog("Unable to close zip file: \(zipError.localizedDescription)")
}
return isZip
}

public static func isCadesContainer(filePath: URL) -> Bool {
if isZipFile(filePath: filePath) {
return containerHasSignatureFiles(filePath: filePath)
}

return false
}

public static func getMimeTypeFromContainer(filePath: URL) -> String {

var mimetype: String = ""

guard let fileHandle = FileHandle(forReadingAtPath: filePath.path) else { return "" }
let fileData = fileHandle.readData(ofLength: 4)
// Check if file is zip format
if fileData.starts(with: [0x50, 0x4b, 0x03, 0x04]) {
if isZipFile(filePath: filePath) {
guard let unzippedFile = unZipFile(filePath: filePath, fileName: "mimetype") else {
return mimetype
}
Expand All @@ -48,7 +66,6 @@ class MimeTypeExtractor {

removeUnzippedFolder(folderPath: unzippedFolder)
}
fileHandle.closeFile()

if isDdoc(url: filePath) {
return ContainerFormatDdocMimetype
Expand Down Expand Up @@ -110,25 +127,46 @@ class MimeTypeExtractor {
}

return fileExtension
}

private static func containerHasSignatureFiles(filePath: URL) -> Bool {
do {
let archive = try Archive(url: filePath, accessMode: .read)

for entry in archive {
let entryUrl = URL(fileURLWithPath: entry.path)
if entryUrl.lastPathComponent.contains("p7s") {
return true
}
}
} catch (let archiveError) {
printLog("Unable to open archive: \(archiveError.localizedDescription)")
return false
}

return false
}

private static func unZipFile(filePath: URL, fileName: String) -> URL? {
let outputPath = MoppFileManager.shared.tempCacheDirectoryPath().appendingPathComponent(filePath.lastPathComponent).deletingPathExtension()
guard let archive = Archive(url: filePath, accessMode: .read) else {
return nil
}
guard let fileInArchive = archive[fileName] else {
return nil
}
var destinationLocation = URL(fileURLWithPath: outputPath.path)
destinationLocation.appendPathComponent("mimetype")

do {
printLog("Extracting file: \(fileName)")
_ = try archive.extract(fileInArchive, to: destinationLocation)
return destinationLocation
} catch {
printLog("Unable to extract file \(fileInArchive). Error: \(error.localizedDescription)")
let archive = try Archive(url: filePath, accessMode: .read)
guard let fileInArchive = archive[fileName] else {
return nil
}
var destinationLocation = URL(fileURLWithPath: outputPath.path)
destinationLocation.appendPathComponent("extractedFile")
do {
printLog("Extracting file: \(fileName) to \(destinationLocation.path)")
_ = try archive.extract(fileInArchive, to: destinationLocation)
return destinationLocation
} catch {
printLog("Unable to extract file \(fileInArchive). Error: \(error.localizedDescription)")
return nil
}
} catch (let archiveError) {
printLog("Unable to open archive: \(archiveError.localizedDescription)")
return nil
}
}
Expand Down
5 changes: 5 additions & 0 deletions MoppApp/MoppApp/PreviewActions.swift
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ extension PreviewActions where Self: ContainerViewController {
let containerViewController = SigningContainerViewController.instantiate()

let destinationPathURL = URL(fileURLWithPath: destinationPath)
SiVaUtil.setIsSentToSiva(isSent: false)
if SiVaUtil.isDocumentSentToSiVa(fileUrl: destinationPathURL) {
SiVaUtil.displaySendingToSiVaDialog { hasAgreed in
if (destinationPathURL.pathExtension == "ddoc" || destinationPathURL.pathExtension == "pdf") && !hasAgreed {
Expand All @@ -59,6 +60,7 @@ extension PreviewActions where Self: ContainerViewController {
openAsicContainerPreviewDocument(containerViewController, isPDF, hasAgreed)
}
} else {
SiVaUtil.setIsSentToSiva(isSent: true)
openAsicContainerPreviewDocument(containerViewController, isPDF, true)
}
}
Expand Down Expand Up @@ -100,20 +102,23 @@ extension PreviewActions where Self: ContainerViewController {

let fileExtension = URL(fileURLWithPath: filePath).pathExtension.lowercased()

SiVaUtil.setIsSentToSiva(isSent: false)
if fileExtension != "pdf" && SiVaUtil.isDocumentSentToSiVa(fileUrl: URL(fileURLWithPath: filePath)) {
SiVaUtil.displaySendingToSiVaDialog { hasAgreed in
if hasAgreed {
openContentPreviewDocument(filePath)
}
}
} else {
SiVaUtil.setIsSentToSiva(isSent: true)
openContentPreviewDocument(filePath)
}

}

let openPDFPreview: () -> Void = { [weak self] in
self?.updateState(.loading)
SiVaUtil.setIsSentToSiva(isSent: false)
MoppLibContainerActions.sharedInstance().openContainer(
withPath: destinationPath,
success: { [weak self] (_ container: MoppLibContainer?) -> Void in
Expand Down
5 changes: 4 additions & 1 deletion MoppApp/MoppApp/RecentContainersViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -210,14 +210,17 @@ extension RecentContainersViewController : UITableViewDelegate {

if ext.isAsicContainerExtension || ext.isPdfContainerExtension {
let containerPathURL = path
SiVaUtil.setIsSentToSiva(isSent: false)
if SiVaUtil.isDocumentSentToSiVa(fileUrl: containerPathURL) || (containerPathURL.pathExtension == "asics" || containerPathURL.pathExtension == "scs") {
SiVaUtil.displaySendingToSiVaDialog { hasAgreed in
if (containerPathURL.pathExtension == "ddoc" || containerPathURL.pathExtension == "pdf") && !hasAgreed {
if (containerPathURL.pathExtension == "ddoc" || containerPathURL.pathExtension == "pdf" ||
MimeTypeExtractor.isCadesContainer(filePath: containerPathURL)) && !hasAgreed {
return
}
self.openContainer(containerPath: path.path, navController: navController, isSendingToSivaAgreed: hasAgreed)
}
} else {
SiVaUtil.setIsSentToSiva(isSent: true)
self.openContainer(containerPath: path.path, navController: navController, isSendingToSivaAgreed: true)
}
} else {
Expand Down
17 changes: 15 additions & 2 deletions MoppApp/MoppApp/SivaUtil.swift
Original file line number Diff line number Diff line change
Expand Up @@ -23,25 +23,33 @@

import Foundation
import PDFKit
import MoppLib

class SiVaUtil {
static func isDocumentSentToSiVa(fileUrl: URL?) -> Bool {
guard let fileLocation = fileUrl else { return false }
let containerTypes = ["asics", "scs", "ddoc"]
let containerType = MimeTypeExtractor.determineContainer(mimetype: MimeTypeExtractor.getMimeTypeFromContainer(filePath: fileLocation), fileExtension: fileLocation.pathExtension).lowercased()

if containerType == "pdf" {
return isSignedPDF(url: fileLocation as CFURL)
let isSignedPDF = isSignedPDF(url: fileLocation as CFURL)
return isSignedPDF
}

return containerType == "ddoc" || SignatureUtil.isCades(signatures: SignatureUtil.getSignatures(filePath: fileLocation))
let isCades = MimeTypeExtractor.isCadesContainer(filePath: fileLocation)
let isSentToSiva = containerTypes.contains(containerType) || isCades

return isSentToSiva
}

static func displaySendingToSiVaDialog(completionHandler: @escaping (Bool) -> Void) {
let alert = UIAlertController(title: L(.sivaSendMessage).removeFirstLinkFromMessage(), message: nil, preferredStyle: .alert)
alert.addAction(UIAlertAction(title: L(.actionYes).uppercased(), style: .default, handler: { (_ action: UIAlertAction) in
setIsSentToSiva(isSent: true)
completionHandler(true)
}))
alert.addAction(UIAlertAction(title: L(.actionAbort), style: .default, handler: {(_ action: UIAlertAction) -> Void in
setIsSentToSiva(isSent: false)
completionHandler(false)
}))
if let linkInUrl: String = L(.sivaSendMessage).getFirstLinkInMessage() {
Expand Down Expand Up @@ -112,4 +120,9 @@ class SiVaUtil {

return false
}

static func setIsSentToSiva(isSent: Bool) {
let validateOnlineInstance = MoppLibDigidocValidateOnline.sharedInstance()
validateOnlineInstance?.validateOnline = isSent
}
}
Loading

0 comments on commit 185a9bc

Please sign in to comment.