Skip to content
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

Feature suggestion: inline-shell #342

Open
georgewsinger opened this issue Jan 25, 2019 · 6 comments
Open

Feature suggestion: inline-shell #342

georgewsinger opened this issue Jan 25, 2019 · 6 comments

Comments

@georgewsinger
Copy link

Suggestion: I think this library would be an order of magnitude more useful if it implemented something akin to inline-C. I.e:

main :: IO ()
main = do
  x <- [S.block| {
      # Print something to console from bash.
      echo "Hello from"
    } |]
 putStrLn $ x ++ " Haskell!"

This would allow someone to mix quick bash scripts with the aid of Turtle's typing system.

@Gabriella439
Copy link
Owner

@georgewsinger: To make sure I understand correctly: would this translate to one call to proc or procs per line in the block?

@Gabriella439
Copy link
Owner

Oops, I mean shell or shells

@georgewsinger
Copy link
Author

georgewsinger commented Jan 25, 2019

I'm not sure what is best long-term, but at first glance it seems translating to one shell would be totally suitable for what I have in mind?

Though on second glance: how does bash itself treat a statement like echo "1"; echo "2"; echo "3"? Is that one "shell" or three "shells" from its perspective (here I'm taking "shell" to mean "process")? What about echo "1" && echo "2" && echo "3"? If bash treats these cases as three separate processes, then maybe the best way to translate would be to spawn multiple shells per inline-block as needed.

(I'm not very familiar with how shells and turtle work under the hood, so I hope I'm not spouting nonsense here).

@Gabriella439
Copy link
Owner

Maybe the simplest approach would be to save the inline shell block to a file and then interpret that file using the shell. The main reason I suggest this is that otherwise turtle would have to parse the file and do things like filter out comments/empty-lines

@georgewsinger
Copy link
Author

georgewsinger commented Jan 30, 2019

That sounds perfect. Every Haskell file file.hs could get its associated file.sh with all of the shell snippets pasted in order (I believe this is how inline-C does it).

@Gabriella439
Copy link
Owner

The main issue I can think of is that this would require creating multiple versions of this utility that parallel shell/shells/inshell/inshellWithStderr, etc.

One way to reduce the API proliferation might be to provide a utility for saving Text to a temporary file, such as:

tempFile :: MonadManaged managed => Text -> m FilePath

... because if you had such a utility then you can combine that with the neat-interpolation package plus the existing API to get most of what you need, like this:

{-# LANGUAGE QuasiQuotes #-}

import Turtle (fp)

import qualified NeatInterpolation
import qualified Turtle

main :: IO ()
main = Turtle.sh $ do
    script <- tempFile [NeatInterpolation.text|
      # Print something to console from bash.
      echo "Hello from"
    |]

    x <- Turtle.strict (Turtle.inshell "bash" [ Turtle.format fp script ] Turtle.empty)

    

... as a bonus, if you use the neat-interpolation package then you also get support for string interpolation into the script

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants