pulsar.sh 7.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266
  1. #!/bin/bash
  2. echoerr() { echo "$@" 1>&2; }
  3. if [ "$(uname)" == 'Darwin' ]; then
  4. OS='Mac'
  5. elif [ "$(expr substr $(uname -s) 1 5)" == 'Linux' ]; then
  6. OS='Linux'
  7. else
  8. echoerr "Your platform ($(uname -a)) is not supported."
  9. exit 1
  10. fi
  11. # Only set the ATOM_DISABLE_SHELLING_OUT_FOR_ENVIRONMENT env var if it hasn't
  12. # been set.
  13. if [ -z "$ATOM_DISABLE_SHELLING_OUT_FOR_ENVIRONMENT" ]
  14. then
  15. export ATOM_DISABLE_SHELLING_OUT_FOR_ENVIRONMENT=true
  16. fi
  17. ATOM_ADD=false
  18. ATOM_NEW_WINDOW=false
  19. EXIT_CODE_OVERRIDE=
  20. while getopts ":anwtfvhp-:" opt; do
  21. case "$opt" in
  22. -)
  23. case "${OPTARG}" in
  24. add)
  25. ATOM_ADD=true
  26. ;;
  27. new-window)
  28. ATOM_NEW_WINDOW=true
  29. ;;
  30. wait)
  31. WAIT=1
  32. ;;
  33. help|version)
  34. EXPECT_OUTPUT=1
  35. ;;
  36. foreground|benchmark|benchmark-test|test)
  37. EXPECT_OUTPUT=1
  38. ;;
  39. package)
  40. PACKAGE_MODE=1
  41. ;;
  42. enable-electron-logging)
  43. export ELECTRON_ENABLE_LOGGING=1
  44. ;;
  45. esac
  46. ;;
  47. a)
  48. ATOM_ADD=true
  49. ;;
  50. n)
  51. ATOM_NEW_WINDOW=true
  52. ;;
  53. w)
  54. WAIT=1
  55. ;;
  56. p)
  57. PACKAGE_MODE=1
  58. ;;
  59. f|t|h|v)
  60. EXPECT_OUTPUT=1
  61. ;;
  62. esac
  63. done
  64. if [ "${ATOM_ADD}" = "true" ] && [ "${ATOM_NEW_WINDOW}" = "true" ]; then
  65. EXPECT_OUTPUT=1
  66. EXIT_CODE_OVERRIDE=1
  67. fi
  68. if [ $REDIRECT_STDERR ]; then
  69. exec 2> /dev/null
  70. fi
  71. ATOM_HOME="${ATOM_HOME:-$HOME/.pulsar}"
  72. mkdir -p "$ATOM_HOME"
  73. if [ $PACKAGE_MODE ]; then
  74. # If `-p` or `--package` is present, then we'll be discarding all arguments
  75. # prior to (and including) `-p`/`--package` and passing the rest to `ppm`.
  76. loop_done=0
  77. while [ $loop_done -eq 0 ]
  78. do
  79. if [[ "$1" == "-p" || "$1" == "--package" || "$1" == "" ]]; then
  80. # We'll shift one last time and then we'll be done.
  81. loop_done=1
  82. fi
  83. shift
  84. done
  85. fi
  86. if [ $OS == 'Mac' ]; then
  87. if [ -L "$0" ]; then
  88. SCRIPT="$(readlink "$0")"
  89. else
  90. SCRIPT="$0"
  91. fi
  92. ATOM_APP="$(dirname "$(dirname "$(dirname "$SCRIPT")")")"
  93. # If this is a `pulsar.sh` from a built version of Pulsar, then `$ATOM_APP`
  94. # should now be the path to the user's instance of Pulsar.app.
  95. if [[ "$ATOM_APP" == . || "$ATOM_APP" != *".app" ]]; then
  96. # This is a `pulsar.sh` that's in the source code of Pulsar or has been
  97. # copied to a location outside of the app (instead of symlinked). We'll try
  98. # another tactic.
  99. unset ATOM_APP
  100. else
  101. # We found the location of the Pulsar.app that this script lives in.
  102. PULSAR_PATH="$(dirname "$ATOM_APP")"
  103. ATOM_APP_NAME="$(basename "$ATOM_APP")"
  104. fi
  105. # Fall back to the default Pulsar.app as the app name.
  106. ATOM_APP_NAME=${ATOM_APP_NAME:-Pulsar.app}
  107. # The executable name will be the same thing but without the `.app` suffix.
  108. ATOM_EXECUTABLE_NAME="${ATOM_APP_NAME%.*}"
  109. if [ -z "${PULSAR_PATH}" ]; then
  110. # If PULSAR_PATH isn't set, check /Applications and then ~/Applications for
  111. # Pulsar.app.
  112. if [ -x "/Applications/${ATOM_APP_NAME}" ]; then
  113. PULSAR_PATH="/Applications"
  114. elif [ -x "$HOME/Applications/${ATOM_APP_NAME}" ]; then
  115. PULSAR_PATH="$HOME/Applications"
  116. else
  117. # We still haven't found a Pulsar.app. Let's try searching for it via
  118. # Spotlight.
  119. PULSAR_APP_SEARCH_RESULT="$(mdfind "kMDItemCFBundleIdentifier == 'dev.pulsar-edit.pulsar'" | grep -v ShipIt | head -1)"
  120. if [ ! -z "$PULSAR_APP_SEARCH_RESULT" ]; then
  121. PULSAR_PATH="$(dirname "$PULSAR_APP_SEARCH_RESULT")"
  122. ATOM_APP_NAME="$(basename "$PULSAR_APP_SEARCH_RESULT")"
  123. fi
  124. fi
  125. fi
  126. PULSAR_EXECUTABLE="$PULSAR_PATH/$ATOM_APP_NAME/Contents/MacOS/$ATOM_EXECUTABLE_NAME"
  127. PPM_EXECUTABLE="$PULSAR_PATH/$ATOM_APP_NAME/Contents/Resources/app/ppm/bin/ppm"
  128. # Exit if Pulsar can't be found.
  129. if [ ! -x "${PULSAR_EXECUTABLE}" ]; then
  130. echoerr "Cannot locate ${ATOM_APP_NAME}; it is usually located in /Applications. Set the PULSAR_PATH environment variable to the directory containing ${ATOM_APP_NAME}."
  131. exit 1
  132. fi
  133. # If `-p` or `--package` was specified, call `ppm` with all the arguments
  134. # that followed it instead of calling the Pulsar executable directly.
  135. if [ $PACKAGE_MODE ]; then
  136. "$PPM_EXECUTABLE" "$@"
  137. exit $?
  138. fi
  139. if [ $EXPECT_OUTPUT ]; then
  140. "$PULSAR_EXECUTABLE" --executed-from="$(pwd)" --pid=$$ "$@"
  141. ATOM_EXIT=$?
  142. if [ ${ATOM_EXIT} -eq 0 ] && [ -n "${EXIT_CODE_OVERRIDE}" ]; then
  143. exit "${EXIT_CODE_OVERRIDE}"
  144. else
  145. exit ${ATOM_EXIT}
  146. fi
  147. else
  148. open -a "$PULSAR_PATH/$ATOM_APP_NAME" -n -g --args --executed-from="$(pwd)" --pid=$$ --path-environment="$PATH" "$@"
  149. fi
  150. elif [ $OS == 'Linux' ]; then
  151. # Set tmpdir only if it's unset.
  152. : ${TMPDIR:=/tmp}
  153. ATOM_EXECUTABLE_NAME="pulsar"
  154. # If `PULSAR_PATH` is set by the user, we'll assume they know what they're
  155. # doing. Otherwise we should try to find it ourselves.
  156. if [ -z "${PULSAR_PATH}" ]; then
  157. # Attempt to infer the installation directory of Pulsar from the location
  158. # of this script. When symlinked to a common location like
  159. # `/usr/local/bin`, this approach should find the true location of the
  160. # Pulsar installation.
  161. if [ -L "$0" ]; then
  162. SCRIPT="$(readlink -f "$0")"
  163. else
  164. SCRIPT="$0"
  165. fi
  166. # The `pulsar.sh` file lives one directory deeper than the root directory
  167. # that contains the `pulsar` binary.
  168. ATOM_APP="$(dirname "$(dirname "$SCRIPT")")"
  169. PULSAR_PATH="$(realpath "$ATOM_APP")"
  170. if [ ! -f "$PULSAR_PATH/pulsar" ]; then
  171. # If that path doesn't contain a `pulsar` executable, then it's not a
  172. # valid path. We'll try something else.
  173. unset ATOM_APP
  174. unset PULSAR_PATH
  175. fi
  176. if [ -z "${PULSAR_PATH}" ]; then
  177. if [ -f "/opt/Pulsar/pulsar" ]; then
  178. # Check the default installation directory for RPM and DEB
  179. # distributions.
  180. PULSAR_PATH="/opt/Pulsar"
  181. elif [ -f "$TMPDIR/pulsar-build/Pulsar/pulsar" ]; then
  182. # This is where Pulsar can be found during some CI build tasks.
  183. PULSAR_PATH="$TMPDIR/pulsar-build/Pulsar"
  184. else
  185. echoerr "Cannot locate Pulsar. Set the PULSAR_PATH environment variable to the directory containing the \`pulsar\` executable."
  186. exit 1
  187. fi
  188. fi
  189. fi
  190. PULSAR_EXECUTABLE="$PULSAR_PATH/$ATOM_EXECUTABLE_NAME"
  191. PPM_EXECUTABLE="$PULSAR_PATH/resources/app/ppm/bin/ppm"
  192. # If `-p` or `--package` was specified, call `ppm` with all the arguments
  193. # that followed it instead of calling the Pulsar executable directly.
  194. if [ $PACKAGE_MODE ]; then
  195. "$PPM_EXECUTABLE" "$@"
  196. exit $?
  197. fi
  198. if [ $EXPECT_OUTPUT ]; then
  199. "$PULSAR_EXECUTABLE" --executed-from="$(pwd)" --pid=$$ "$@" --no-sandbox
  200. ATOM_EXIT=$?
  201. if [ ${ATOM_EXIT} -eq 0 ] && [ -n "${EXIT_CODE_OVERRIDE}" ]; then
  202. exit "${EXIT_CODE_OVERRIDE}"
  203. else
  204. exit ${ATOM_EXIT}
  205. fi
  206. else
  207. (
  208. nohup "$PULSAR_EXECUTABLE" --executed-from="$(pwd)" --pid=$$ "$@" --no-sandbox > "$ATOM_HOME/nohup.out" 2>&1
  209. if [ $? -ne 0 ]; then
  210. cat "$ATOM_HOME/nohup.out"
  211. exit $?
  212. fi
  213. ) &
  214. fi
  215. fi
  216. # Exits this process when Pulsar is used as $EDITOR
  217. on_die() {
  218. exit 0
  219. }
  220. trap 'on_die' SIGQUIT SIGTERM
  221. # If the wait flag is set, don't exit this process until Pulsar kills it.
  222. if [ $WAIT ]; then
  223. WAIT_FIFO="$ATOM_HOME/.wait_fifo"
  224. if [ ! -p "$WAIT_FIFO" ]; then
  225. rm -f "$WAIT_FIFO"
  226. mkfifo "$WAIT_FIFO"
  227. fi
  228. # Block endlessly by reading from a named pipe.
  229. exec 2>/dev/null
  230. read < "$WAIT_FIFO"
  231. # If the read completes for some reason, fall back to sleeping in a loop.
  232. while true; do
  233. sleep 1
  234. done
  235. fi