I have a command-line app A, and in A I execute an executable script B, in B I'm expecting an input from stdin.
I wrote a demo, implementing A in Swift, using Foundation's Process api, finding that B, no matter implemented in whatever language, cannot get user input from stdin.
Code:
// `A`'s main.swift
import Foundation
let process = Process()
process.launchPath = PATH_TO_SCRIPT_B
process.launch()
process.waitUntilExit()
// `B`
#!/usr/bin/swift 
print("intpu something")
let input = readLine()
print("input: \(input)")
I did not set the process's input since according to the doc:
If this method isn’t used, the standard input is inherited from the process that created the receiver.
UPDATE:
A is an executable package created using Swift Package Manager. I used swift package generate-xcodeproj to generate an Xcode project file. I confirmed that if I run the executable built using swift build or xcodebuild in a shell, the problem with getting input from stdin from B arose. However if I run it directly inside Xcode, by pressing command + R inside Xcode, then it worked. So if I understand the difference between running an executable in a shell and Xcode, I can probably make everything work.
func task() {
  print("input here")
  let x = input()
  print ("inputed:" + x)
}
func input() -> String {
  let keyboard = FileHandle.standardInput
  let inputData = keyboard.availableData
  let strData = String(data: inputData, encoding: .utf8)!
  let string = strData.trimmingCharacters(in: .newlines)
  return string
}
task()
Hope it helps
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With