Skip to content

Commit

Permalink
Merge branch 'main' into cleanup
Browse files Browse the repository at this point in the history
  • Loading branch information
chicio committed Oct 24, 2024
2 parents 23864fa + 4f94cc3 commit bf8f2c4
Show file tree
Hide file tree
Showing 12 changed files with 244 additions and 65 deletions.
13 changes: 12 additions & 1 deletion Demo/Demo.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -379,8 +379,9 @@
452832E72044D28E00458375 /* Project object */ = {
isa = PBXProject;
attributes = {
BuildIndependentTargetsInParallel = YES;
LastSwiftUpdateCheck = 1600;
LastUpgradeCheck = 1200;
LastUpgradeCheck = 1600;
ORGANIZATIONNAME = "Fabrizio Duroni";
TargetAttributes = {
45966C942CBACF5000F841E7 = {
Expand Down Expand Up @@ -583,6 +584,7 @@
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "Mac Developer";
COPY_PHASE_STRIP = NO;
DEAD_CODE_STRIPPING = YES;
DEBUG_INFORMATION_FORMAT = dwarf;
ENABLE_STRICT_OBJC_MSGSEND = YES;
ENABLE_TESTABILITY = YES;
Expand Down Expand Up @@ -645,6 +647,7 @@
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "Mac Developer";
COPY_PHASE_STRIP = NO;
DEAD_CODE_STRIPPING = YES;
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
ENABLE_NS_ASSERTIONS = NO;
ENABLE_STRICT_OBJC_MSGSEND = YES;
Expand Down Expand Up @@ -689,6 +692,7 @@
"@executable_path/Frameworks",
);
LOCALIZATION_PREFERS_STRING_CATALOGS = YES;
MACOSX_DEPLOYMENT_TARGET = 11.0;
MARKETING_VERSION = 1.0;
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
MTL_FAST_MATH = YES;
Expand Down Expand Up @@ -726,6 +730,7 @@
"@executable_path/Frameworks",
);
LOCALIZATION_PREFERS_STRING_CATALOGS = YES;
MACOSX_DEPLOYMENT_TARGET = 11.0;
MARKETING_VERSION = 1.0;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = "it.chicio.Demo-tvOS";
Expand Down Expand Up @@ -766,6 +771,7 @@
"@executable_path/Frameworks",
);
LOCALIZATION_PREFERS_STRING_CATALOGS = YES;
MACOSX_DEPLOYMENT_TARGET = 11.0;
MARKETING_VERSION = 1.0;
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
MTL_FAST_MATH = YES;
Expand Down Expand Up @@ -806,6 +812,7 @@
"@executable_path/Frameworks",
);
LOCALIZATION_PREFERS_STRING_CATALOGS = YES;
MACOSX_DEPLOYMENT_TARGET = 11.0;
MARKETING_VERSION = 1.0;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = "it.chicio.Demo-iOS";
Expand All @@ -830,6 +837,7 @@
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_ASSET_PATHS = "\"Demo macOS/Preview Content\"";
DEVELOPMENT_TEAM = 5Y4K7JX2AU;
ENABLE_HARDENED_RUNTIME = YES;
Expand Down Expand Up @@ -867,6 +875,7 @@
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_ASSET_PATHS = "\"Demo macOS/Preview Content\"";
DEVELOPMENT_TEAM = 5Y4K7JX2AU;
ENABLE_HARDENED_RUNTIME = YES;
Expand Down Expand Up @@ -914,6 +923,7 @@
"@executable_path/Frameworks",
);
LOCALIZATION_PREFERS_STRING_CATALOGS = YES;
MACOSX_DEPLOYMENT_TARGET = 11.0;
MARKETING_VERSION = 1.0;
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
MTL_FAST_MATH = YES;
Expand Down Expand Up @@ -953,6 +963,7 @@
"@executable_path/Frameworks",
);
LOCALIZATION_PREFERS_STRING_CATALOGS = YES;
MACOSX_DEPLOYMENT_TARGET = 11.0;
MARKETING_VERSION = 1.0;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = "it.chicio.Demo-watchOS";
Expand Down
4 changes: 2 additions & 2 deletions ID3TagEditor.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -1020,7 +1020,7 @@
SKIP_INSTALL = YES;
SWIFT_VERSION = 6.0;
TARGETED_DEVICE_FAMILY = 3;
TVOS_DEPLOYMENT_TARGET = 12.0;
TVOS_DEPLOYMENT_TARGET = 15.0;
};
name = Debug;
};
Expand Down Expand Up @@ -1054,7 +1054,7 @@
SKIP_INSTALL = YES;
SWIFT_VERSION = 6.0;
TARGETED_DEVICE_FAMILY = 3;
TVOS_DEPLOYMENT_TARGET = 12.0;
TVOS_DEPLOYMENT_TARGET = 15.0;
VALIDATE_PRODUCT = YES;
};
name = Release;
Expand Down
16 changes: 12 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,13 @@ In the following screenshots you can find examples of the data extracted/updated
<sub><b>martinjbaker</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/fabiankr">
<img src="https://avatars.githubusercontent.com/u/143137?v=4" width="100;" alt="fabiankr"/>
<br />
<sub><b>fabiankr</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/joeljfischer">
<img src="https://avatars.githubusercontent.com/u/1767063?v=4" width="100;" alt="joeljfischer"/>
Expand All @@ -78,15 +85,15 @@ In the following screenshots you can find examples of the data extracted/updated
<br />
<sub><b>BLeeEZ</b></sub>
</a>
</td>
</td></tr>
<tr>
<td align="center">
<a href="https://github.com/NCrusher74">
<img src="https://avatars.githubusercontent.com/u/56804260?v=4" width="100;" alt="NCrusher74"/>
<br />
<sub><b>NCrusher74</b></sub>
</a>
</td></tr>
<tr>
</td>
<td align="center">
<a href="https://github.com/Scytalion">
<img src="https://avatars.githubusercontent.com/u/2079490?v=4" width="100;" alt="Scytalion"/>
Expand Down Expand Up @@ -121,7 +128,8 @@ In the following screenshots you can find examples of the data extracted/updated
<br />
<sub><b>jverkoey</b></sub>
</a>
</td>
</td></tr>
<tr>
<td align="center">
<a href="https://github.com/github-actions[bot]">
<img src="https://avatars.githubusercontent.com/in/15368?v=4" width="100;" alt="github-actions[bot]"/>
Expand Down
16 changes: 10 additions & 6 deletions Source/ID3TagEditor.swift
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import Foundation
*/
public class ID3TagEditor {
private let id3TagParser: ID3TagParser
private let id3TagCreator: ID3TagCreator
private let mp3FileReader: Mp3FileReader
private let mp3FileWriter: Mp3FileWriter
private let mp3WithID3TagBuilder: Mp3WithID3TagBuilder
Expand All @@ -21,9 +22,10 @@ public class ID3TagEditor {
*/
public init() {
self.id3TagParser = ID3TagParserFactory.make()
self.id3TagCreator = ID3TagCreatorFactory.make()
self.mp3FileReader = Mp3FileReaderFactory.make()
self.mp3FileWriter = Mp3FileWriter()
self.mp3WithID3TagBuilder = Mp3WithID3TagBuilder(id3TagCreator: ID3TagCreatorFactory.make(),
self.mp3WithID3TagBuilder = Mp3WithID3TagBuilder(id3TagCreator: id3TagCreator,
id3TagConfiguration: ID3TagConfiguration())
}

Expand All @@ -38,7 +40,10 @@ public class ID3TagEditor {
Could throw `CorruptedFile` if the file is corrupted.
*/
public func read(from path: String) throws -> ID3Tag? {
let mp3 = try mp3FileReader.readID3TagFrom(path: path)
guard let mp3 = try mp3FileReader.readID3TagFrom(path: path) else {
return nil
}

return try self.id3TagParser.parse(mp3: mp3)
}

Expand Down Expand Up @@ -68,10 +73,9 @@ public class ID3TagEditor {
ID3 tag).
*/
public func write(tag: ID3Tag, to path: String, andSaveTo newPath: String? = nil) throws {
let mp3 = try mp3FileReader.readFileFrom(path: path)
let currentTag = try self.id3TagParser.parse(mp3: mp3)
let mp3WithId3Tag = try mp3WithID3TagBuilder.build(mp3: mp3, newId3Tag: tag, currentId3Tag: currentTag)
try mp3FileWriter.write(mp3: mp3WithId3Tag, path: newPath ?? path)
let currentId3TagData = try mp3FileReader.readID3TagFrom(path: path)
let newId3TagData = try id3TagCreator.create(id3Tag: tag)
try mp3FileWriter.write(newId3TagData: newId3TagData, currentId3TagData: currentId3TagData, fromPath: path, toPath: newPath ?? path)
}

/**
Expand Down
60 changes: 40 additions & 20 deletions Source/Mp3/Mp3FileReader.swift
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,17 @@ import Foundation
class Mp3FileReader {
private let tagSizeParser: TagSizeParser
private let id3TagConfiguration: ID3TagConfiguration
private let tagVersionParser: TagVersionParser
private let tagPresence: TagPresence

init(tagSizeParser: TagSizeParser,
id3TagConfiguration: ID3TagConfiguration) {
id3TagConfiguration: ID3TagConfiguration,
tagVersionParser: TagVersionParser,
tagPresence: TagPresence) {
self.tagSizeParser = tagSizeParser
self.id3TagConfiguration = id3TagConfiguration
self.tagVersionParser = tagVersionParser
self.tagPresence = tagPresence
}

/**
Expand All @@ -41,40 +47,54 @@ class Mp3FileReader {

- parameter path: the path to the mp3 file

- returns: ID3 header data of the file
- returns: ID3 header data or nil, if a tag doesn't exists in the file.

- throws: Could throw `InvalidFileFormat` if an mp3 file doesn't exists at the specified path, or if the file
does not contain the entire ID3 header
- throws: Could throw `InvalidFileFormat` if an mp3 file doesn't exists at the specified path.
Could throw `CorruptedFile` if the file is corrupted.
*/
func readID3TagFrom(path: String) throws -> Data {
func readID3TagFrom(path: String) throws -> Data? {
let validPath = URL(fileURLWithPath: path)
guard validPath.pathExtension.caseInsensitiveCompare("mp3") == ComparisonResult.orderedSame else {
throw ID3TagEditorError.invalidFileFormat
}

guard let inputStream = InputStream(fileAtPath: path) else {
throw ID3TagEditorError.corruptedFile
let readHandle = try FileHandle(forReadingFrom: URL(fileURLWithPath: path))
defer {
if #available(macOS 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *) {
try? readHandle.close()
} else {
readHandle.closeFile()
}
}

inputStream.open()

let headerSize = id3TagConfiguration.headerSize()
let header = try read(bytesCount: headerSize, fromStream: inputStream)
let headerData = Data(header) as NSData
let header = try read(bytesCount: headerSize, from: readHandle)

let frameSize = tagSizeParser.parse(data: headerData)
let frame = try read(bytesCount: Int(frameSize), fromStream: inputStream)
// Verify that there is a valid ID3 tag to parse the size from
let version = tagVersionParser.parse(mp3: header)
guard tagPresence.isTagPresentIn(mp3: header, version: version) else {
return nil
}

let mp3 = header + frame
return Data(mp3)
let frameSize = tagSizeParser.parse(data: header as NSData)
let frame = try read(bytesCount: Int(frameSize), from: readHandle)

return header + frame
}

private func read(bytesCount: Int, fromStream stream: InputStream) throws -> [UInt8] {
var buffer = [UInt8](repeating: 0, count: bytesCount)
let result = stream.read(&buffer, maxLength: bytesCount)
if result < bytesCount {
private func read(bytesCount: Int, from fileHandle: FileHandle) throws -> Data {
let result = try {
if #available(macOS 10.15.4, iOS 13.4, watchOS 6.2, tvOS 13.4, *) {
return try fileHandle.read(upToCount: bytesCount)
} else {
return fileHandle.readData(ofLength: bytesCount)
}
}()

guard let result, result.count == bytesCount else {
throw ID3TagEditorError.corruptedFile
}
return buffer

return result
}
}
6 changes: 4 additions & 2 deletions Source/Mp3/Mp3FileReaderFactory.swift
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,10 @@ class Mp3FileReaderFactory {
let tagSizeParser = ID3TagSizeParser()
let id3TagConfiguration = ID3TagConfiguration()
let fileReader = Mp3FileReader(tagSizeParser: tagSizeParser,
id3TagConfiguration: id3TagConfiguration)

id3TagConfiguration: id3TagConfiguration,
tagVersionParser: ID3TagVersionParser(),
tagPresence: ID3TagPresence(id3TagConfiguration: id3TagConfiguration))

return fileReader
}
}
Loading

0 comments on commit bf8f2c4

Please sign in to comment.