Notice
Recent Posts
Recent Comments
Link
«   2025/12   »
1 2 3 4 5 6
7 8 9 10 11 12 13
14 15 16 17 18 19 20
21 22 23 24 25 26 27
28 29 30 31
Tags
more
Archives
Today
Total
관리 메뉴

Dev.heestory

[UIKit/iOS] 게시판을 만들며 알아보는 Alamofire 본문

iOS

[UIKit/iOS] 게시판을 만들며 알아보는 Alamofire

cloudhee 2023. 1. 25. 21:54

교내 동아리에서 동아리 학습 커뮤니티 어플을 만들게 되었는데, 공지사항 등의 게시판을 만들어야 했다.

nodeJS 서버에서 백엔드 개발자가 주신 API를 통해서 데이터를 주고 받아야하는데,

swift에서 http통신을 쓰기 위해서는 애플에서 제공해주는 URLSession으로 네트워킹이 가능하다.

그러나 빠르고 간단하게 프로젝트를 완성하기 위해 Alamofire를 쓰기로 결정했다.

Alamofire가 무엇이길래 URLSession보다 간단하게 사용할 수 있는 것 일까 ?

Alamofire는 Swift로 작성된 HTTP 네트워킹 라이브러리이다.
즉, Swift의 내장되어 있는 네트워크 기능을 이용하여 구현된 라이브러리이다.

네트워크 통신 작업을 알라모파이어 구현으로 내부로 감추고 겉으로 구현된 클래스와 메소드들을 제공한다.

따라서 코드의 가독성을 높이면서도 에러 발생 확률을 줄이며 HTTP통신을 할 수 있다.

다음으로 Alamofire의 사용법을 게시판 예제와 함께 알아보자.

사용법

일단 REST API에서 이용되는 대표적인 method인 get, post, put, delete는 아래와 같이 사용하면 된다.

//GET
AF.request(url)
//POST
AF.request(url, method: .post)
//PUT
AF.request(url, method: .put)
//DEL
AF.request(url, method: .delete)

게시글을 읽는 경우와 생성하는 경우가 있다.
서버에서 데이터를 읽어와 뷰에 뿌려줄 때 GET metod를, 게시글을 작성할 때에는 POST method를 사용하였다.

먼저 서버에서 데이터를 읽어오는 과정을 살펴보자

서버에 있는 공지사항들을 불러오기 위해 아래와 같이 Model을 만들어주었다.

공지사항 데이터를 받아오는 함수를 따로 만들어 Alamofire로 통신하였다.

func getNoticeData() {
        let url = "\(Config.appURL)/post/notice?sort=-createdAt&page=\(page)&limit=20"
        let header : HTTPHeaders = ["Content-Type": "application/json"]
        let dataRequest = AF.request(url, method: .get, encoding: JSONEncoding.default, headers: header)
        // 서버 응답 처리
        dataRequest.validate().responseJSON { (response) in
            switch response.result {
            case .success(let obj):
                do {
                    let dataJSON = try JSONSerialization.data(withJSONObject:obj, options: .prettyPrinted)
                    let getData = try JSONDecoder().decode(APIResponse.self, from: dataJSON)

                    for i in 0 ..< getData.data.count {
                        self.noticeData.append(getData.data[i])
                    }
                    DispatchQueue.main.async {
                        self.noticeTableView.reloadData()
                    }
                } catch(let error) {
                    print(error)
                }
            case .failure(let error) :
                print(error)
            }
        }
    }

위의 코드에서 dataRequest 변수에서 Alamofire로 통신을 하는데, JSONEncoding은 parameter 객체를 JSON 타입으로 인코딩 하는 것이다.

dataRequest.validate().responseJSON { (response) in
            switch response.result {
            case .success(let obj):
                do {
                    let dataJSON = try JSONSerialization.data(withJSONObject:obj, options: .prettyPrinted)
                    let getData = try JSONDecoder().decode(APIResponse.self, from: dataJSON)

validate()는 자동적으로 정상 status code범위와, request의 헤더와 일치하는 Content-Type에 대해 유효성을 검증한다.

response의 결과가 success일 때, 즉 상태 코드의 범위가 200 - 300일 때

  1. dataJSON 변수에 JSONSerialization을 사용하여 서버에서 받아온 json타입의 데이터들을 Array나 Dictionary 객체 타입으로 만든다.
  2. dataJSON으로부터 JSON을 파싱해 getData변수에 넣어주었다.

서버에서 가져오는 데이터는 대부분 JSON 포맷을 따르기 때문에 이 JSON 데이터를 IOS 앱에 보여주려면 Swift를 통해 가공해야 한다.

이 때 사용한 JSONDecoder는 스위프트의 Foundation 프레임워크에 있는 클래스이다. JSONDecoder()를 선언해 이 클래스에 있는

decode<T>(\_:T.type, from: Data)라는 메서드를 활용하여 첫번째 인자에 구조체 타입을 넣어주면, 그 구조체에 맞게 JSON을 파싱해준다.

struct APIResponse: Codable {
    let data: [Notice]
    var status: Int
    var message: String
    var success: Bool
    var count: Int
}

이 APIResponse JSON구조체를 파싱하였고 이 구조체 안의 [Notice]타입의 data를 보여줘야함으로 noticeData에 담아주었다.

이 noticeData를 활용하여 뷰에 뿌려주는 작업을 하면 된다.

여기까지 Alamofire를 이용하여 데이터를 가져와보았다.

그렇다면 사용자가 작성한 게시글을 저장하기 위해 서버에 전송하는 POST 메소드는 어떻게 사용할까 ?

왼쪽의 형태를 바디에 담아 요청을 보내면 오른쪽의 형태로 응답이 온다.

위 이미지는 스토리보드에서 제목과 글 내용을 적을 부분을 만들어놓은 사진이다.

여기서 등록버튼을 누르면 사용자가 작성한 제목과 글을 서버에 전송하는 코드를 자세히 살펴보자

@IBAction func onBtnPost(_ sender: UIButton) {

        let data = [
            "content": self.contentTextView.text!,
            "title": self.titleTextField.text!,
        ]

        // API 호출
        let url = "\(Config.appURL)/post/notice"
        let dataRequest = AF.request(url, method: .post, parameters: data, encoding: JSONEncoding.default)
        // 서버 응답 처리
        dataRequest.validate().responseData { response in
            switch response.result {
            case .success:
                let alert = UIAlertController(title: "", message: "등록되었습니다.", preferredStyle: .alert)
                let okay = UIAlertAction(title: "확인", style: .default, handler: nil)
                alert.addAction(okay)
                self.present(alert, animated: true)

            case let .failure(error):
                let fail = UIAlertController(title: "오류", message: "등록에 실패하였습니다", preferredStyle: .alert)
                let okay = UIAlertAction(title: "확인", style: .default, handler: nil)
                fail.addAction(okay)
                self.present(fail, animated: true)
                print(error)
            }
        }
    }

POST는 서버에 보낼 데이터를 parameters 자리에 작성하면 된다.

등록 버튼을 누를 시 Dictionary 타입의 제목과 글 내용을 담은 data 배열을 parameters에 담아 보내준다.

위의 get방식과 마찬가지로 response의 결과가 success일 때는 성공적으로 게시글이 작성된 것 이므로 등록되었다는 alert를 띄워준다.

Alamofire를 써서 편했던 부분

Alamofire를 사용하여 HTTP 통신을 해봤는데 확실히 직접 구축하기엔 복잡한 코드들을 쉽게 사용할 수 있어 코드가 간소화되고 가독성이 좋아지는 것을 느꼈다.

 

 

자세한 코드는 아래 깃허브주소를 통해 확인할 수 있다.

https://github.com/cbnu-sequence/sequence-ios-app

 

GitHub - cbnu-sequence/sequence-ios-app: 학습 보조 커뮤니티 시퀀스 iOS 어플리케이션 🌹

학습 보조 커뮤니티 시퀀스 iOS 어플리케이션 🌹. Contribute to cbnu-sequence/sequence-ios-app development by creating an account on GitHub.

github.com

 

 

 

글 읽어주셔서 감사합니다 :)

제가 잘못 알고 있는 내용이 있거나 말씀해주실 부분이 있다면 댓글 한 번 적어주시면 정말 감사하겠습니다.