I have the following code from RevenueCat and I would like to put all of my offerings in a variable
The following is not working for me
func allOffering(){
let myOfferings = Purchases.shared.getOfferings { (offerings, error) in
if let offerings = offerings {
// Display current offering with offerings.current
}
}
// print to log
print(myOfferings)
}
I can print all of the offerings this way however I want to put it in a value so that I can use the data in other places in the function
func allOffering(){
let myOfferings = Purchases.shared.getOfferings { (offerings, error) in
if let offerings = offerings {
// Display current offering with offerings.current
print(offerings.current)
}
}
// print to log
print(myOfferings)
}
CodePudding user response:
The reason it's not working is because myOfferings
is being set to the closure itself, not the actual values it loads. The offerings won't be available outside of the scope of the completion closure yet because they still need to be fetched.
The point of the completion block is that you can execute code once you know for a fact that the offerings are available (or once you've received an error, to which you can then respond appropriately).
The easiest thing to do is to perform any action you need myOfferings
for inside that completion block - or pass the values as a parameter to other functions:
Purchases.shared.getOfferings { [weak self] (offerings, error) in
if let offerings = offerings {
self?.doSomething(with: offerings)
}
}
func doSomething(with offers: [Offer]) {
// do something
}
That might already address what you need. If not, there are other options.
An approach I like to take when I need access to values like this independently from the completion block is to use a LoadingState wrapper, which I can then use to see if the values are available yet. For example:
enum OfferingsLoadingState {
case initialized
case loaded([Offering])
case error(Error)
}
Then I can make a variable like this:
var myOfferings: OfferingLoadingState = .initialized
And set its value to the fetched offerings once it's done:
Purchases.shared.getOfferings { [weak self] (offerings, error) in
if let offerings = offerings {
self?.myOfferings = .loaded(offerings)
}
}
When using myOfferings
outside of the completion block, you can then check if it's loaded and if it is get the values from it.
switch myOfferings {
case .loaded(let offerings):
print(offerings)
default:
// TODO: do something here if needed
break