title: Parsing XML in Swift 4
body: <p>I'm new to XML parsing in Swift and I found this code on <a href="https://stackoverflow.com/questions/31083348/parsing-xml-from-url-in-swift/31084545#31084545">Parsing XML from URL in Swift</a> but I get a <code>EXC_BAD_INSTRUCTION</code> error when I try running the code. The description of the error reads: <code>fatal error: unexpectedly found nil while unwrapping an Optional value</code></p>
  
  <p>This is my simple XML file:</p>
  
  <pre><code>&lt;xml&gt;
      &lt;book&gt;
          &lt;title&gt;Book Title&lt;/title&gt;
          &lt;author&gt;Book Author&lt;/author&gt;
      &lt;/book&gt;
  &lt;/xml&gt;
  </code></pre>
  
  <p>The following code creates an <code>XMLParser</code> object and parses the XML file located in my Documents.</p>
  
  <pre><code>// get xml file path from Documents and parse
  
  let filePath = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).last?.appendingPathComponent("example.xml")
  
  let parser = XMLParser(contentsOf: filePath!)
  parser?.delegate = self
  
  if (parser?.parse())! {
      print(self.results)
  }
  </code></pre>
  
  <p>Here I implement the <code>XMLParserDelegate</code> methods and define my dictionaries:</p>
  
  <pre><code>// a few constants that identify what element names we're looking for inside the XML
  
  let recordKey = "book"
  let dictionaryKeys = ["title","author"]
  
  // a few variables to hold the results as we parse the XML
  
  var results: [[String: String]]!          // the whole array of dictionaries
  var currentDictionary: [String: String]!  // the current dictionary
  var currentValue: String?                 // the current value for one of the keys in the dictionary
  
  // start element
  //
  // - If we're starting a "record" create the dictionary that will hold the results
  // - If we're starting one of our dictionary keys, initialize `currentValue` (otherwise leave `nil`)
  
  
  func parser(_ parser: XMLParser, didStartElement elementName: String, namespaceURI: String?, qualifiedName qName: String?, attributes attributeDict: [String : String] = [:]) {
  
      if elementName == recordKey {
  
          currentDictionary = [String : String]()
  
      } else if dictionaryKeys.contains(elementName) {
  
          currentValue = String()
  
      }
  }
  
  // found characters
  //
  // - If this is an element we care about, append those characters.
  // - If `currentValue` still `nil`, then do nothing.
  
  func parser(_ parser: XMLParser, foundCharacters string: String) {
  
      currentValue? += string
  
  }
  
  // end element
  //
  // - If we're at the end of the whole dictionary, then save that dictionary in our array
  // - If we're at the end of an element that belongs in the dictionary, then save that value in the dictionary
  
  
  func parser(_ parser: XMLParser, didEndElement elementName: String, namespaceURI: String?, qualifiedName qName: String?) {
  
      if elementName == recordKey {
  
          results.append(currentDictionary)
          currentDictionary = nil
  
      } else if dictionaryKeys.contains(elementName) {
  
          currentDictionary[elementName] = currentValue
          currentValue = nil
  
      }
  }
  
  // Just in case, if there's an error, report it. (We don't want to fly blind here.)
  
  func parser(_ parser: XMLParser, parseErrorOccurred parseError: Error) {
  
      print(parseError)
  
      currentValue = nil
      currentDictionary = nil
      results = nil
  
  }
  </code></pre>
  
  <p>The error is found on the <code>didEndElement</code> method when the <code>currentDictionary</code> is appended to the <code>results</code> dictionary.</p>
  
  <pre><code>func parser(_ parser: XMLParser, didEndElement elementName: String, namespaceURI: String?, qualifiedName qName: String?) {
  
      if elementName == recordKey {
  
          results.append(currentDictionary)    // Line with Error
          currentDictionary = nil
  
      } else if dictionaryKeys.contains(elementName) {
  
          currentDictionary[elementName] = currentValue
          currentValue = nil
  
      }
  }
  </code></pre>
  
  <p>Please help me solve this issue. I'm using the exact same code provided on <a href="https://stackoverflow.com/questions/31083348/parsing-xml-from-url-in-swift/31084545#31084545">Parsing XML from URL in Swift</a> and they don't seem to have any issues. Am I doing anything wrong?</p>