My code is posted below, not sure what the issue is but the return errors are listed as above along with **fatal error:** 

> 
> unexpectedly found nil while unwrapping an Optional value
> 
> 
> 

I have seen other answers to similar errors, but all of those involve things such as if let, which is not where my error seems to be occurring, the error message is connected to a line near the top that says "`audioFile = try AVAudioFile(forReading: recordedAudioURL as URl)`"

```
//
//  PlaySoundsViewController+Audio.swift
//  PitchPerfect
//
//  Copyright © 2016 Udacity. All rights reserved.
//
import UIKit
import AVFoundation

extension PlaySoundsViewController: AVAudioPlayerDelegate {
struct Alerts {
    static let DismissAlert = "Dismiss"
    static let RecordingDisabledTitle = "Recording Disabled"
    static let RecordingDisabledMessage = "You've disabled this app from recording your microphone. Check Settings."
    static let RecordingFailedTitle = "Recording Failed"
    static let RecordingFailedMessage = "Something went wrong with your recording."
    static let AudioRecorderError = "Audio Recorder Error"
    static let AudioSessionError = "Audio Session Error"
    static let AudioRecordingError = "Audio Recording Error"
    static let AudioFileError = "Audio File Error"
    static let AudioEngineError = "Audio Engine Error"
}

// raw values correspond to sender tags
enum PlayingState { case Playing, NotPlaying }

// MARK: Audio Functions

func setupAudio() {
    // initialize (recording) audio file
    do {
        audioFile = try AVAudioFile(forReading: recordedAudioURL as URL)
    } catch {
        showAlert(title: Alerts.AudioFileError, message: String(describing: error))
    }
    print("Audio has been setup")
}

func playSound(rate: Float? = nil, pitch: Float? = nil, echo: Bool = false, reverb: Bool = false) {

    // initialize audio engine components
    audioEngine = AVAudioEngine()

    // node for playing audio
    audioPlayerNode = AVAudioPlayerNode()
    audioEngine.attach(audioPlayerNode)

    // node for adjusting rate/pitch
    let changeRatePitchNode = AVAudioUnitTimePitch()
    if let pitch = pitch {
        changeRatePitchNode.pitch = pitch
    }
    if let rate = rate {
        changeRatePitchNode.rate = rate
    }
    audioEngine.attach(changeRatePitchNode)

    // node for echo
    let echoNode = AVAudioUnitDistortion()
    echoNode.loadFactoryPreset(.multiEcho1)
    audioEngine.attach(echoNode)

    // node for reverb
    let reverbNode = AVAudioUnitReverb()
    reverbNode.loadFactoryPreset(.cathedral)
    reverbNode.wetDryMix = 50
    audioEngine.attach(reverbNode)

    // connect nodes
    if echo == true && reverb == true {
        connectAudioNodes(nodes: audioPlayerNode, changeRatePitchNode, echoNode, reverbNode, audioEngine.outputNode)
    } else if echo == true {
        connectAudioNodes(nodes: audioPlayerNode, changeRatePitchNode, echoNode, audioEngine.outputNode)
    } else if reverb == true {
        connectAudioNodes(nodes: audioPlayerNode, changeRatePitchNode, reverbNode, audioEngine.outputNode)
    } else {
        connectAudioNodes(nodes: audioPlayerNode, changeRatePitchNode, audioEngine.outputNode)
    }

    // schedule to play and start the engine!
    audioPlayerNode.stop()
    audioPlayerNode.scheduleFile(audioFile, at: nil) {

        var delayInSeconds: Double = 0

        if let lastRenderTime = self.audioPlayerNode.lastRenderTime, let playerTime = self.audioPlayerNode.playerTime(forNodeTime: lastRenderTime) {

            if let rate = rate {
                delayInSeconds = Double(self.audioFile.length - playerTime.sampleTime) / Double(self.audioFile.processingFormat.sampleRate) / Double(rate)
            } else {
                delayInSeconds = Double(self.audioFile.length - playerTime.sampleTime) / Double(self.audioFile.processingFormat.sampleRate)
            }
        }

        // schedule a stop timer for when audio finishes playing
        self.stopTimer = Timer(timeInterval: delayInSeconds, target: self, selector: #selector(PlaySoundsViewController.stopAudio), userInfo: nil, repeats: false)
        RunLoop.main.add(self.stopTimer!, forMode: RunLoopMode.defaultRunLoopMode)
    }

    do {
        try audioEngine.start()
    } catch {
        showAlert(title: Alerts.AudioEngineError, message: String(describing: error))
        return
    }

    // play the recording!
    audioPlayerNode.play()
}

// MARK: Connect List of Audio Nodes

func connectAudioNodes(nodes: AVAudioNode...) {
    for x in 0..<nodes.count-1 {
        audioEngine.connect(nodes[x], to: nodes[x+1], format: audioFile.processingFormat)
    }
}

func stopAudio() {

    if let stopTimer = stopTimer {
        stopTimer.invalidate()
    }

    configureUI(playState: .NotPlaying)

    if let audioPlayerNode = audioPlayerNode {
        audioPlayerNode.stop()
    }

    if let audioEngine = audioEngine {
        audioEngine.stop()
        audioEngine.reset()
    }
}

// MARK: UI Functions

func configureUI(playState: PlayingState) {
    switch(playState) {
    case .Playing:
        setPlayButtonsEnabled(enabled: false)
        stopplaybackButton.isEnabled = true
    case .NotPlaying:
        setPlayButtonsEnabled(enabled: true)
        stopplaybackButton.isEnabled = false
    }
}

func setPlayButtonsEnabled(enabled: Bool) {
    snailButton.isEnabled = enabled
    chipmunkButton.isEnabled = enabled
    rabbitButton.isEnabled = enabled
    vaderButton.isEnabled = enabled
    echoButton.isEnabled = enabled
    reverbButton.isEnabled = enabled
}

func showAlert(title: String, message: String) {
    let alert = UIAlertController(title: title, message: message, preferredStyle: .alert)
    alert.addAction(UIAlertAction(title: Alerts.DismissAlert, style: .default, handler: nil))
    self.present(alert, animated: true, completion: nil)
}

}

```