-
Notifications
You must be signed in to change notification settings - Fork 1
/
install.swift
105 lines (88 loc) · 3.75 KB
/
install.swift
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
//
// main.swift
// Install VIPERX Xcode Template
//
// Created by Agus Cahyono on 05/08/2019.
//
//```sudo swift install.swift```
import Foundation
struct Constants {
struct CommandLineValues {
static let yes = "YES"
static let no = "NO"
}
struct File {
static let templateName = "VIPERX.xctemplate"
static let destinationRelativePath = "/Platforms/iPhoneOS.platform/Developer/Library/Xcode/Templates/Project Templates/iOS/Application"
}
struct Messages {
static let successMessage = "✅ VIPERX was installed succesfully 🎉. Enjoy it 🙂"
static let successfullReplaceMessage = "✅ The Template has been replaced for you with the new version 🎉. Enjoy it 🙂"
static let errorMessage = "❌ Ooops! Something went wrong 😭"
static let exitMessage = "Bye Bye 👋"
static let promptReplace = "That Template already exists. Do you want to replace it? (YES or NO)"
}
struct Blocks {
static let printSeparator = { print("====================================") }
}
}
func printToConsole(_ message:Any){
Constants.Blocks.printSeparator()
print("\(message)")
Constants.Blocks.printSeparator()
}
func moveTemplate(){
do {
let fileManager = FileManager.default
let destinationPath = bash(command: "xcode-select", arguments: ["--print-path"]).appending(Constants.File.destinationRelativePath)
printToConsole("Template will be copied to: \(destinationPath)")
if !fileManager.fileExists(atPath: "\(destinationPath)/\(Constants.File.templateName)"){
try fileManager.copyItem(atPath: Constants.File.templateName, toPath: "\(destinationPath)/\(Constants.File.templateName)")
printToConsole(Constants.Messages.successMessage)
} else {
print(Constants.Messages.promptReplace)
var input = ""
repeat {
guard let textFormCommandLine = readLine(strippingNewline: true) else {
continue
}
input = textFormCommandLine.uppercased()
} while(input != Constants.CommandLineValues.yes && input != Constants.CommandLineValues.no)
if input == Constants.CommandLineValues.yes {
try replaceItemAt(URL(fileURLWithPath: "\(destinationPath)/\(Constants.File.templateName)"), withItemAt: URL(fileURLWithPath: Constants.File.templateName))
printToConsole(Constants.Messages.successfullReplaceMessage)
} else {
print(Constants.Messages.exitMessage)
}
}
}
catch let error as NSError {
printToConsole("\(Constants.Messages.errorMessage) : \(error.localizedFailureReason!)")
}
}
func replaceItemAt(_ url: URL, withItemAt itemAtUrl: URL) throws {
let fileManager = FileManager.default
try fileManager.removeItem(at: url)
try fileManager.copyItem(atPath: itemAtUrl.path, toPath: url.path)
}
func shell(launchPath: String, arguments: [String]) -> String {
let task = Process()
task.launchPath = launchPath
task.arguments = arguments
let pipe = Pipe()
task.standardOutput = pipe
task.launch()
let data = pipe.fileHandleForReading.readDataToEndOfFile()
let output = String(data: data, encoding: String.Encoding.utf8)!
if output.count > 0 {
//remove newline character.
let lastIndex = output.index(before: output.endIndex)
return String(output[output.startIndex ..< lastIndex])
}
return output
}
func bash(command: String, arguments: [String]) -> String {
let whichPathForCommand = shell(launchPath: "/bin/bash", arguments: [ "-l", "-c", "which \(command)" ])
return shell(launchPath: whichPathForCommand, arguments: arguments)
}
moveTemplate()