
Hey Mike,
f <- async getPages cancel f
you haven't read the PR I linked carefully enough yet :) It essentially says to never use the `async` function, as that is almost never what you want Full docs, with what you need to read highlighted: https://github.com/nh2/async/blob/1d96dc555b70a4c5aba07f15d0c7895545eb8582/C...
Am I guaranteed the the getURL() calls will definitely have either finished, or cancel?
For do (page1, page2, page3) <- runConcurrently $ (,,) <$> Concurrently (getURL "url1") <*> Concurrently (getURL "url2") <*> Concurrently (getURL "url3") you are guaranteed that when `runConcurrently` returns, all 3 downloads have finished successfully. Only the `instance Alternative Concurrently` (that is, when you use <|>) is implemented in terms of `race`. You are using <*>, as implemented in the `instance Applicative Concurrently`, which uses `concurrently`, which waits for both of two actions. Your code in
main = do f <- async getPages cancel f
does not make much sense: Here you're starting a thread that would go off do something, but then you immediately cancel that thread, so it won't achieve anything. You do not need to wrap things into additional `async`s. You can directly do, for example: main :: IO () main = do (page1, page2, page3) <- runConcurrently $ (,,) <$> Concurrently (getURL "url1") <*> Concurrently (getURL "url2") <*> Concurrently (getURL "url3") putStrLn "Here are the page contents:" putStrLn page1 putStrLn page2 putStrLn page3 Hope that helps! Niklas