forked from parse-community/Parse-Swift
-
-
Notifications
You must be signed in to change notification settings - Fork 7
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: Add fetchAll method for Parse pointers (#141)
* feat: Add fetchAll method for Parse pointers * add fetchAll methods * Update project * add test cases * nit * nits
- Loading branch information
Showing
12 changed files
with
467 additions
and
93 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
2 changes: 1 addition & 1 deletion
2
ParseSwift.xcodeproj/xcshareddata/xcschemes/ParseSwift.xcscheme
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
// | ||
// ParsePointerable+async.swift | ||
// ParseSwift | ||
// | ||
// Created by Corey Baker on 1/8/24. | ||
// Copyright © 2024 Network Reconnaissance Lab. All rights reserved. | ||
// | ||
|
||
import Foundation | ||
|
||
// MARK: Batch Support | ||
public extension Sequence where Element: ParsePointerObject { | ||
|
||
/** | ||
Fetches a collection of objects *aynchronously* with the current data from the server and sets | ||
an error if one occurs. | ||
- parameter includeKeys: The name(s) of the key(s) to include that are | ||
`ParseObject`s. Use `["*"]` to include all keys one level deep. This is similar to `include` and | ||
`includeAll` for `Query`. | ||
- parameter options: A set of header options sent to the server. Defaults to an empty set. | ||
- returns: Returns an array of Result enums with the object if a fetch was successful or a | ||
`ParseError` if it failed. | ||
- throws: An error of type `ParseError`. | ||
*/ | ||
@discardableResult func fetchAll( | ||
includeKeys: [String]? = nil, | ||
options: API.Options = [] | ||
) async throws -> [(Result<Self.Element.Object, ParseError>)] { | ||
try await withCheckedThrowingContinuation { continuation in | ||
self.fetchAll( | ||
includeKeys: includeKeys, | ||
options: options, | ||
completion: continuation.resume | ||
) | ||
} | ||
} | ||
|
||
} |
41 changes: 41 additions & 0 deletions
41
Sources/ParseSwift/Protocols/ParsePointerable+combine.swift
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
// | ||
// ParsePointerable+combine.swift | ||
// ParseSwift | ||
// | ||
// Created by Corey Baker on 1/8/24. | ||
// Copyright © 2024 Network Reconnaissance Lab. All rights reserved. | ||
// | ||
|
||
#if canImport(Combine) | ||
|
||
import Foundation | ||
import Combine | ||
|
||
// MARK: Batch Support | ||
public extension Sequence where Element: ParsePointerObject { | ||
|
||
/** | ||
Fetches a collection of objects *aynchronously* with the current data from the server and sets | ||
an error if one occurs. Publishes when complete. | ||
- parameter includeKeys: The name(s) of the key(s) to include that are | ||
`ParseObject`s. Use `["*"]` to include all keys one level deep. This is similar to `include` and | ||
`includeAll` for `Query`. | ||
- parameter options: A set of header options sent to the server. Defaults to an empty set. | ||
- returns: A publisher that eventually produces an an array of Result enums with the object if a fetch was | ||
successful or a `ParseError` if it failed. | ||
*/ | ||
func fetchAllPublisher( | ||
includeKeys: [String]? = nil, | ||
options: API.Options = []) -> Future<[(Result<Self.Element.Object, ParseError>)], ParseError> { | ||
Future { promise in | ||
self.fetchAll( | ||
includeKeys: includeKeys, | ||
options: options, | ||
completion: promise | ||
) | ||
} | ||
} | ||
|
||
} | ||
|
||
#endif |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,134 @@ | ||
// | ||
// ParsePointerable.swift | ||
// ParseSwift | ||
// | ||
// Created by Corey Baker on 12/25/23. | ||
// Copyright © 2023 Network Reconnaissance Lab. All rights reserved. | ||
// | ||
|
||
import Foundation | ||
|
||
public protocol ParsePointer: Encodable { | ||
|
||
var __type: String { get } // swiftlint:disable:this identifier_name | ||
|
||
var className: String { get } | ||
|
||
var objectId: String { get set } | ||
} | ||
|
||
extension ParsePointer { | ||
/** | ||
Determines if two objects have the same objectId. | ||
- parameter as: Object to compare. | ||
- returns: Returns a **true** if the other object has the same `objectId` or **false** if unsuccessful. | ||
*/ | ||
func hasSameObjectId(as other: any ParsePointer) -> Bool { | ||
return other.className == className && other.objectId == objectId | ||
} | ||
} | ||
|
||
public protocol ParsePointerObject: ParsePointer, ParseTypeable, Fetchable, Hashable { | ||
associatedtype Object: ParseObject | ||
} | ||
|
||
extension ParsePointerObject { | ||
|
||
/** | ||
Convert a Pointer to its respective `ParseObject`. | ||
- returns: A `ParseObject` created from this Pointer. | ||
*/ | ||
func toObject() -> Object { | ||
var object = Object() | ||
object.objectId = self.objectId | ||
return object | ||
} | ||
|
||
/** | ||
Determines if a `ParseObject` and `Pointer`have the same `objectId`. | ||
- parameter as: `ParseObject` to compare. | ||
- returns: Returns a **true** if the other object has the same `objectId` or **false** if unsuccessful. | ||
*/ | ||
func hasSameObjectId(as other: Object) -> Bool { | ||
return other.className == className && other.objectId == objectId | ||
} | ||
|
||
/** | ||
Determines if two `Pointer`'s have the same `objectId`. | ||
- parameter as: `Pointer` to compare. | ||
- returns: Returns a **true** if the other object has the same `objectId` or **false** if unsuccessful. | ||
*/ | ||
func hasSameObjectId(as other: Self) -> Bool { | ||
return other.className == className && other.objectId == objectId | ||
} | ||
|
||
/** | ||
Fetches the `ParseObject` *asynchronously* and executes the given callback block. | ||
- parameter includeKeys: The name(s) of the key(s) to include. Use `["*"]` to include | ||
all keys. | ||
- parameter options: A set of header options sent to the server. Defaults to an empty set. | ||
- parameter callbackQueue: The queue to return to after completion. Default | ||
value of .main. | ||
- parameter completion: The block to execute when completed. | ||
It should have the following argument signature: `(Result<T, ParseError>)`. | ||
- note: The default cache policy for this method is `.reloadIgnoringLocalCacheData`. If a developer | ||
desires a different policy, it should be inserted in `options`. | ||
*/ | ||
func fetch(includeKeys: [String]? = nil, | ||
options: API.Options = [], | ||
callbackQueue: DispatchQueue = .main, | ||
completion: @escaping (Result<Object, ParseError>) -> Void) { | ||
Task { | ||
var options = options | ||
options.insert(.cachePolicy(.reloadIgnoringLocalCacheData)) | ||
|
||
let method = API.Method.GET | ||
let path = API.Endpoint.object(className: className, objectId: objectId) | ||
let params: [String: String]? = { | ||
guard let includeKeys = includeKeys else { | ||
return nil | ||
} | ||
return ["include": "\(Set(includeKeys))"] | ||
}() | ||
let mapper = { (data) -> Object in | ||
try ParseCoding.jsonDecoder().decode(Object.self, from: data) | ||
} | ||
await API.NonParseBodyCommand<NoBody, Object>(method: method, path: path, params: params, mapper: mapper) | ||
.execute(options: options, | ||
callbackQueue: callbackQueue, | ||
completion: completion) | ||
} | ||
} | ||
} | ||
|
||
// MARK: Batch Support | ||
public extension Sequence where Element: ParsePointerObject { | ||
|
||
/** | ||
Fetches a collection of objects all at once *asynchronously* and executes the completion block when done. | ||
- parameter includeKeys: The name(s) of the key(s) to include that are | ||
`ParseObject`s. Use `["*"]` to include all keys one level deep. This is similar to `include` and | ||
`includeAll` for `Query`. | ||
- parameter options: A set of header options sent to the server. Defaults to an empty set. | ||
- parameter callbackQueue: The queue to return to after completion. Default value of .main. | ||
- parameter completion: The block to execute. | ||
It should have the following argument signature: `(Result<[(Result<Element.Object, ParseError>)], ParseError>)`. | ||
- warning: The order in which objects are returned are not guarenteed. You should not expect results in | ||
any particular order. | ||
*/ | ||
func fetchAll( | ||
includeKeys: [String]? = nil, | ||
options: API.Options = [], | ||
callbackQueue: DispatchQueue = .main, | ||
completion: @escaping (Result<[(Result<Element.Object, ParseError>)], ParseError>) -> Void | ||
) { | ||
let objects = Set(compactMap { $0.toObject() }) | ||
objects.fetchAll( | ||
includeKeys: includeKeys, | ||
options: options, | ||
callbackQueue: callbackQueue, | ||
completion: completion | ||
) | ||
} | ||
|
||
} |
Oops, something went wrong.