## Query by Id Now that you were able to make a mutation, take the `Id` that was printed out and use it in your query to retrieve data. <BlockSwitcher> <Block name="Listener (iOS 11+)"> ```swift func getTodo() { Amplify.API.query(request: .get(Todo.self, byId: "9FCF5DD5-1D65-4A82-BE76-42CB438607A0")) { event in switch event { case .success(let result): switch result { case .success(let todo): guard let todo = todo else { print("Could not find todo") return } print("Successfully retrieved todo: \(todo)") case .failure(let error): print("Got failed result with \(error.errorDescription)") } case .failure(let error): print("Got failed event with error \(error)") } } } ``` </Block> <Block name="Combine (iOS 13+)"> ```swift func getTodo() -> AnyCancellable { Amplify.API .query(request: .get(Todo.self, byId: "9FCF5DD5-1D65-4A82-BE76-42CB438607A0")) .resultPublisher .sink { if case let .failure(error) = $0 { print("Got failed event with error \(error)") } } receiveValue: { result in switch result { case .success(let todo): guard let todo = todo else { print("Could not find todo") return } print("Successfully retrieved todo: \(todo)") case .failure(let error): print("Got failed result with \(error.errorDescription)") } } } ``` </Block> </BlockSwitcher> ## List Query You can get the list of items using `.paginatedList` with optional parameters `limit` and `where` to specify the page size and condition. By default, the page size is 1000. <BlockSwitcher> <Block name="Listener (iOS 11+)"> ```swift func listTodos() { let todo = Todo.keys let predicate = todo.name == "my first todo" && todo.description == "todo description" Amplify.API.query(request: .paginatedList(Todo.self, where: predicate, limit: 1000)) { event in switch event { case .success(let result): switch result { case .success(let todos): print("Successfully retrieved list of todos: \(todos)") case .failure(let error): print("Got failed result with \(error.errorDescription)") } case .failure(let error): print("Got failed event with error \(error)") } } } ``` </Block> <Block name="Combine (iOS 13+)"> ```swift func listTodos() -> AnyCancellable { let todo = Todo.keys let predicate = todo.name == "my first todo" && todo.description == "todo description" let sink = Amplify.API.query(request: .paginatedList(Todo.self, where: predicate, limit: 1000)) .resultPublisher .sink { if case let .failure(error) = $0 { print("Got failed event with error \(error)") } } receiveValue: { result in switch result { case .success(let todos): print("Successfully retrieved list of todos: \(todos)") case .failure(let error): print("Got failed result with \(error.errorDescription)") } } return sink } ``` </Block> </BlockSwitcher> ### List subsequent pages of items If you are using SwiftUI and have SwiftUI imported in the same code file, you will need to import the class `Amplify.List` to resolve name collision with `SwiftUI.List`: ```swift import SwiftUI import Amplify import class Amplify.List ``` For large data sets, you'll need to paginate through the results. After receiving the first page of results, you can check if there is a subsequent page and obtain the next page. ```swift var todos: [Todo] = [] var currentPage: List<Todo>? func listFirstPage() { let todo = Todo.keys let predicate = todo.name == "my first todo" && todo.description == "todo description" Amplify.API.query(request: .paginatedList(Todo.self, where: predicate, limit: 1000)) { event in switch event { case .success(let result): switch result { case .success(let todos): print("Successfully retrieved list of todos: \(todos)") self.currentPage = todos self.todos.append(contentsOf: todos) case .failure(let error): print("Got failed result with \(error.errorDescription)") } case .failure(let error): print("Got failed event with error \(error)") } } } func listNextPage() { if let current = currentPage, current.hasNextPage() { current.getNextPage { result in switch result { case .success(let todos): self.todos.append(contentsOf: todos) self.currentPage = todos case .failure(let coreError): print("Failed to get next page \(coreError)") } } } } ``` ## List all pages If you want to get all pages, retrieve the subsequent page when you have successfully retrieved the first or next page. 1. Update the above method `listFirstPage()` to `listAllPages()` 2. Call `listNextPageRecursively()` in the success block of the query in `listAllPages()` 2. Update the `listNextPage()` to `listNextPageRecursively()` 3. Call `listNextPageRecursively()` in the success block of the query in `listNextPageRecursively()` The completed changes should look like this ```swift var todos: [Todo] = [] var currentPage: List<Todo>? func listAllPages() { // 1. Updated from `listFirstPage()` let todo = Todo.keys let predicate = todo.name == "my first todo" && todo.description == "todo description" Amplify.API.query(request: .paginatedList(Todo.self, where: predicate, limit: 1000)) { event in switch event { case .success(let result): switch result { case .success(let todos): print("Successfully retrieved list of todos: \(todos)") self.currentPage = todos self.todos.append(contentsOf: todos) self.listNextPageRecursively() // 2. Added case .failure(let error): print("Got failed result with \(error.errorDescription)") } case .failure(let error): print("Got failed event with error \(error)") } } } func listNextPageRecursively() { // 3. Updated from `listNextPage()` if let current = currentPage, current.hasNextPage() { current.getNextPage { result in switch result { case .success(let todos): self.todos.append(contentsOf: todos) self.currentPage = todos self.listNextPageRecursively() // 4. Added case .failure(let coreError): print("Failed to get next page \(coreError)") } } } } ```