LoginSignup
0
0

More than 1 year has passed since last update.

DispatchGroupの.leaveと.notifyを使用して取得したデータを表示(楽天API)

Posted at

今回の内容

  • 最近、DispatchQueue.main.asyncAfterをよく使ってましたが、データの取得が終わった時にUITableViewに表示させる為にDispatchGroup.leave.notifyを使用してます。

コード

Model

GetDataDetailModel
struct GetDataDetailModel{

    let mediumImageURL:String?
    let itemName:String?
    let itemPrice:Int?
    let itemCaption:String?
}

AlamofireProcess
import Alamofire
import SwiftyJSON

class AlamofireProcess{

    public var getDataResultArray = [GetDataDetailModel]()
    private var keyword:String?

    init(getKey:String?){

        keyword = getKey
    }
}

extension AlamofireProcess{

    public func getItemDetailData(completion: @escaping() -> Void){

        guard let key = keyword else { return }

        let apiKey = "https://app.rakuten.co.jp/services/api/IchibaItem/Search/20170706?format=json&keyword=\(key.urlEncoded)&applicationId=作成したアプリID"

        AF.request(apiKey, method: .get, parameters: nil, encoding: JSONEncoding.default).responseJSON {[self] response in

            switch response.result{

            case .success:

                let jsonDetail = JSON(response.data as Any)
                getDataResultArray = []

                for dataCount in 0..<jsonDetail["Items"].count{

                    if let getMediumImageURL = jsonDetail["Items"][dataCount]["Item"]["mediumImageUrls"][0]["imageUrl"].string,
                       let getItemName = jsonDetail["Items"][dataCount]["Item"]["itemName"].string,
                       let getItemPrice = jsonDetail["Items"][dataCount]["Item"]["itemPrice"].int,
                       let getItemCaption = jsonDetail["Items"][dataCount]["Item"]["itemCaption"].string{

                        getDataResultArray.append(GetDataDetailModel(mediumImageURL: getMediumImageURL,
                                                                     itemName: getItemName,
                                                                     itemPrice: getItemPrice,
                                                                     itemCaption: getItemCaption))
                    }

                }
                completion()

            case .failure:

                completion()
            }
        }
    }
}

extension String{

    var urlEncoded:String{

        let charset = CharacterSet.alphanumerics.union(.init(charactersIn: "/?-._~"))
        let remove = removingPercentEncoding ?? self

        return remove.addingPercentEncoding(withAllowedCharacters: charset) ?? remove
    }
}

View

Main.storyboard

69F900EB-C36B-4257-8460-45FC523CCFF6_4_5005_c.jpeg

SearchResultCell

27768BE6-0468-4453-B3E9-2989E1B13DC5_4_5005_c.jpeg

SearchResultCell
import UIKit

class SearchResultCell: UITableViewCell {

    @IBOutlet weak var mediumImageView: UIImageView!
    @IBOutlet weak var itemNameLabel: UILabel!
    @IBOutlet weak var itemPriceLabel: UILabel!
    @IBOutlet weak var itemCaptionView: UITextView!

    override func awakeFromNib() {
        super.awakeFromNib()

    }

    override func setSelected(_ selected: Bool, animated: Bool) {
        super.setSelected(selected, animated: animated)


    }

    required init?(coder: NSCoder) {
        super.init(coder: coder)

    }

    override func prepareForReuse() {
        super.prepareForReuse()

        mediumImageView.image = UIImage(named: "")
        itemNameLabel.text = ""
        itemPriceLabel.text = ""
        itemCaptionView.text = ""
    }
}

Controller

import UIKit
import SDWebImage

class ViewController: UIViewController {

    @IBOutlet weak var searchTextField: UITextField!
    @IBOutlet weak var searchButton: UIButton!
    @IBOutlet weak var resultTableView: UITableView!

    private let alamofireProcess = AlamofireProcess(getKey: nil)

    private let dispatchGroup = DispatchGroup()
    private let dispachQueue = DispatchQueue(label: "alamofire",attributes: .concurrent)

    private var cellContentsArray = [GetDataDetailModel]()

    override func viewDidLoad() {
        super.viewDidLoad()

        resultTableView.register(UINib(nibName: "SearchResultCell", bundle: nil), forCellReuseIdentifier: "ItemDetailCell")
        resultTableView.delegate = self
        resultTableView.dataSource = self

    }

    @IBAction func search(_ sender: UIButton) {

        let afProcess = AlamofireProcess(getKey: searchTextField.text)

        dispatchGroup.enter()
        dispachQueue.async {[self] in

            afProcess.getItemDetailData {

                self.dispatchGroup.leave()
            }
        }

        dispatchGroup.notify(queue: .main){ [self] in

            cellContentsArray = afProcess.getDataResultArray
            print(cellContentsArray)
            resultTableView.reloadData()
        }
    }

}

extension ViewController:UITableViewDelegate{

    func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {

        return tableView.frame.height / 2.4
    }
}


extension ViewController:UITableViewDataSource{

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {

        return cellContentsArray.count
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

        let cell = tableView.dequeueReusableCell(withIdentifier: "ItemDetailCell", for: indexPath) as! SearchResultCell

        cell.mediumImageView.sd_setImage(with: URL(string: cellContentsArray[indexPath.row].mediumImageURL!), completed: nil)
        cell.itemNameLabel.text = cellContentsArray[indexPath.row].itemName
        cell.itemPriceLabel.text = String(cellContentsArray[indexPath.row].itemPrice!) + "円"
        cell.itemCaptionView.text = cellContentsArray[indexPath.row].itemCaption

        return cell
    }
}

終わり

ご指摘、ご質問などありましたら、コメントまでお願い致します。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0