title: DispatchGroup notify() called immediately - not waiting for Enter/Leave
body: <p>I've been stuck with this problem for some time now, and I ran out of useful google results.</p>
  <p>I've got two requests, the first one retrieves some links from a server and in the other request I download the images from the links. After all the images finished downloading, I return the result to a view controller.</p>
  <p>Int the code <code>requestBanners()</code> is called from a UIViewController, entering the dispatch group. In theory, before leaving the dispatch group <code>storeImage()</code> should be called for every url that I got from the server, and on every call it should enter and leave the dispatch group, adding the image to an array. Once finished downloading all the images, it leaves the dispatch group, and fires the <code>notify()</code> to execute <code>setUpCollection()</code> on the UIViewController.</p>
  <p>Using <code>print()</code> as guidance to see what's really happening, I get:</p>
  <blockquote>
  <p>I'm downloading the urls</p>
  </blockquote>
  <blockquote>
  <p>Now I'm in the UIViewController
  <em>(this <code>print()</code> is called in the implementation of <code>setUpCollection()</code>)</em></p>
  </blockquote>
  <blockquote>
  <p>I'm downloading an image</p>
  </blockquote>
  <p>When it actually should be downloading the urls, then downloading the images and only then, returning to the UIViewController</p>
  <p>I've used semaphores at first, but then I thought using a dispatch group would be a cleaner solution.</p>
  <p>On both approaches, the empty bannersArr is returned before finishing downloading the images. Maybe that compact map is messing everything up.</p>
  <p>Here's the code:</p>
  <pre class="lang-swift prettyprint-override"><code>class BannersHelper {
      
      private var bannersArr: [UIImage] = []
      private let dispatchGroup = DispatchGroup()
      private var delegate: LoadBanners? = nil
      
      init(delegate: LoadBanners) {
          self.delegate = delegate
          
          dispatchGroup.notify(queue: .main) {
              self.delegate?.setUpCollection(errImg: self.bannersArr)
          }
      }
      
      func requestBanners() {
          print(&quot;I'm downloading the urls\n&quot;)
          self.dispatchGroup.enter()
          ServiceParametria.getBanners(handler: { response in
              guard let bannersResponse = response as? BannerModel else {
                  return
              }
              
              let banners = bannersResponse.data as! [DataBannerModel]
              let _ = banners.compactMap({self.storeImage(model: $0)})
              self.dispatchGroup.leave()
          })
      }
      
      private func storeImage(model: DataBannerModel) {
          print(&quot;I'm downloading an image\n&quot;)
          self.dispatchGroup.enter()
          ServiceParametria.getImage(url: model.urlImagen!, handler: { result in
              let image = result as! UIImage
              self.bannersArr.append(image)
              self.dispatchGroup.leave()
          })
      }
  }
  </code></pre>
  <p>Is there a better way to do this or am I just using the dispatch group wrong?</p>