Skip to content

Returns Xcode.Project from generate() #1517

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 10 commits into from
May 9, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions Sources/Commands/SwiftPackageTool.swift
Original file line number Diff line number Diff line change
Expand Up @@ -162,13 +162,13 @@ public class SwiftPackageTool: SwiftTool<PackageToolOptions> {
dstdir = try getPackageRoot()
projectName = graph.rootPackages[0].name
}
let outpath = try Xcodeproj.generate(
outputDir: dstdir,
let xcodeprojPath = Xcodeproj.buildXcodeprojPath(outputDir: dstdir, projectName: projectName)
try Xcodeproj.generate(
projectName: projectName,
xcodeprojPath: xcodeprojPath,
graph: graph,
options: options.xcodeprojOptions)

print("generated:", outpath.prettyPath(cwd: originalWorkingDirectory))
print("generated:", xcodeprojPath.prettyPath(cwd: originalWorkingDirectory))

case .describe:
let graph = try loadPackageGraph()
Expand Down
33 changes: 19 additions & 14 deletions Sources/Xcodeproj/generate().swift
Original file line number Diff line number Diff line change
Expand Up @@ -38,26 +38,28 @@ public struct XcodeprojOptions {
}
}

// Determine the path of the .xcodeproj wrapper directory.
public func buildXcodeprojPath(outputDir: AbsolutePath, projectName: String) -> AbsolutePath {
let xcodeprojName = "\(projectName).xcodeproj"
return outputDir.appending(RelativePath(xcodeprojName))
}

/// Generates an Xcode project and all needed support files. The .xcodeproj
/// wrapper directory is created in the path specified by `outputDir`, basing
/// the file name on the project name `projectName`. Returns the path of the
/// generated project. All ancillary files will be generated inside of the
/// .xcodeproj wrapper directory.
/// wrapper directory is created to the path specified by `xcodeprojPath`
/// Returns the generated project. All ancillary files will
/// be generated inside of the .xcodeproj wrapper directory.
@discardableResult
public func generate(
outputDir: AbsolutePath,
projectName: String,
xcodeprojPath: AbsolutePath,
graph: PackageGraph,
options: XcodeprojOptions
) throws -> AbsolutePath {
) throws -> Xcode.Project {
// Note that the output directory might be completely separate from the
// path of the root package (which is where the sources live).

let srcroot = graph.rootPackages[0].path

// Determine the path of the .xcodeproj wrapper directory.
let xcodeprojName = "\(projectName).xcodeproj"
let xcodeprojPath = outputDir.appending(RelativePath(xcodeprojName))

// Determine the path of the scheme directory (it's inside the .xcodeproj).
let schemesDir = xcodeprojPath.appending(components: "xcshareddata", "xcschemes")

Expand All @@ -70,10 +72,13 @@ public func generate(
let extraDirs = try findDirectoryReferences(path: srcroot)

/// Generate the contents of project.xcodeproj (inside the .xcodeproj).
// FIXME: This could be more efficient by directly writing to a stream
// instead of first creating a string.
let project = try pbxproj(xcodeprojPath: xcodeprojPath, graph: graph, extraDirs: extraDirs, options: options)
try open(xcodeprojPath.appending(component: "project.pbxproj")) { stream in
// FIXME: This could be more efficient by directly writing to a stream
// instead of first creating a string.
let str = try pbxproj(xcodeprojPath: xcodeprojPath, graph: graph, extraDirs: extraDirs, options: options)
// Serialize the project model we created to a plist, and return
// its string description.
let str = "// !$*UTF8*$!\n" + project.generatePlist().description
stream(str)
}

Expand Down Expand Up @@ -144,7 +149,7 @@ public func generate(
}
}

return xcodeprojPath
return project
}

/// Writes the contents to the file specified.
Expand Down
7 changes: 2 additions & 5 deletions Sources/Xcodeproj/pbxproj().swift
Original file line number Diff line number Diff line change
Expand Up @@ -34,16 +34,13 @@ public func pbxproj(
extraDirs: [AbsolutePath],
options: XcodeprojOptions,
fileSystem: FileSystem = localFileSystem
) throws -> String {
let project = try xcodeProject(
) throws -> Xcode.Project {
return try xcodeProject(
xcodeprojPath: xcodeprojPath,
graph: graph,
extraDirs: extraDirs,
options: options,
fileSystem: fileSystem)
// Serialize the project model we created to a plist, and return
// its string description.
return "// !$*UTF8*$!\n" + project.generatePlist().description
}

/// A set of c99 target names that are invalid for Xcode Framework targets.
Expand Down
11 changes: 10 additions & 1 deletion Tests/XcodeprojTests/GenerateXcodeprojTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,14 @@ import Utility
import XCTest

class GenerateXcodeprojTests: XCTestCase {
func testBuildXcodeprojPath() {
let outdir = AbsolutePath("/path/to/project")
let projectName = "Bar"
let xcodeprojPath = Xcodeproj.buildXcodeprojPath(outputDir: outdir, projectName: projectName)
let expectedPath = AbsolutePath("/path/to/project/Bar.xcodeproj")
XCTAssertEqual(xcodeprojPath, expectedPath)
}

func testXcodebuildCanParseIt() {
#if os(macOS)
mktmpdir { dstdir in
Expand All @@ -28,7 +36,8 @@ class GenerateXcodeprojTests: XCTestCase {
XCTAssertFalse(diagnostics.hasErrors)

let projectName = "DummyProjectName"
let outpath = try Xcodeproj.generate(outputDir: dstdir, projectName: projectName, graph: graph, options: XcodeprojOptions())
let outpath = Xcodeproj.buildXcodeprojPath(outputDir: dstdir, projectName: projectName)
try Xcodeproj.generate(projectName: projectName, xcodeprojPath: outpath, graph: graph, options: XcodeprojOptions())

XCTAssertDirectoryExists(outpath)
XCTAssertEqual(outpath, dstdir.appending(component: projectName + ".xcodeproj"))
Expand Down