Rage
Rage

Reputation: 970

Basic Auth not working in Alamofire Swift

I am trying to get a Client Credential token, which is needed for Spotify's public Web API to search for public tracks.

It is extremely simple to get a token using postman.

REQUEST BODY PARAMETER: VALUE: grant_type Set it to client_credentials. 

The header of this POST request must contain the following parameter:

HEADER PARAMETER: VALUE:  Authorization  Base 64 encoded string that contains the client ID and client secret key. The field must have the format: Authorization: Basic <base64 encoded client_id:client_secret>

I need to get a Spotify token in Swift. I started with this decodable struct:

struct SpotifyAuth: Decodable {
    var access_token: String
    var expires_in: Int
}

I have then tried dozens of variations of the following code to no avail:

let headers : HTTPHeaders = ["Content-Type":"application/x-www-form-urlencoded"]

let paramaters : Parameters = ["grant_type": "client_credentials", ]

    AF.request("https://accounts.spotify.com/api/token", method: .post, parameters: paramaters, encoding: URLEncoding.httpBody, headers: headers ).authenticate(username: "{clientID}", password:"{clientSecrent}").responseJSON { response in
            if response.error == nil {
                do {
                    let spotifyAuth = try JSONDecoder().decode(SpotifyAuth.self, from: response.data!)

                    completion(.success(spotifyAuth))
                } catch let error {
                    completion(.failure(error))
                }
            } else {
                completion(.failure(response.error!))
            }
        
    }

Is anyone aware of what I am doing wrong/the correct way of acquiring a simple token from Spotify?

Upvotes: 3

Views: 1083

Answers (1)

Jon Shier
Jon Shier

Reputation: 12800

authenticate() is used to respond to authentication challenges. It does not unconditionally add the header. If the server does not respond with a Basic challenge you'll need to add the header yourself. Alamofire has a convenience method to help: HTTPHeader.authorization(username:password:). This will properly generate the Basic header for you.

Upvotes: 4

Related Questions