FileOtter/FileOtterTests/FilePathTests.swift

206 lines
7.1 KiB
Swift

//
// FilePathTests.swift
// FileOtterTests
//
// Created by Sami Samhuri on 2025-08-19.
//
@testable import FileOtter
import XCTest
final class FilePathTests: XCTestCase {
var tempDir: URL!
override func setUpWithError() throws {
tempDir = URL.temporaryDirectory
.appendingPathComponent("FilePathTests-\(UUID().uuidString)")
try FileManager.default.createDirectory(at: tempDir, withIntermediateDirectories: true)
}
override func tearDownWithError() throws {
if FileManager.default.fileExists(atPath: tempDir.path) {
try FileManager.default.removeItem(at: tempDir)
}
}
// MARK: - basename Tests
func testBasename() throws {
let url1 = URL(fileURLWithPath: "/Users/sjs/file.txt")
XCTAssertEqual(File.basename(url1), "file.txt")
let url2 = URL(fileURLWithPath: "/Users/sjs/dir/")
XCTAssertEqual(File.basename(url2), "dir")
let url3 = URL(fileURLWithPath: "/")
XCTAssertEqual(File.basename(url3), "/")
let url4 = URL(fileURLWithPath: "file.rb")
XCTAssertEqual(File.basename(url4), "file.rb")
}
func testBasenameWithSuffix() throws {
let url = URL(fileURLWithPath: "/Users/sjs/file.txt")
XCTAssertEqual(File.basename(url, suffix: ".txt"), "file")
XCTAssertEqual(File.basename(url, suffix: ".rb"), "file.txt")
let url2 = URL(fileURLWithPath: "/Users/sjs/archive.tar.gz")
XCTAssertEqual(File.basename(url2, suffix: ".gz"), "archive.tar")
XCTAssertEqual(File.basename(url2, suffix: ".tar.gz"), "archive")
}
func testBasenameWithWildcardSuffix() throws {
let url = URL(fileURLWithPath: "/Users/sjs/file.txt")
XCTAssertEqual(File.basename(url, suffix: ".*"), "file")
let url2 = URL(fileURLWithPath: "/Users/sjs/archive.tar.gz")
XCTAssertEqual(File.basename(url2, suffix: ".*"), "archive.tar")
let url3 = URL(fileURLWithPath: "/Users/sjs/noext")
XCTAssertEqual(File.basename(url3, suffix: ".*"), "noext")
}
// MARK: - dirname Tests
func testDirname() throws {
let url1 = URL(fileURLWithPath: "/Users/sjs/file.txt")
XCTAssertEqual(File.dirname(url1).path(), "/Users/sjs/")
let url2 = URL(fileURLWithPath: "/Users/sjs/dir/")
XCTAssertEqual(File.dirname(url2).path(), "/Users/sjs/")
let url3 = URL(fileURLWithPath: "/file.txt")
XCTAssertEqual(File.dirname(url3).path(), "/")
let url4 = URL(fileURLWithPath: "file.txt")
XCTAssertEqual(File.dirname(url4).path(), "./")
}
func testDirnameWithLevel() throws {
let url = URL(fileURLWithPath: "/Users/sjs/dir/file.txt")
XCTAssertEqual(File.dirname(url, level: 1).path(), "/Users/sjs/dir/")
XCTAssertEqual(File.dirname(url, level: 2).path(), "/Users/sjs/")
XCTAssertEqual(File.dirname(url, level: 3).path(), "/Users/")
XCTAssertEqual(File.dirname(url, level: 4).path(), "/")
XCTAssertEqual(File.dirname(url, level: 5).path(), "/") // Can't go beyond root
}
// MARK: - extname Tests
func testExtname() throws {
XCTAssertEqual(File.extname(URL(fileURLWithPath: "test.rb")), ".rb")
XCTAssertEqual(File.extname(URL(fileURLWithPath: "a/b/d/test.rb")), ".rb")
XCTAssertEqual(File.extname(URL(fileURLWithPath: ".a/b/d/test.rb")), ".rb")
XCTAssertEqual(File.extname(URL(fileURLWithPath: "test")), "")
XCTAssertEqual(File.extname(URL(fileURLWithPath: "test.tar.gz")), ".gz")
}
func testExtnameWithDotfile() throws {
XCTAssertEqual(File.extname(URL(fileURLWithPath: ".profile")), "")
XCTAssertEqual(File.extname(URL(fileURLWithPath: ".profile.sh")), ".sh")
XCTAssertEqual(File.extname(URL(fileURLWithPath: "/Users/sjs/.bashrc")), "")
XCTAssertEqual(File.extname(URL(fileURLWithPath: "/Users/sjs/.config.bak")), ".bak")
}
// MARK: - split Tests
func testSplit() throws {
let (dir1, name1) = File.split(URL(fileURLWithPath: "/Users/sjs/file.txt"))
XCTAssertEqual(dir1.path, "/Users/sjs")
XCTAssertEqual(name1, "file.txt")
let (dir2, name2) = File.split(URL(fileURLWithPath: "/file.txt"))
XCTAssertEqual(dir2.path, "/")
XCTAssertEqual(name2, "file.txt")
let (dir3, name3) = File.split(URL(fileURLWithPath: "file.txt"))
XCTAssertEqual(dir3.path(), "./")
XCTAssertEqual(name3, "file.txt")
let (dir4, name4) = File.split(URL(fileURLWithPath: "/Users/sjs/"))
XCTAssertEqual(dir4.path, "/Users")
XCTAssertEqual(name4, "sjs")
// Root path edge case
let (dir5, name5) = File.split(URL(fileURLWithPath: "/"))
XCTAssertEqual(dir5.path, "/")
XCTAssertEqual(name5, "")
}
// MARK: - join Tests
func testJoin() throws {
let u = URL(fileURLWithPath: "hello")
XCTAssertEqual(File.join(u.path(), "world").path(), "hello/world")
XCTAssertEqual(File.join("usr", "mail", "gumby").path(), "usr/mail/gumby")
XCTAssertEqual(File.join("/usr", "mail", "gumby").path(), "/usr/mail/gumby")
XCTAssertEqual(File.join("/", "usr", "bin").path(), "/usr/bin/")
// Single component
XCTAssertEqual(File.join("file.txt").path(), "file.txt")
XCTAssertEqual(File.join("/file.txt").path(), "/file.txt")
// Empty components are ignored
XCTAssertEqual(File.join("usr", "", "bin").path(), "usr/bin")
// Handles trailing slashes
XCTAssertEqual(File.join("/usr/", "local/", "bin").path(), "/usr/local/bin/")
}
func testJoinWithArray() throws {
let components = ["usr", "local", "bin"]
XCTAssertEqual(File.join(components).path(), "usr/local/bin")
let absoluteComponents = ["/usr", "local", "bin"]
XCTAssertEqual(File.join(absoluteComponents).path(), "/usr/local/bin/")
let singleComponent = ["file.txt"]
XCTAssertEqual(File.join(singleComponent).path(), "file.txt")
}
// MARK: - absolutePath Tests
func testAbsolutePath() throws {
// TODO: Implement
// Converts relative to absolute
}
func testAbsolutePathWithBase() throws {
// TODO: Implement
}
// MARK: - expandPath Tests
func testExpandPath() throws {
// TODO: Implement
// File.expandPath("~") => home directory
// File.expandPath("~/Documents") => home/Documents
}
func testExpandPathWithRelative() throws {
// TODO: Implement
}
// MARK: - realpath Tests
func testRealpath() throws {
// TODO: Implement
// Resolves symlinks, all components must exist
}
func testRealpathThrowsForNonExistent() throws {
// TODO: Implement
}
// MARK: - realdirpath Tests
func testRealdirpath() throws {
// TODO: Implement
// Resolves symlinks, last component may not exist
}
func testRealdirpathWithNonExistentLast() throws {
// TODO: Implement
}
}