iOS
...
Data Objects
iOS에서 ParseSwift로 CRUD 데이터베이스 작업하기
16 분
ios에서 crud parse 객체 소개 parse에 데이터를 저장하는 것은 parse object parse object 클래스 주위에 구축되어 있습니다 각 parse object parse object 는 json 호환 데이터의 키 값 쌍을 포함합니다 이 데이터는 스키마가 없으므로 각 parse object parse object 에 어떤 키가 존재하는지 미리 지정할 필요가 없습니다 원하는 키 값 쌍을 설정하면, 우리의 백엔드가 이를 저장합니다 응용 프로그램의 필요에 따라 데이터 유형을 지정하고 number number , boolean boolean , string string , datetime datetime , list list , geopointers geopointers , 및 object object , 저장하기 전에 json으로 인코딩합니다 parse는 또한 pointers pointers 및 relations relations 를 사용하여 관계형 데이터를 저장하고 쿼리하는 것을 지원합니다 이 가이드에서는 crud 예제 앱(할 일 목록 앱)을 통해 기본 데이터 작업을 수행하는 방법을 배우게 되며, parseswift sdk parseswift sdk 를 사용하여 parse 서버 데이터베이스에서 데이터를 생성, 읽기, 업데이트 및 삭제하는 방법을 보여줍니다 이 튜토리얼은 xcode 12에서 생성된 기본 앱과 ios 14 을 사용합니다 언제든지 github 리포지토리를 통해 전체 프로젝트에 접근할 수 있습니다 ios 예제 리포지토리 목표 to learn how to perform basic database operations on back4app using a todo list app as an example 필수 조건 to complete this quickstart, you need xcode back4app에서 생성된 앱 다음의 new parse app 튜토리얼 을 따라 back4app에서 parse 앱을 만드는 방법을 배우세요 참고 다음의 parse sdk (swift) 설치 튜토리얼 을 따라 back4app에 연결된 xcode 프로젝트를 만드세요 우리의 할 일 목록 앱 이해하기 to better understand the parseswift sdk parseswift sdk you will perform crud operations on a to do list app the application database will have a simple task class with a title and a description (both 문자열 문자열 ) you can update each task’s title and/or description 우리가 사용할 명령어의 빠른 참조 once an object conforms the parseswift parseswift protocol, it automatically implements a set of methods that will allow you to manage the object and update any changes on your back4app database given the object todolistitem todolistitem 1 struct todolistitem parseobject { 2 3 4 /// title for the todo item 5 var title string? 6 7 /// description for the todo item 8 var description string? 9 } 이 방법들은 아래에 나열되어 있습니다 create //once created an instance of todolistitem object and set its custom properties, you can save it on your back4app database by calling any of the following methods 1 var newitem todoilisttem 2 // newitem's properties 3 4 // saves newitem on your back4app database synchronously and returns the new saved item it throws and error if something went wrong 5 let saveditem = try? newitem save() 6 7 // saves newitem on your back4app database asynchronously, and passes a result\<todolistitem, parseerror> object to the completion block to handle the save proccess 8 newitem save { result in 9 // handle the result to check the save was successfull or not 10 } 11 read //for reading objects stored on your back4app database, todolistitem now provides the query() static method which returns a query\<todolistitem> this query object can be constructed using on or more queryconstraint objects int he following way 1 let query = todolistitem query() // a query to fetch all todolistitem items on your back4app database 2 let query = todolistitem query("title" == "some title") // a query to fetch all todolistitem items with title "some title" on your back4app database 3 let query = todolistitem query(\["title" == "some title", "description" = "ok"]) // a query to fetch all todolistitem items with title = "some title" and description = "ok" 4 5 // fetchs the items synchronously or throws an error if found 6 let fetcheditems = try? query find() 7 8 // fetchs the items asynchronously and calls a completion block passing a result object containing the result of the operation 9 query find { result in 10 // handle the result 11 } update //given the objectid of an object stored on you back4app database, you can update it in the following way 1 let itemtoupdate = todolistitem(objectid "oobject id") 2 // update the properites of itemtoupdate 3 4 // save changes synchronousty 5 itemtoupdate save() 6 7 // or save changes asynchronously 8 itemtoupdate save { result in 9 // handle the result 10 } delete //the deletion process is performed by calling the method delete() on the object to be deleted 1 var itemtodelete todolistitem 2 3 // delete itemtodelete synchronously 4 try? itemtodelete delete() 5 6 // delte itemtodelete asynchronously 7 itemtodelete delete { result in 8 // handleresult 9 } 1 할 일 목록 앱 템플릿 만들기 언제든지 github 리포지토리를 통해 전체 프로젝트에 접근할 수 있습니다 ios 예제 리포지토리 xcode로 가서 scenedelegate swift scenedelegate swift 파일을 찾습니다 앱 상단에 내비게이션 바를 추가하기 위해, 다음과 같이 uinavigationcontroller uinavigationcontroller 를 루트 뷰 컨트롤러로 설정합니다 1 class scenedelegate uiresponder, uiwindowscenedelegate { 2 3 var window uiwindow? 4 5 func scene( scene uiscene, willconnectto session uiscenesession, options connectionoptions uiscene connectionoptions) { 6 guard let scene = (scene as? uiwindowscene) else { return } 7 8 window = init(windowscene scene) 9 window? rootviewcontroller = uinavigationcontroller(rootviewcontroller todolistcontroller()) 10 window? makekeyandvisible() 11 12 // additional logic 13 } 14 15 16 } 내비게이션 컨트롤러의 루트 뷰 컨트롤러 클래스 ( todolistcontroller todolistcontroller )는 uitableviewcontroller uitableviewcontroller , 이로 인해 항목 목록을 쉽게 레이아웃할 수 있습니다 2 crud 객체 설정 back4app 데이터베이스에 저장하려는 객체는 parseobject parseobject 프로토콜을 준수해야 합니다 우리의 할 일 목록 앱에서 이 객체는 todolistitem todolistitem 따라서, 먼저 이 객체를 생성해야 합니다 1 import foundation 2 import parseswift 3 4 struct todolistitem parseobject { 5 // required properties from parseobject protocol 6 var objectid string? 7 var createdat date? 8 var updatedat date? 9 var acl parseacl? 10 11 /// title for the todo item 12 var title string? 13 14 /// description for the todo item 15 var description string? 16 } 이 객체는 back4app 데이터베이스에서 클래스를 정의합니다 이 객체의 새로운 인스턴스는 todolistitem todolistitem 클래스 아래에 데이터베이스에 저장됩니다 3 todolistcontroller 설정 우리는 todolistcontroller todolistcontroller 에서 navigationbar navigationbar , 그리고 tableview tableview 속성을 위한 모든 필요한 구성을 구현해야 합니다 1 class todolistcontroller uitableviewcontroller { 2 var items \[todolistitem] = \[] 3 4 override func viewdidload() { 5 super viewdidload() 6 7 setuptableview() 8 setupnavigationbar() 9 } 10 11 private func setupnavigationbar() { 12 navigationitem title = "to do list" uppercased() 13 navigationitem rightbarbuttonitem = uibarbuttonitem(barbuttonsystemitem add, target self, action #selector(handlenewitem)) 14 } 15 16 private func setuptableview() { 17 tableview\ register(todolistitemcell self, forcellreuseidentifier todolistitemcell identifier) 18 } 19 20 override func tableview( tableview uitableview, numberofrowsinsection section int) > int { 21 items count 22 } 23 24 override func tableview( tableview uitableview, cellforrowat indexpath indexpath) > uitableviewcell { 25 let cell = tableview\ dequeuereusablecell(withidentifier todolistitemcell identifier, for indexpath) as! todolistitemcell 26 cell item = items\[indexpath row] 27 return cell 28 } 29 30 /// this method is called when the user wants to add a new item to the to do list 31 @objc private func handlenewitem() { 32 33 } 34 35 36 } 이 단계의 결론을 내리기 위해, 우리는 사용자 정의 테이블 뷰 셀을 구현합니다 todolistitemcell todolistitemcell 1 // content of todolistitemcell swift file 2 class todolistitemcell uitableviewcell { 3 class var identifier string { "\\(nsstringfromclass(self self)) identifier" } // cell's identifier 4 5 /// when set, it updates the title and detail texts of the cell 6 var item todolistitem? { 7 didset { 8 textlabel? text = item? title 9 detailtextlabel? text = item? description 10 } 11 } 12 13 override init(style uitableviewcell cellstyle, reuseidentifier string?) { 14 super init(style subtitle, reuseidentifier reuseidentifier) 15 16 accessorytype = detailbutton // this accessory button will be used to present edit options for the item 17 } 18 19 required init?(coder nscoder) { 20 super init(coder coder) 21 22 accessorytype = detailbutton // this accessory button will be used to present edit options for the item 23 } 24 } 4 crud 흐름 우리는 모든 crud 로직을 todolistcontroller todolistcontroller 클래스에 구현합니다 todolistcontroller swift todolistcontroller swift 로 가서 다음 메서드를 todolistcontroller todolistcontroller 클래스에 추가합니다 1 // mark crud flow 2 extension todolistcontroller { 3 /// creates a todolistitem and stores it on your back4app database 4 /// parameters 5 /// title the title for the to do task 6 /// description an optional description for the to to task 7 func createobject(title string, description string?) { 8 9 } 10 11 /// retrieves all the todolistitem objects from your back4app database 12 func readobjects() { 13 14 } 15 16 /// updates a todolistitem object on your back4app database 17 /// parameters 18 /// objectid the object id of the todolistitem to update 19 /// newtitle new title for the to to task 20 /// newdescription new description for the to do task 21 func updateobject(objectid string, newtitle string, newdescription string?) { 22 23 } 24 25 /// deletes a todolistitem on your back4app database 26 /// parameter item the item to be deleted on your back4app database 27 func deleteobject(item todolistitem) { 28 29 } 30 } \ 객체 생성 이제 createobject(title\ description ) createobject(title\ description ) 메서드를 구현하기 시작합니다 todolistitem todolistitem 의 인스턴스를 생성합니다 init(title\ description ) init(title\ description ) 초기자를 사용합니다 이 새 항목을 back4app 데이터베이스에 저장하기 위해 parseswift parseswift 프로토콜은 save() save() 메서드를 제공합니다 이 메서드는 동기 또는 비동기적으로 호출할 수 있으며, 사용 사례에 따라 하나를 선택하십시오 비동기 구현은 다음과 같아야 합니다 1 func createobject(title string, description string?) { 2 let item = todolistitem(title title, description description) 3 4 item save { \[weak self] result in 5 guard let self = self else { return } 6 switch result { 7 case success(let saveditem) 8 self items append(saveditem) 9 dispatchqueue main async { 10 self tableview\ insertrows(at \[indexpath(row self items count 1, section 0)], with right) 11 } 12 case failure(let error) 13 dispatchqueue main async { 14 self showalert(title "error", message "failed to save item \\(error message)") 15 } 16 } 17 } 18 } 이제 내비게이션 바 오른쪽에 위치한 추가 버튼의 작업을 완료할 수 있습니다 다음으로 이동하십시오 todolistcontroller todolistcontroller 다음 내용을 추가하십시오 1 class todolistcontroller uitableviewcontroller { 2 enum itemdescription int { case title = 0, description = 1 } 3 4 5 6 /// this method is called when the user wants to add a new item to the to do list 7 @objc private func handlenewitem() { 8 showeditcontroller(item nil) 9 } 10 11 /// presents an alert where the user enters a to do task for either create a new one (item parameter is nil) or edit an existing one 12 private func showeditcontroller(item todolistitem?) { 13 let controllertitle string = item == nil ? "new item" "update item" 14 15 let edititemalertcontroller = uialertcontroller(title controllertitle, message nil, preferredstyle alert) 16 17 edititemalertcontroller addtextfield { textfield in 18 textfield tag = itemdescription title rawvalue 19 textfield placeholder = "title" 20 textfield text = item? title 21 } 22 23 edititemalertcontroller addtextfield { textfield in 24 textfield tag = itemdescription description rawvalue 25 textfield placeholder = "description" 26 textfield text = item? description 27 } 28 29 let mainactiontitle string = item == nil ? "add" "update" 30 31 let mainaction uialertaction = uialertaction(title mainactiontitle, style default) { \[weak self] in 32 guard let title = edititemalertcontroller textfields? first(where { $0 tag == itemdescription title rawvalue })? text else { 33 return edititemalertcontroller dismiss(animated true, completion nil) 34 } 35 36 let description = edititemalertcontroller textfields? first(where { $0 tag == itemdescription description rawvalue })? text 37 38 edititemalertcontroller dismiss(animated true) { 39 if let objectid = item? objectid { // if the item passed as parameter is not nil, the alert will update it 40 self? updateobject(objectid objectid, newtitle title, newdescription description) 41 } else { 42 self? createobject(title title, description description) 43 } 44 } 45 } 46 47 let cancelaction = uialertaction(title "cancel", style cancel, handler nil) 48 49 edititemalertcontroller addaction(mainaction) 50 edititemalertcontroller addaction(cancelaction) 51 52 present(edititemalertcontroller, animated true, completion nil) 53 } 54 } \ 객체 읽기 우리는 readobjects() readobjects() 메서드로 이동합니다 todolistitem todolistitem 항목을 back4app 데이터베이스에서 가져오는 것은 query\<todolistitem> query\<todolistitem> 객체를 통해 수행됩니다 이 쿼리는 다음과 같이 인스턴스화됩니다 1 func readobjects() { 2 let query = todolistitem query() 3 4 } 이 튜토리얼에서는 back4app 데이터베이스에서 todolistitem todolistitem 유형의 모든 항목을 검색하는 쿼리를 사용합니다 특정 항목 집합을 검색하려는 경우 queryconstraint queryconstraint 요소를 todolistitem query(queryconstraint ) todolistitem query(queryconstraint ) 에 제공할 수 있습니다 예를 들어, title == "some title" title == "some title" ,인 경우 쿼리는 다음과 같은 형태를 취합니다 1 let query = todolistitem query("title" == "some title") 쿼리가 준비되면, 우리는 query find() query find() 를 호출하여 항목을 검색합니다 다시 말해, 이는 동기적으로 또는 비동기적으로 수행할 수 있습니다 우리의 할 일 목록 앱에서는 비동기적으로 구현합니다 1 func readobjects() { 2 let query = todolistitem query() 3 4 query find { \[weak self] result in 5 guard let self = self else { return } 6 switch result { 7 case success(let items) 8 self items = items 9 dispatchqueue main async { 10 self tableview\ reloadsections(\[0], with top) 11 } 12 case failure(let error) 13 dispatchqueue main async { 14 self showalert(title "error", message "failed to save item \\(error message)") 15 } 16 } 17 } 18 } 이제 readobjects() readobjects() 가 완료되었으므로, 이제 back4app 데이터베이스에 저장된 모든 작업을 가져와 앱이 포그라운드로 들어올 때 바로 보여줄 수 있습니다 todolistcontroller todolistcontroller 로 돌아가서 viewdidappear() viewdidappear() 메서드를 오버라이드합니다 1 class todolistcontroller uitableviewcontroller { 2 3 4 override func viewdidappear( animated bool) { 5 super viewdidappear(animated) 6 7 readobjects() 8 } 9 10 11 } \ 객체 업데이트 주어진 objectid objectid 의 todolistitem todolistitem 객체는 업데이트를 수행하는 것이 간단합니다 우리는 단순히 todolistitem todolistitem 객체를 init(objectid ) init(objectid ) 초기화자를 사용하여 인스턴스화합니다 다음으로, 필요한 속성을 업데이트하고 save() save() 메서드 (의 todolistitem todolistitem )를 호출하여 변경 사항을 저장합니다 1 func updateobject(objectid string, newtitle string, newdescription string?) { 2 var item = todolistitem(objectid objectid) 3 item title = newtitle 4 item description = newdescription 5 6 item save { \[weak self] result in 7 switch result { 8 case success 9 if let row = self? items firstindex(where { $0 objectid == item objectid }) { 10 self? items\[row] = item 11 dispatchqueue main async { 12 self? tableview\ reloadrows(at \[indexpath(row row, section 0)], with fade) 13 } 14 } 15 case failure(let error) 16 dispatchqueue main async { 17 self? showalert(title "error", message "failed to save item \\(error message)") 18 } 19 } 20 } 21 } \ 객체 삭제 back4app 데이터베이스에서 객체를 삭제하는 것은 객체를 생성하는 것과 매우 유사합니다 우리는 삭제하려는 항목의 objectid로 todolistitem todolistitem 의 인스턴스를 생성하는 것으로 시작합니다 다음으로, 우리는 단순히 객체의 delete() delete() 메서드를 호출합니다(동기 또는 비동기) 삭제가 성공하면 ui를 업데이트하고, 그렇지 않으면 오류를 보고합니다 1 func deleteobject(item todolistitem) { 2 item delete { \[weak self] result in 3 switch result { 4 case success 5 if let row = self? items firstindex(where { $0 objectid == item objectid }) { 6 self? items remove(at row) 7 dispatchqueue main async { 8 self? tableview\ deleterows(at \[indexpath(row row, section 0)], with left) 9 } 10 } 11 case failure(let error) 12 dispatchqueue main async { 13 self? showalert(title "error", message "failed to save item \\(error message)") 14 } 15 } 16 } 17 } 다음과 함께 deleteobject(item ) deleteobject(item ) 및 updateobject(objectid\ newtitle\ newdescription) updateobject(objectid\ newtitle\ newdescription) 가 완료되면, 이러한 작업을 호출하는 해당 작업을 추가합니다 todolistcontroller todolistcontroller 로 돌아가서 추가합니다 1 // mark uitableviewdatasource delegate 2 extension todolistcontroller { 3 // when the user taps on the accessory button of a cell, we present the edit options for the to do list task 4 override func tableview( tableview uitableview, accessorybuttontappedforrowwith indexpath indexpath) { 5 guard !items isempty else { return } 6 7 showeditoptions(item items\[indexpath row]) 8 } 9 10 /// presents a sheet where the user can select an action for the to do list item 11 private func showeditoptions(item todolistitem) { 12 let alertcontroller = uialertcontroller(title title, message nil, preferredstyle actionsheet) 13 14 let editaction = uialertaction(title "edit", style default) { \[weak self] in 15 self? showeditcontroller(item item) 16 } 17 18 let deleteaction = uialertaction(title "delete", style destructive) { \[weak self] in 19 alertcontroller dismiss(animated true) { 20 self? deleteobject(item item) 21 } 22 } 23 24 let cancelaction = uialertaction(title "cancel", style cancel) { in 25 alertcontroller dismiss(animated true, completion nil) 26 } 27 28 alertcontroller addaction(editaction) 29 alertcontroller addaction(deleteaction) 30 alertcontroller addaction(cancelaction) 31 32 present(alertcontroller, animated true, completion nil) 33 } 34 } 앞서 언급한 바와 같이, 각 todolistitemcell todolistitemcell 의 보조 버튼은 tableview( accessorybuttontappedforrowwith ) tableview( accessorybuttontappedforrowwith ) 대리자 메서드를 통해 편집 시트를 호출합니다 완료되었습니다! 이 시점에서, ios에서 parse를 사용하여 기본 crud 작업을 수행하는 방법을 배웠습니다