電子書籍検索API（楽天API）から画像、タイトル、著者名、説明文を取得して表示

#今回の内容

* `UITextField`に入力された値から検索をして、取得したデータを`UITableView`に表示していきます。


#コード

##Model

```Swift:EbookDetailDatas
struct EbookDetailDatas{
    
    let mediumImageUrl:String?
    let title:String?
    let author:String?
    let itemCaption:String?
}
```

```Swift:AlamofireProcess
import Alamofire
import SwiftyJSON


class AlamofireProcess{
    
    private var privateMediumImageUrl:String?
    private var privateTitle:String?
    private var privateAuthor:String?
    private var privateItemCaption:String?
    
    private var resultEbookDetailArray = [EbookDetailDatas]()
}

extension AlamofireProcess{
    
    public func getEbookDetailData(searchKeyWord:String?,completion: @escaping ([EbookDetailDatas]?,Error?) -> Void){
        
        guard let keyword = searchKeyWord else { return }
        
        let apiKey = "https://app.rakuten.co.jp/services/api/BooksCD/Search/20170404?format=json&artistName=\(keyword.urlEncoded)&hits=30&applicationId=アプリID"

        
        AF.request(apiKey, method: .get, parameters: nil, encoding: JSONEncoding.default).responseJSON {[self] response in
            
            switch response.result{
                
            case .success:
                
                let detailData = JSON(response.data as Any)
                
                print(detailData)
                
                for dataCount in 0..<30{
                    
                    getDataNilCheck(mediumImageUrlCheck: detailData["Items"][dataCount]["Item"]["mediumImageUrl"].string,
                                    titleCheck: detailData["Items"][dataCount]["Item"]["title"].string,
                                    authorCheck: detailData["Items"][dataCount]["Item"]["author"].string,
                                    itemCaptionCheck: detailData["Items"][dataCount]["Item"]["itemCaption"].string)
                    
                    resultEbookDetailArray.append(EbookDetailDatas(mediumImageUrl: privateMediumImageUrl,
                                                                   title: privateTitle,
                                                                   author: privateAuthor,
                                                                   itemCaption: privateItemCaption))
                    
                    
                }
                print(resultEbookDetailArray)
                completion(resultEbookDetailArray, nil)
                
                
            case .failure(let error):
                
                completion(nil, error)
            }
        }
        
    }
}

extension AlamofireProcess{
    
    private func getDataNilCheck(mediumImageUrlCheck:String?,titleCheck:String?,authorCheck:String?,itemCaptionCheck:String?){
        
        if mediumImageUrlCheck != nil{
            
            privateMediumImageUrl = mediumImageUrlCheck
        }else{
            
            privateMediumImageUrl = "nosign"
        }
        
        if titleCheck != nil{
            
            privateTitle = titleCheck
        }else{
            
            privateTitle = "読み込みエラー"
        }
        
        if authorCheck != nil{
            
            privateAuthor = authorCheck
        }else{
            
            privateAuthor = "読み込みエラー"
        }
        
        if itemCaptionCheck != nil{
            
            privateItemCaption = itemCaptionCheck
        }else{
            
            privateItemCaption = "読み込みエラー"
        }   
    }

}

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
<img width="150" alt="4D28CEF3-C0CA-4A75-827D-2497599557BC_1_201_a.jpeg" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1466343/43abdc47-a0ac-d309-110f-688f9f692ff2.jpeg">

###TableViewCustomCell
<img width="150" alt="45765B2E-70C8-410B-BC4E-2160122E24EE_4_5005_c.jpeg" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1466343/14d8f89a-eda4-25cd-e20a-f343c2bba823.jpeg">

```Swift:
import UIKit

class TableViewCustomCell: UITableViewCell {

    
    @IBOutlet weak var mediumImageView: UIImageView!
    @IBOutlet weak var titleLabel: UILabel!
    @IBOutlet weak var authorLabel: UILabel!
    @IBOutlet weak var itemCaptionTextView: UITextView!
    
    override func awakeFromNib() {
        super.awakeFromNib()
        // Initialization code
    }

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

        // Configure the view for the selected state
    }
 
    required init?(coder: NSCoder) {
        super.init(coder: coder)
    }
    
    override func prepareForReuse() {
        super.prepareForReuse()
        
        mediumImageView.image = UIImage(named: "")
        titleLabel.text = ""
        authorLabel.text = ""
        itemCaptionTextView.text = ""
    }
}
```



##Controller

```Swift:
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()
    
    private var cellContentsArray = [EbookDetailDatas]()
    
    override func viewDidLoad() {
        super.viewDidLoad()
 
        resultTableView.register(UINib(nibName: "TableViewCustomCell", bundle: nil), forCellReuseIdentifier: "EbookDetailCell")
        resultTableView.delegate = self
        resultTableView.dataSource = self
        
    }

    @IBAction func search(_ sender: UIButton) {
        
        alamofireProcess.getEbookDetailData(searchKeyWord: searchTextField.text) { result, error in
            
            if error != nil{
                
                return
            }
            
            DispatchQueue.main.asyncAfter(deadline: .now() + 5) {[self] in
                
                cellContentsArray = result!
                resultTableView.reloadData()
            }
        }
    }
    
}

extension ViewController:UITableViewDelegate{
    
    func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
        
        return tableView.frame.height / 3.5
    }

}

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: "EbookDetailCell", for: indexPath) as! TableViewCustomCell
        
        cell.mediumImageView.sd_setImage(with: URL(string: cellContentsArray[indexPath.row].mediumImageUrl!), completed: nil)
        cell.titleLabel.text = cellContentsArray[indexPath.row].title
        cell.authorLabel.text = cellContentsArray[indexPath.row].author
        cell.itemCaptionTextView.text = cellContentsArray[indexPath.row].itemCaption
        
        return cell
    }
}
```

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