mirror of
https://github.com/wnagrodzki/SwiftLogger.git
synced 2025-04-06 12:31:51 +02:00
Merge branch 'feature/migrate_to_ios_13_file_handle_methods' into develop
This commit is contained in:
commit
eed8485760
7 changed files with 138 additions and 101 deletions
|
@ -1,5 +1,5 @@
|
|||
language: swift
|
||||
osx_image: xcode10.2
|
||||
osx_image: xcode11.2
|
||||
xcode_project: Logger.xcodeproj
|
||||
script: xcodebuild test -project Logger.xcodeproj -scheme Logger -destination 'platform=iOS Simulator,name=iPhone XS,OS=12.2'
|
||||
script: xcodebuild test -project Logger.xcodeproj -scheme Logger -destination 'platform=iOS Simulator,name=iPhone 11,OS=13.2'
|
||||
after_success: bash <(curl -s https://codecov.io/bash)
|
|
@ -370,7 +370,7 @@
|
|||
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
|
||||
GCC_WARN_UNUSED_FUNCTION = YES;
|
||||
GCC_WARN_UNUSED_VARIABLE = YES;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 13.0;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
|
||||
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
|
||||
MTL_FAST_MATH = YES;
|
||||
ONLY_ACTIVE_ARCH = YES;
|
||||
|
@ -425,7 +425,7 @@
|
|||
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
|
||||
GCC_WARN_UNUSED_FUNCTION = YES;
|
||||
GCC_WARN_UNUSED_VARIABLE = YES;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 13.0;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
|
||||
MTL_ENABLE_DEBUG_INFO = NO;
|
||||
MTL_FAST_MATH = YES;
|
||||
SDKROOT = iphoneos;
|
||||
|
|
|
@ -46,6 +46,7 @@ protocol LogrotateFactory {
|
|||
}
|
||||
|
||||
/// Logger that writes messages into the file at specified URL with log rotation support.
|
||||
@available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *)
|
||||
public final class DiskLogger: Logger {
|
||||
|
||||
private let fileURL: URL
|
||||
|
@ -97,7 +98,7 @@ public final class DiskLogger: Logger {
|
|||
try self.writeBuffer()
|
||||
}
|
||||
catch is SizeLimitedFileQuotaReached {
|
||||
self.closeSizeLimitedFile()
|
||||
try self.closeSizeLimitedFile()
|
||||
try self.rotateLogFiles()
|
||||
try self.openSizeLimitedFile()
|
||||
try self.writeBuffer()
|
||||
|
@ -124,8 +125,8 @@ public final class DiskLogger: Logger {
|
|||
buffer.removeAll()
|
||||
}
|
||||
|
||||
private func closeSizeLimitedFile() {
|
||||
self.sizeLimitedFile.synchronizeAndCloseFile()
|
||||
private func closeSizeLimitedFile() throws {
|
||||
try self.sizeLimitedFile.synchronizeAndCloseFile()
|
||||
self.sizeLimitedFile = nil
|
||||
}
|
||||
|
||||
|
|
|
@ -9,15 +9,45 @@
|
|||
import Foundation
|
||||
|
||||
protocol OSFileHandle {
|
||||
func seekToEndOfFile() -> UInt64
|
||||
func swift_write(_ data: Data) throws
|
||||
func synchronizeFile()
|
||||
func closeFile()
|
||||
func osSeekToEndOfFile() throws -> UInt64
|
||||
func osWrite(_ data: Data) throws
|
||||
func osSynchronizeFile() throws
|
||||
func osCloseFile() throws
|
||||
}
|
||||
|
||||
extension FileHandle: OSFileHandle {
|
||||
|
||||
func swift_write(_ data: Data) throws {
|
||||
try __write(data, error: ())
|
||||
func osSeekToEndOfFile() throws -> UInt64 {
|
||||
if #available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
|
||||
var offsetInFile: UInt64 = 0
|
||||
try __seek(toEndReturningOffset:&offsetInFile)
|
||||
return offsetInFile
|
||||
} else {
|
||||
fatalError()
|
||||
}
|
||||
}
|
||||
|
||||
func osWrite(_ data: Data) throws {
|
||||
if #available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
|
||||
try __write(data, error: ())
|
||||
} else {
|
||||
fatalError()
|
||||
}
|
||||
}
|
||||
|
||||
func osSynchronizeFile() throws {
|
||||
if #available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
|
||||
try synchronize()
|
||||
} else {
|
||||
fatalError()
|
||||
}
|
||||
}
|
||||
|
||||
func osCloseFile() throws {
|
||||
if #available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
|
||||
try close()
|
||||
} else {
|
||||
fatalError()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -42,7 +42,7 @@ protocol SizeLimitedFile {
|
|||
func write(_ data: Data) throws
|
||||
|
||||
/// Writes all in-memory data to permanent storage and closes the file.
|
||||
func synchronizeAndCloseFile()
|
||||
func synchronizeAndCloseFile() throws
|
||||
}
|
||||
|
||||
/// Allows writing to a file while respecting allowed size limit.
|
||||
|
@ -61,7 +61,7 @@ final class SizeLimitedFileImpl {
|
|||
init(fileURL: URL, fileSizeLimit: UInt64, fileFactory: FileHandleFactory) throws {
|
||||
file = try fileFactory.makeInstance(forWritingTo: fileURL)
|
||||
self.sizeLimit = fileSizeLimit
|
||||
currentSize = file.seekToEndOfFile()
|
||||
currentSize = try file.osSeekToEndOfFile()
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -72,12 +72,12 @@ extension SizeLimitedFileImpl: SizeLimitedFile {
|
|||
guard currentSize + dataSize <= sizeLimit else {
|
||||
throw SizeLimitedFileQuotaReached()
|
||||
}
|
||||
try file.swift_write(data)
|
||||
try file.osWrite(data)
|
||||
currentSize += dataSize
|
||||
}
|
||||
|
||||
func synchronizeAndCloseFile() {
|
||||
file.synchronizeFile()
|
||||
file.closeFile()
|
||||
func synchronizeAndCloseFile() throws {
|
||||
try file.osSynchronizeFile()
|
||||
try file.osCloseFile()
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,89 +30,95 @@ class DiskLoggerTests: XCTestCase {
|
|||
let logURL = URL(fileURLWithPath: "/var/log/application.log")
|
||||
|
||||
func testLoggingMessageToFile() {
|
||||
let expectation = XCTestExpectation(description: "write(_:) was called on SizeLimitedFile")
|
||||
expectation.expectedFulfillmentCount = 1
|
||||
|
||||
let fimeManager = FileManagerStub()
|
||||
let sizeLimitedFileFactory = SizeLimitedFileMockFactory(writeCall: expectation)
|
||||
let logrotateFactory = LogrotateMockFactory()
|
||||
let logger = DiskLogger(fileURL: logURL,
|
||||
fileSizeLimit: 1024,
|
||||
rotations: 1,
|
||||
fileManager: fimeManager,
|
||||
sizeLimitedFileFactory: sizeLimitedFileFactory,
|
||||
logrotateFactory: logrotateFactory)
|
||||
|
||||
logger.log("message", level: .critical)
|
||||
|
||||
let result = XCTWaiter().wait(for: [expectation], timeout: 1.0)
|
||||
XCTAssertEqual(result, .completed)
|
||||
|
||||
XCTAssertEqual(sizeLimitedFileFactory.files.count, 1)
|
||||
|
||||
// "2018-08-30 17:23:11.514 <crit> DiskLoggerTests:46 testWritingMessageToFile() a message\n"
|
||||
let loggedMessage = String(decoding: sizeLimitedFileFactory.files[0].data, as: UTF8.self)
|
||||
let expectedSuffix = " <crit> DiskLoggerTests:46 testLoggingMessageToFile() message\n"
|
||||
|
||||
XCTAssertTrue(loggedMessage.hasSuffix(expectedSuffix))
|
||||
if #available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
|
||||
let expectation = XCTestExpectation(description: "write(_:) was called on SizeLimitedFile")
|
||||
expectation.expectedFulfillmentCount = 1
|
||||
|
||||
let fimeManager = FileManagerStub()
|
||||
let sizeLimitedFileFactory = SizeLimitedFileMockFactory(writeCall: expectation)
|
||||
let logrotateFactory = LogrotateMockFactory()
|
||||
let logger = DiskLogger(fileURL: logURL,
|
||||
fileSizeLimit: 1024,
|
||||
rotations: 1,
|
||||
fileManager: fimeManager,
|
||||
sizeLimitedFileFactory: sizeLimitedFileFactory,
|
||||
logrotateFactory: logrotateFactory)
|
||||
|
||||
logger.log("message", level: .critical)
|
||||
|
||||
let result = XCTWaiter().wait(for: [expectation], timeout: 1.0)
|
||||
XCTAssertEqual(result, .completed)
|
||||
|
||||
XCTAssertEqual(sizeLimitedFileFactory.files.count, 1)
|
||||
|
||||
// "2018-08-30 17:23:11.514 <crit> DiskLoggerTests:46 testWritingMessageToFile() a message\n"
|
||||
let loggedMessage = String(decoding: sizeLimitedFileFactory.files[0].data, as: UTF8.self)
|
||||
let expectedSuffix = " <crit> DiskLoggerTests:47 testLoggingMessageToFile() message\n"
|
||||
|
||||
XCTAssertTrue(loggedMessage.hasSuffix(expectedSuffix))
|
||||
}
|
||||
}
|
||||
|
||||
func testExceedingFileSizeLimit() {
|
||||
let expectation = XCTestExpectation(description: "write(_:) was called on SizeLimitedFile")
|
||||
expectation.expectedFulfillmentCount = 2
|
||||
|
||||
let fimeManager = FileManagerStub()
|
||||
let sizeLimitedFileFactory = SizeLimitedFileMockFactory(writeCall: expectation)
|
||||
let logrotateFactory = LogrotateMockFactory()
|
||||
let logger = DiskLogger(fileURL: logURL,
|
||||
fileSizeLimit: 91,
|
||||
rotations: 1,
|
||||
fileManager: fimeManager,
|
||||
sizeLimitedFileFactory: sizeLimitedFileFactory,
|
||||
logrotateFactory: logrotateFactory)
|
||||
|
||||
logger.log("1st message", level: .critical)
|
||||
logger.log("2st message", level: .critical)
|
||||
|
||||
let result = XCTWaiter().wait(for: [expectation], timeout: 1.0)
|
||||
XCTAssertEqual(result, .completed)
|
||||
|
||||
XCTAssertEqual(sizeLimitedFileFactory.files.count, 2)
|
||||
|
||||
// "2018-08-31 18:29:34.748 <crit> DiskLoggerTests:75 testExceedingFileSizeLimit() 2st message\n"
|
||||
let loggedMessage = String(decoding: sizeLimitedFileFactory.files[1].data, as: UTF8.self)
|
||||
let expectedSuffix = " <crit> DiskLoggerTests:75 testExceedingFileSizeLimit() 2st message\n"
|
||||
|
||||
XCTAssertTrue(loggedMessage.hasSuffix(expectedSuffix))
|
||||
if #available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
|
||||
let expectation = XCTestExpectation(description: "write(_:) was called on SizeLimitedFile")
|
||||
expectation.expectedFulfillmentCount = 2
|
||||
|
||||
let fimeManager = FileManagerStub()
|
||||
let sizeLimitedFileFactory = SizeLimitedFileMockFactory(writeCall: expectation)
|
||||
let logrotateFactory = LogrotateMockFactory()
|
||||
let logger = DiskLogger(fileURL: logURL,
|
||||
fileSizeLimit: 91,
|
||||
rotations: 1,
|
||||
fileManager: fimeManager,
|
||||
sizeLimitedFileFactory: sizeLimitedFileFactory,
|
||||
logrotateFactory: logrotateFactory)
|
||||
|
||||
logger.log("1st message", level: .critical)
|
||||
logger.log("2st message", level: .critical)
|
||||
|
||||
let result = XCTWaiter().wait(for: [expectation], timeout: 1.0)
|
||||
XCTAssertEqual(result, .completed)
|
||||
|
||||
XCTAssertEqual(sizeLimitedFileFactory.files.count, 2)
|
||||
|
||||
// "2018-08-31 18:29:34.748 <crit> DiskLoggerTests:75 testExceedingFileSizeLimit() 2st message\n"
|
||||
let loggedMessage = String(decoding: sizeLimitedFileFactory.files[1].data, as: UTF8.self)
|
||||
let expectedSuffix = " <crit> DiskLoggerTests:78 testExceedingFileSizeLimit() 2st message\n"
|
||||
|
||||
XCTAssertTrue(loggedMessage.hasSuffix(expectedSuffix))
|
||||
}
|
||||
}
|
||||
|
||||
func testErrorDuringLogProcess() {
|
||||
let expectation = XCTestExpectation(description: "write(_:) was called on SizeLimitedFile")
|
||||
expectation.expectedFulfillmentCount = 2
|
||||
|
||||
let fimeManager = FileManagerStub()
|
||||
let sizeLimitedFileFactory = UnwritableFileStubFactory(writeCall: expectation)
|
||||
let logrotateFactory = LogrotateMockFactory()
|
||||
let logger = DiskLogger(fileURL: logURL,
|
||||
fileSizeLimit: 91,
|
||||
rotations: 1,
|
||||
fileManager: fimeManager,
|
||||
sizeLimitedFileFactory: sizeLimitedFileFactory,
|
||||
logrotateFactory: logrotateFactory)
|
||||
|
||||
logger.log("1st message", level: .critical)
|
||||
logger.log("2st message", level: .critical)
|
||||
|
||||
let result = XCTWaiter().wait(for: [expectation], timeout: 1.0)
|
||||
XCTAssertEqual(result, .completed)
|
||||
|
||||
XCTAssertEqual(sizeLimitedFileFactory.files.count, 1)
|
||||
|
||||
// "2018-08-31 18:29:34.748 <crit> DiskLoggerTests:75 testExceedingFileSizeLimit() 2st message\n"
|
||||
let loggedMessage = String(decoding: sizeLimitedFileFactory.files[0].data, as: UTF8.self)
|
||||
let expectedOccurence = " <warning> WriteFailed()"
|
||||
|
||||
XCTAssertTrue(loggedMessage.contains(expectedOccurence))
|
||||
if #available(OSX 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
|
||||
let expectation = XCTestExpectation(description: "write(_:) was called on SizeLimitedFile")
|
||||
expectation.expectedFulfillmentCount = 2
|
||||
|
||||
let fimeManager = FileManagerStub()
|
||||
let sizeLimitedFileFactory = UnwritableFileStubFactory(writeCall: expectation)
|
||||
let logrotateFactory = LogrotateMockFactory()
|
||||
let logger = DiskLogger(fileURL: logURL,
|
||||
fileSizeLimit: 91,
|
||||
rotations: 1,
|
||||
fileManager: fimeManager,
|
||||
sizeLimitedFileFactory: sizeLimitedFileFactory,
|
||||
logrotateFactory: logrotateFactory)
|
||||
|
||||
logger.log("1st message", level: .critical)
|
||||
logger.log("2st message", level: .critical)
|
||||
|
||||
let result = XCTWaiter().wait(for: [expectation], timeout: 1.0)
|
||||
XCTAssertEqual(result, .completed)
|
||||
|
||||
XCTAssertEqual(sizeLimitedFileFactory.files.count, 1)
|
||||
|
||||
// "2018-08-31 18:29:34.748 <crit> DiskLoggerTests:75 testExceedingFileSizeLimit() 2st message\n"
|
||||
let loggedMessage = String(decoding: sizeLimitedFileFactory.files[0].data, as: UTF8.self)
|
||||
let expectedOccurence = " <warning> WriteFailed()"
|
||||
|
||||
XCTAssertTrue(loggedMessage.contains(expectedOccurence))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -60,7 +60,7 @@ class SizeLimitedFileTests: XCTestCase {
|
|||
func testSynchronizingAndClosingFile() throws {
|
||||
let factory = FileMockFactory()
|
||||
let writer = try SizeLimitedFileImpl(fileURL: logURL, fileSizeLimit: 1, fileFactory: factory)
|
||||
writer.synchronizeAndCloseFile()
|
||||
try writer.synchronizeAndCloseFile()
|
||||
XCTAssertTrue(factory.mock.synchronizeFileCallCount == 1 && factory.mock.closeFileCallCount == 1)
|
||||
}
|
||||
}
|
||||
|
@ -89,19 +89,19 @@ private class FileMock: OSFileHandle {
|
|||
private(set) var synchronizeFileCallCount = 0
|
||||
private(set) var closeFileCallCount = 0
|
||||
|
||||
func seekToEndOfFile() -> UInt64 {
|
||||
func osSeekToEndOfFile() throws -> UInt64 {
|
||||
return 0
|
||||
}
|
||||
|
||||
func swift_write(_ data: Data) throws {
|
||||
func osWrite(_ data: Data) throws {
|
||||
self.writtenData.append(data)
|
||||
}
|
||||
|
||||
func synchronizeFile() {
|
||||
func osSynchronizeFile() throws {
|
||||
synchronizeFileCallCount += 1
|
||||
}
|
||||
|
||||
func closeFile() {
|
||||
func osCloseFile() throws {
|
||||
closeFileCallCount += 1
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue