Skip to content

Commit ac073f0

Browse files
authored
Merge pull request #657 from damuellen/NSArray
2 parents a2904a2 + 10cff6d commit ac073f0

File tree

2 files changed

+93
-4
lines changed

2 files changed

+93
-4
lines changed

Foundation/NSArray.swift

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -397,8 +397,20 @@ open class NSArray : NSObject, NSCopying, NSMutableCopying, NSSecureCoding, NSCo
397397
return objects
398398
}
399399

400-
open func write(toFile path: String, atomically useAuxiliaryFile: Bool) -> Bool { NSUnimplemented() }
401-
open func write(to url: URL, atomically: Bool) -> Bool { NSUnimplemented() }
400+
open func write(toFile path: String, atomically useAuxiliaryFile: Bool) -> Bool {
401+
return write(to: URL(fileURLWithPath: path), atomically: useAuxiliaryFile)
402+
}
403+
404+
// the atomically flag is ignored if url of a type that cannot be written atomically.
405+
open func write(to url: URL, atomically: Bool) -> Bool {
406+
do {
407+
let pListData = try PropertyListSerialization.data(fromPropertyList: self, format: .xml, options: 0)
408+
try pListData.write(to: url, options: atomically ? .atomic : [])
409+
return true
410+
} catch {
411+
return false
412+
}
413+
}
402414

403415
open func objects(at indexes: IndexSet) -> [Any] {
404416
var objs = [Any]()
@@ -571,8 +583,20 @@ open class NSArray : NSObject, NSCopying, NSMutableCopying, NSSecureCoding, NSCo
571583
return lastEqual ? result + 1 : result
572584
}
573585

574-
public convenience init?(contentsOfFile path: String) { NSUnimplemented() }
575-
public convenience init?(contentsOfURL url: URL) { NSUnimplemented() }
586+
public convenience init?(contentsOfFile path: String) {
587+
self.init(contentsOfURL: URL(fileURLWithPath: path))
588+
}
589+
590+
public convenience init?(contentsOfURL url: URL) {
591+
do {
592+
guard let plistDoc = try? Data(contentsOf: url),
593+
let plistArray = try PropertyListSerialization.propertyList(from: plistDoc, options: [], format: nil) as? Array<Any>
594+
else { return nil }
595+
self.init(array: plistArray)
596+
} catch {
597+
return nil
598+
}
599+
}
576600

577601
override open var _cfTypeID: CFTypeID {
578602
return CFArrayGetTypeID()

TestFoundation/TestNSArray.swift

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,8 @@ class TestNSArray : XCTestCase {
4242
("test_equality", test_equality),
4343
("test_copying", test_copying),
4444
("test_mutableCopying", test_mutableCopying),
45+
("test_writeToFile", test_writeToFile),
46+
("test_initWithContentsOfFile", test_initWithContentsOfFile)
4547
]
4648
}
4749

@@ -456,4 +458,67 @@ class TestNSArray : XCTestCase {
456458
}
457459
}
458460

461+
func test_initWithContentsOfFile() {
462+
let testFilePath = createTestFile("TestFileOut.txt", _contents: Data(capacity: 234))
463+
if let _ = testFilePath {
464+
let a1: NSArray = ["foo", "bar"]
465+
let isWritten = a1.write(toFile: testFilePath!, atomically: true)
466+
if isWritten {
467+
let array = NSArray.init(contentsOfFile: testFilePath!)
468+
XCTAssert(array == a1)
469+
} else {
470+
XCTFail("Write to file failed")
471+
}
472+
removeTestFile(testFilePath!)
473+
} else {
474+
XCTFail("Temporary file creation failed")
475+
}
476+
}
477+
478+
func test_writeToFile() {
479+
let testFilePath = createTestFile("TestFileOut.txt", _contents: Data(capacity: 234))
480+
if let _ = testFilePath {
481+
let d1: NSArray = ["foo", "bar"]
482+
let isWritten = d1.write(toFile: testFilePath!, atomically: true)
483+
if isWritten {
484+
do {
485+
let plistDoc = try XMLDocument(contentsOf: URL(fileURLWithPath: testFilePath!, isDirectory: false), options: [])
486+
try plistDoc.validate()
487+
XCTAssert(plistDoc.rootElement()?.name == "plist")
488+
let plist = try PropertyListSerialization.propertyList(from: plistDoc.xmlData, options: [], format: nil) as! [Any]
489+
XCTAssert((plist[0] as? String) == d1[0] as? String)
490+
XCTAssert((plist[1] as? String) == d1[1] as? String)
491+
} catch {
492+
XCTFail("XMLDocument failes to read / validate contenets")
493+
}
494+
} else {
495+
XCTFail("Write to file failed")
496+
}
497+
removeTestFile(testFilePath!)
498+
} else {
499+
XCTFail("Temporary file creation failed")
500+
}
501+
}
502+
503+
private func createTestFile(_ path: String, _contents: Data) -> String? {
504+
let tempDir = "/tmp/TestFoundation_Playground_" + NSUUID().uuidString + "/"
505+
do {
506+
try FileManager.default.createDirectory(atPath: tempDir, withIntermediateDirectories: false, attributes: nil)
507+
if FileManager.default.createFile(atPath: tempDir + "/" + path, contents: _contents, attributes: nil) {
508+
return tempDir + path
509+
} else {
510+
return nil
511+
}
512+
} catch _ {
513+
return nil
514+
}
515+
}
516+
517+
private func removeTestFile(_ location: String) {
518+
do {
519+
try FileManager.default.removeItem(atPath: location)
520+
} catch _ {
521+
522+
}
523+
}
459524
}

0 commit comments

Comments
 (0)