Skip to content

Commit

Permalink
Merge pull request #94 from superwall-me/develop
Browse files Browse the repository at this point in the history
v1.0.0-alpha.45
  • Loading branch information
yusuftor authored Feb 2, 2024
2 parents 5813403 + e17f904 commit 716bfd3
Show file tree
Hide file tree
Showing 7 changed files with 81 additions and 53 deletions.
8 changes: 8 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,14 @@

The changelog for `Superwall`. Also see the [releases](https://github.com/superwall-me/Superwall-Android/releases) on GitHub.

## 1.0.0-alpha.45

### Fixes

- Fixes issue where the `paywallProductsLoad_fail` event wasn't correctly being logged. This is a
"soft fail", meaning that even though it gets logged, your paywall will still show. The error message
with the event has been updated to include all product subscription IDs that are failing to be retrieved.

## 1.0.0-alpha.44

### Fixes
Expand Down
2 changes: 1 addition & 1 deletion superwall/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ plugins {
id("maven-publish")
}

version = "1.0.0-alpha.44"
version = "1.0.0-alpha.45"

android {
compileSdk = 33
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@ import android.widget.TextView
import androidx.appcompat.app.AppCompatActivity
import androidx.appcompat.app.AppCompatDelegate
import com.superwall.sdk.debug.localizations.SWLocalizationActivity
import com.superwall.sdk.dependencies.TriggerSessionManagerFactory
import kotlinx.coroutines.withContext

interface AppCompatActivityEncapsulatable {
Expand All @@ -79,7 +80,7 @@ class DebugViewController(
private val debugManager: DebugManager,
private val factory: Factory
) : ConstraintLayout(context), AppCompatActivityEncapsulatable {
interface Factory: RequestFactory, ViewControllerFactory {}
interface Factory: RequestFactory, ViewControllerFactory, TriggerSessionManagerFactory {}
data class AlertOption(
val title: String? = "",
val action: (suspend () -> Unit)? = null,
Expand Down Expand Up @@ -418,7 +419,11 @@ class DebugViewController(
)
var paywall = paywallRequestManager.getPaywall(request)

val productVariables = storeKitManager.getProductVariables(paywall)
val productVariables = storeKitManager.getProductVariables(
paywall,
request = request,
factory = factory
)
paywall.productVariables = productVariables

this.paywall = paywall
Expand Down Expand Up @@ -565,7 +570,8 @@ class DebugViewController(
}

val (productsById, _) = storeKitManager.getProducts(
responseProductIds = paywall.productIds
paywall = paywall,
factory = factory
)
val products = paywall.productIds.mapNotNull { productsById[it] }
SWConsoleActivity.products = products
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -187,31 +187,25 @@ class PaywallRequestManager(
private suspend fun getProducts(paywall: Paywall, request: PaywallRequest): Paywall = withContext(singleThreadContext) {
var paywall = paywall

try {
val result = storeKitManager.getProducts(
paywall.productIds,
paywall.products,
request.overrides.products
)

paywall.products = result.products
val result = storeKitManager.getProducts(
substituteProducts = request.overrides.products,
paywall = paywall,
request = request,
factory = factory
)
paywall = result.paywall
paywall.products = result.products

val outcome = PaywallLogic.getVariablesAndFreeTrial(
result.products,
result.productsById,
request.overrides.isFreeTrial
)
paywall.productVariables = outcome.productVariables
val outcome = PaywallLogic.getVariablesAndFreeTrial(
result.products,
result.productsById,
request.overrides.isFreeTrial
)
paywall.productVariables = outcome.productVariables
// paywall.swProductVariablesTemplate = outcome.swProductVariablesTemplate
paywall.isFreeTrialAvailable = outcome.isFreeTrialAvailable
paywall.isFreeTrialAvailable = outcome.isFreeTrialAvailable

return@withContext paywall
} catch (error: Throwable) {
paywall.productsLoadingInfo.failAt = Date()
val paywallInfo = paywall.getInfo(request.eventData, factory)
trackProductLoadFail(error.message, paywallInfo, request.eventData)
throw error
}
return@withContext paywall
}

// Analytics
Expand All @@ -228,19 +222,6 @@ class PaywallRequestManager(
return@withContext paywall
}

private suspend fun trackProductLoadFail(
errorMessage: String?,
paywallInfo: PaywallInfo,
event: EventData?
) = withContext(singleThreadContext) {
val productLoadEvent = InternalSuperwallEvent.PaywallProductsLoad(
state = InternalSuperwallEvent.PaywallProductsLoad.State.Fail(errorMessage),
paywallInfo = paywallInfo,
eventData = event
)
Superwall.instance.track(productLoadEvent)
}

private suspend fun trackProductsLoadFinish(paywall: Paywall, event: EventData?): Paywall = withContext(singleThreadContext) {
var paywall = paywall
paywall.productsLoadingInfo.endAt = Date()
Expand Down
51 changes: 40 additions & 11 deletions superwall/src/main/java/com/superwall/sdk/store/StoreKitManager.kt
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,21 @@ import LogLevel
import LogScope
import Logger
import android.content.Context
import com.superwall.sdk.Superwall
import com.superwall.sdk.analytics.internal.track
import com.superwall.sdk.analytics.internal.trackable.InternalSuperwallEvent
import com.superwall.sdk.dependencies.TriggerSessionManagerFactory
import com.superwall.sdk.models.paywall.Paywall
import com.superwall.sdk.models.paywall.PaywallProducts
import com.superwall.sdk.models.product.Product
import com.superwall.sdk.models.product.ProductType
import com.superwall.sdk.models.product.ProductVariable
import com.superwall.sdk.paywall.request.PaywallRequest
import com.superwall.sdk.store.abstractions.product.StoreProduct
import com.superwall.sdk.store.abstractions.product.receipt.ReceiptManager
import com.superwall.sdk.store.coordinator.ProductsFetcher
import com.superwall.sdk.store.products.GooglePlayProductsFetcher
import java.util.Date

/*
class StoreKitManager(private val context: Context) : StoreKitManagerInterface {
Expand Down Expand Up @@ -104,8 +110,16 @@ class StoreKitManager(
val products: List<Product>
)

suspend fun getProductVariables(paywall: Paywall): List<ProductVariable> {
val output = getProducts(paywall.productIds)
suspend fun getProductVariables(
paywall: Paywall,
request: PaywallRequest,
factory: TriggerSessionManagerFactory
): List<ProductVariable> {
val output = getProducts(
paywall = paywall,
request = request,
factory = factory
)

val variables = paywall.products.mapNotNull { product ->
output.productsById[product.id]?.let { storeProduct ->
Expand All @@ -120,19 +134,30 @@ class StoreKitManager(
}

suspend fun getProducts(
responseProductIds: List<String>,
responseProducts: List<Product> = emptyList(),
substituteProducts: PaywallProducts? = null
substituteProducts: PaywallProducts? = null,
paywall: Paywall,
request: PaywallRequest? = null,
factory: TriggerSessionManagerFactory
): GetProductsResponse {
val processingResult = removeAndStore(
substituteProducts = substituteProducts,
responseProductIds,
responseProducts = responseProducts
responseProductIds = paywall.productIds,
responseProducts = paywall.products
)

val products = products(
identifiers = processingResult.productIdsToLoad
)
var products: Set<StoreProduct> = setOf()
try {
products = products(identifiers = processingResult.productIdsToLoad)
} catch (error: Throwable) {
paywall.productsLoadingInfo.failAt = Date()
val paywallInfo = paywall.getInfo(request?.eventData, factory)
val productLoadEvent = InternalSuperwallEvent.PaywallProductsLoad(
state = InternalSuperwallEvent.PaywallProductsLoad.State.Fail(error.message),
paywallInfo = paywallInfo,
eventData = request?.eventData
)
Superwall.instance.track(productLoadEvent)
}

val productsById = processingResult.substituteProductsById.toMutableMap()

Expand All @@ -142,7 +167,11 @@ class StoreKitManager(
this.productsById[productIdentifier] = product
}

return GetProductsResponse(productsById, processingResult.products)
return GetProductsResponse(
productsById = productsById,
products = processingResult.products,
paywall = paywall
)
}

private fun removeAndStore(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,8 @@ import com.superwall.sdk.store.abstractions.product.StoreProduct

data class GetProductsResponse(
val productsById: Map<String, StoreProduct>,
val products: List<Product>
val products: List<Product>,
val paywall: Paywall
)

interface StoreKitManagerInterface {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -242,18 +242,20 @@ open class GooglePlayProductsFetcher(
.toMap()
.toMutableMap() as MutableMap<String, Result<RawStoreProduct>>

val missingProductsString = missingProducts.joinToString(separator = ", ")
missingProducts.forEach { missingProductId ->
productIdsBySubscriptionId[missingProductId]?.forEach { product ->
subscriptionIdToResult[product.fullId] = Result.Error(Exception("Failed to query product details"))
subscriptionIdToResult[product.fullId] = Result.Error(Exception("Failed to query product details for $missingProductsString"))
}
}

return subscriptionIdToResult.toMap()
} else {
val missingProductsString = subscriptionIds.joinToString(separator = ", ")
val results: MutableMap<String, Result<RawStoreProduct>> = mutableMapOf()
subscriptionIds.forEach { subscriptionId ->
productIdsBySubscriptionId[subscriptionId]?.forEach { product ->
results[product.fullId] = Result.Error(Exception("Failed to query product details. Billing response code: ${billingResult.responseCode}"))
results[product.fullId] = Result.Error(Exception("Failed to query product details for $missingProductsString. Billing response code: ${billingResult.responseCode}"))
}
}
return results
Expand All @@ -271,6 +273,7 @@ open class GooglePlayProductsFetcher(
return productResults.values.mapNotNull {
when (it) {
is Result.Success -> StoreProduct(it.value) // Assuming RawStoreProduct can be converted to StoreProduct
is Result.Error -> throw it.error
else -> null
}
}.toSet()
Expand Down

0 comments on commit 716bfd3

Please sign in to comment.