How to extract street, city, etc. from GMSPlace Address Components

For the latest Google Places API (July 2019) this is what could help you. Actually, Google now putting a couple of types for each element. So the "type" is now deprecated and "types" is new filed.

You can do something like this:

 for addressComponent in (self.mySelectedPlace?.addressComponents)! {
            for type in (addressComponent.types){

                switch(type){
                    case "country":
                        var country = addressComponent.name

                    case "postal_code":
                         var postCode = addressComponent.name

                default:
                    break
                }

            }
        }

A safe Swift 4.2 solution:

let name = place.addressComponents?.first(where: { $0.type == "city" })?.name

selectedPlace.addressComponents is a array of GMSAddressComponent which have 2 properties type and name. In you case it will be like

    for component in addressComponents! {
    if component.type == "city" {
    print(component.name)
    }
   }

GMSAddressComponent is a class not a dictionary or array that's you are getting this error.

Additional component types can be referred from the link.


Swift 4

    var keys = [String]()
    place.addressComponents?.forEach{keys.append($0.type)}
    var values = [String]()
    place.addressComponents?.forEach({ (component) in
        keys.forEach{ component.type == $0 ? values.append(component.name): nil}
    })
    print(values) 

It's working in Swift 5 and iOS 13.3

1. Create a function for showing GMSAutocompleteViewController

    func googlePlacesSearchVC() {
    
        let acController = GMSAutocompleteViewController()
        acController.delegate = self
        // Specify the place data types to return.
        let fields: GMSPlaceField = GMSPlaceField(rawValue: UInt(GMSPlaceField.name.rawValue) |
      UInt(GMSPlaceField.formattedAddress.rawValue)  |
               UInt(GMSPlaceField.addressComponents.rawValue))!
    
        acController.placeFields = fields
        // Specify a filter.
        let filter = GMSAutocompleteFilter()
        filter.country = "IN"
        acController.autocompleteFilter = filter

        acController.secondaryTextColor = .darkGray
        acController.primaryTextColor = .lightGray
        acController.primaryTextHighlightColor = .black
        acController.tableCellBackgroundColor = .whiteThree
        acController.tableCellSeparatorColor = .lightGray
        // Display the autocomplete view controller.
        present(acController, animated: true) {

            let views = acController.view.subviews
            let subviewsOfSubview = views.first!.subviews
            let subOfNavTransitionView = subviewsOfSubview[1].subviews
            let subOfContentView = subOfNavTransitionView[1].subviews
            let searchBar = subOfContentView[0] as! UISearchBar
            searchBar.searchTextField.placeholder = "places_picker_hint_add_address".localized
            searchBar.searchBarStyle = .minimal
            searchBar.searchTextField.font = UIFont.screenTitle16Pt
            searchBar.searchTextField.backgroundColor = UIColor.white
            searchBar.searchTextField.leftView?.tintColor = .darkGray
            searchBar.delegate?.searchBar?(searchBar, textDidChange: "")
        }
   }

2. Call that function where ever you need, for ex:-

   override func viewDidLoad() {
      super.viewDidLoad()

      googlePlacesSearchVC()
   }

3. Call GMSAutoCompleteViewControllerDelegates Methods. Here will get all details like Street, City, etc. from GMSPlace Address Components

extension ViewController {

      // Handle the user's selection.
      func viewController(_ viewController: GMSAutocompleteViewController, didAutocompleteWith place: GMSPlace) {
        
            // Show HouseAndFlat
            if place.name?.description != nil {
                
                yourTxtField.text = place.name?.description ?? ""
            }

            // Show latitude
            if place.coordinate.latitude.description.count != 0 {
                var latitude = place.coordinate.latitude
            }
            // Show longitude
            if place.coordinate.longitude.description.count != 0 {
                selectedLongitude = place.coordinate.longitude
            }

            // Show AddressComponents
            if place.addressComponents != nil {
                
                for addressComponent in (place.addressComponents)! {
                   for type in (addressComponent.types){

                       switch(type){
                           case "sublocality_level_2":
                               yourTxtField.text = addressComponent.name
                           case "sublocality_level_1":
                                yourTxtField.text = addressComponent.name
                            case "administrative_area_level_2":
                                yourTxtField.text = addressComponent.name

                            case "administrative_area_level_1":
                                 yourTxtField.text = addressComponent.name
                            case "country":
                                yourTxtField.text = addressComponent.name

                            case "postal_code":
                                 yourTxtField.text = addressComponent.name
                       default:
                           break
                       }
                   }
               }
            }
            dismiss(animated: true, completion: nil)
      }

      func viewController(_ viewController: GMSAutocompleteViewController, didFailAutocompleteWithError error: Error) {
            // TODO: handle the error.
            print("Error: ", error.localizedDescription)
      }

      // User canceled the operation.
      func wasCancelled(_ viewController: GMSAutocompleteViewController) {
            dismiss(animated: true, completion: nil)
      }
}

I have found an answer from this link