@@ -119,6 +119,8 @@ module System.Process.Typed
119
119
120
120
-- * Exceptions
121
121
, ExitCodeException (.. )
122
+ , exitCodeExceptionWithOutput
123
+ , exitCodeExceptionNoOutput
122
124
, ByteStringOutputException (.. )
123
125
124
126
-- * Re-exports
@@ -638,12 +640,7 @@ checkExitCodeSTM p = do
638
640
ec <- readTMVar (pExitCode p)
639
641
case ec of
640
642
ExitSuccess -> return ()
641
- _ -> throwSTM ExitCodeException
642
- { eceExitCode = ec
643
- , eceProcessConfig = clearStreams (pConfig p)
644
- , eceStdout = L. empty
645
- , eceStderr = L. empty
646
- }
643
+ _ -> throwSTM $ exitCodeExceptionNoOutput p ec
647
644
648
645
-- | Returns the PID (process ID) of a subprocess.
649
646
--
@@ -682,6 +679,18 @@ getStdout = pStdout
682
679
getStderr :: Process stdin stdout stderr -> stderr
683
680
getStderr = pStderr
684
681
682
+ -- | Get a process's configuration.
683
+ --
684
+ -- This is useful for constructing 'ExitCodeException's.
685
+ --
686
+ -- Note that the stdin, stdout, and stderr streams are stored in the 'Process',
687
+ -- not the 'ProcessConfig', so the returned 'ProcessConfig' will always have
688
+ -- empty stdin, stdout, and stderr values.
689
+ --
690
+ -- @since 0.2.12.0
691
+ getProcessConfig :: Process stdin stdout stderr -> ProcessConfig () () ()
692
+ getProcessConfig = pConfig
693
+
685
694
-- | Take 'System.Process.ProcessHandle' out of the 'Process'.
686
695
-- This method is needed in cases one need to use low level functions
687
696
-- from the @process@ package. Use cases for this method are:
@@ -703,3 +712,45 @@ getStderr = pStderr
703
712
-- @since 0.1.1
704
713
unsafeProcessHandle :: Process stdin stdout stderr -> P. ProcessHandle
705
714
unsafeProcessHandle = pHandle
715
+
716
+ -- | Get an 'ExitCodeException' containing the process's stdout and stderr data.
717
+ --
718
+ -- Note that this will call 'waitExitCode' to block until the process exits, if
719
+ -- it has not exited already.
720
+ --
721
+ -- Unlike 'checkExitCode' and similar, this will return an 'ExitCodeException'
722
+ -- even if the process exits with 'ExitSuccess'.
723
+ --
724
+ -- @since 0.2.12.0
725
+ exitCodeExceptionWithOutput :: MonadIO m
726
+ => Process stdin (STM L. ByteString ) (STM L. ByteString )
727
+ -> m ExitCodeException
728
+ exitCodeExceptionWithOutput process = liftIO $ atomically $ do
729
+ exitCode <- waitExitCodeSTM process
730
+ stdout <- getStdout process
731
+ stderr <- getStderr process
732
+ pure ExitCodeException
733
+ { eceExitCode = exitCode
734
+ , eceProcessConfig = pConfig process
735
+ , eceStdout = stdout
736
+ , eceStderr = stderr
737
+ }
738
+
739
+ -- | Get an 'ExitCodeException' containing no data other than the exit code and
740
+ -- process config.
741
+ --
742
+ -- Unlike 'checkExitCode' and similar, this will return an 'ExitCodeException'
743
+ -- even if the process exits with 'ExitSuccess'.
744
+ --
745
+ -- @since 0.2.12.0
746
+ exitCodeExceptionNoOutput :: Process stdin stdout stderr
747
+ -> ExitCode
748
+ -> ExitCodeException
749
+ exitCodeExceptionNoOutput process exitCode =
750
+ ExitCodeException
751
+ { eceExitCode = exitCode
752
+ , eceProcessConfig = pConfig process
753
+ , eceStdout = L. empty
754
+ , eceStderr = L. empty
755
+ }
756
+
0 commit comments