diff --git a/personalization-sdk/src/main/kotlin/com/personalization/SDK.kt b/personalization-sdk/src/main/kotlin/com/personalization/SDK.kt index 065fc9dc..d2507d12 100644 --- a/personalization-sdk/src/main/kotlin/com/personalization/SDK.kt +++ b/personalization-sdk/src/main/kotlin/com/personalization/SDK.kt @@ -10,6 +10,7 @@ import com.personalization.Params.InternalParameter import com.personalization.Params.TrackEvent import com.personalization.api.OnApiCallbackListener import com.personalization.api.managers.InAppNotificationManager +import com.personalization.api.managers.ProductsManager import com.personalization.api.managers.RecommendationManager import com.personalization.api.managers.SearchManager import com.personalization.api.managers.TrackEventManager @@ -53,6 +54,9 @@ open class SDK { @Inject lateinit var recommendationManager: RecommendationManager + @Inject + lateinit var productsManager: ProductsManager + @Inject lateinit var trackEventManager: TrackEventManager diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/managers/ProductsManager.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/managers/ProductsManager.kt new file mode 100644 index 00000000..7c428415 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/managers/ProductsManager.kt @@ -0,0 +1,17 @@ +package com.personalization.api.managers + +import com.personalization.api.OnApiCallbackListener + +interface ProductsManager { + + fun getProductsList( + brands: String?, + merchants: String?, + categories: String?, + locations: String?, + limit: Int?, + page: Int?, + filters: Map?, + listener: OnApiCallbackListener? = null + ) +} diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/brand/Brand.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/brand/Brand.kt new file mode 100644 index 00000000..007b7de5 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/brand/Brand.kt @@ -0,0 +1,12 @@ +package com.personalization.api.responses.products.brand + +import com.google.gson.annotations.SerializedName + +data class Brand( + @SerializedName("name") + val name: String, + @SerializedName("picture") + val picture: String, + @SerializedName("count") + val count: Int +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/category/Category.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/category/Category.kt new file mode 100644 index 00000000..cb1b9571 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/category/Category.kt @@ -0,0 +1,20 @@ +package com.personalization.api.responses.products.category + +import com.google.gson.annotations.SerializedName + +data class Category( + @SerializedName("id") + val id: String, + @SerializedName("name") + val name: String, + @SerializedName("url") + val url: String, + @SerializedName("url_handle") + val urlHandle: String, + @SerializedName("count") + val count: Int, + @SerializedName("parent") + val parent: String?, + @SerializedName("alias") + val alias: String? +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/Filter.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/Filter.kt new file mode 100644 index 00000000..55a88a94 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/Filter.kt @@ -0,0 +1,8 @@ +package com.personalization.api.responses.products.filter + +import com.google.gson.annotations.SerializedName + +data class Filter( + @SerializedName("filter") + val filter: FilterDetails +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/FilterDetails.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/FilterDetails.kt new file mode 100644 index 00000000..85b65e0a --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/FilterDetails.kt @@ -0,0 +1,14 @@ +package com.personalization.api.responses.products.filter + +import com.google.gson.annotations.SerializedName + +data class FilterDetails( + @SerializedName("count") + val count: Int, + @SerializedName("priority") + val priority: Int, + @SerializedName("ranges") + val ranges: List?, + @SerializedName("values") + val values: List +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/FilterValue.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/FilterValue.kt new file mode 100644 index 00000000..1908095b --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/filter/FilterValue.kt @@ -0,0 +1,10 @@ +package com.personalization.api.responses.products.filter + +import com.google.gson.annotations.SerializedName + +data class FilterValue( + @SerializedName("value") + val value: String, + @SerializedName("count") + val count: Int +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/image/ImageUrlResized.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/image/ImageUrlResized.kt new file mode 100644 index 00000000..fc6c295f --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/image/ImageUrlResized.kt @@ -0,0 +1,5 @@ +package com.personalization.api.responses.products.image + +data class ImageUrlResized( + val sizeToPath: Map +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/price/PriceRange.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/price/PriceRange.kt new file mode 100644 index 00000000..317c9c83 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/price/PriceRange.kt @@ -0,0 +1,10 @@ +package com.personalization.api.responses.products.price + +import com.google.gson.annotations.SerializedName + +data class PriceRange( + @SerializedName("min") + val min: Double, + @SerializedName("max") + val max: Double +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/price/PriceRangeItem.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/price/PriceRangeItem.kt new file mode 100644 index 00000000..b9b41c76 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/price/PriceRangeItem.kt @@ -0,0 +1,10 @@ +package com.personalization.api.responses.products.price + +import com.google.gson.annotations.SerializedName + +data class PriceRangeItem( + @SerializedName("to") + val to: Double, + @SerializedName("count") + val count: Int +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/Product.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/Product.kt new file mode 100644 index 00000000..2927a978 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/Product.kt @@ -0,0 +1,55 @@ +package com.personalization.api.responses.products.product + +import com.google.gson.annotations.SerializedName +import com.personalization.api.responses.product.ImageUrlResized + +data class Product( + @SerializedName("brand") + val brand: String, + @SerializedName("currency") + val currency: String, + @SerializedName("id") + val id: String, + @SerializedName("is_new") + val isNew: Boolean? = null, + @SerializedName("name") + val name: String, + @SerializedName("old_price") + val oldPrice: String = "0", + @SerializedName("price") + val price: Double, + @SerializedName("price_formatted") + val priceFormatted: String, + @SerializedName("price_full_formatted") + val priceFullFormatted: String, + @SerializedName("picture") + val picture: String, + @SerializedName("url") + val url: String, + @SerializedName("description") + val description: String, + @SerializedName("category_ids") + val categoryIds: List, + @SerializedName("fashion_feature") + val fashionFeature: String?, + @SerializedName("fashion_gender") + val fashionGender: String?, + @SerializedName("sales_rate") + val salesRate: Int, + @SerializedName("relative_sales_rate") + val relativeSalesRate: Double, + @SerializedName("image_url") + val imageUrl: String, + @SerializedName("image_url_handle") + val imageUrlHandle: String, + @SerializedName("image_url_resized") + val imageUrlResized: ImageUrlResized, + @SerializedName("_id") + val internalId: String, + @SerializedName("group_id") + val groupId: String, + @SerializedName("barcode") + val barcode: String, + @SerializedName("categories") + val categories: List +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductCategory.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductCategory.kt new file mode 100644 index 00000000..3924f7a2 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductCategory.kt @@ -0,0 +1,8 @@ +package com.personalization.api.responses.products.product + +data class ProductCategory( + val id: String, + val name: String, + val parent: String?, + val params: List +) \ No newline at end of file diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductParam.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductParam.kt new file mode 100644 index 00000000..602282de --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductParam.kt @@ -0,0 +1,6 @@ +package com.personalization.api.responses.products.product + +data class ProductParam( + val key: String, + val values: List +) \ No newline at end of file diff --git a/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductsResponse.kt b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductsResponse.kt new file mode 100644 index 00000000..c5863358 --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/api/responses/products/product/ProductsResponse.kt @@ -0,0 +1,27 @@ +package com.personalization.api.responses.products.product + +import com.google.gson.annotations.SerializedName +import com.personalization.api.responses.products.brand.Brand +import com.personalization.api.responses.products.category.Category +import com.personalization.api.responses.products.filter.Filter +import com.personalization.api.responses.products.price.PriceRange +import com.personalization.api.responses.products.price.PriceRangeItem + +data class ProductsResponse( + @SerializedName("brands") + val brands: List, + @SerializedName("categories") + val categories: List, + @SerializedName("filters") + val filters: List, + @SerializedName("price_range") + val priceRange: PriceRange, + @SerializedName("products") + val products: List, + @SerializedName("products_total") + val productsTotal: Int, + @SerializedName("price_ranges") + val priceRanges: List, + @SerializedName("price_median") + val priceMedian: Double +) diff --git a/personalization-sdk/src/main/kotlin/com/personalization/di/SdkModule.kt b/personalization-sdk/src/main/kotlin/com/personalization/di/SdkModule.kt index e9cce6c5..1ae1df92 100644 --- a/personalization-sdk/src/main/kotlin/com/personalization/di/SdkModule.kt +++ b/personalization-sdk/src/main/kotlin/com/personalization/di/SdkModule.kt @@ -2,10 +2,12 @@ package com.personalization.di import com.personalization.RegisterManager import com.personalization.api.managers.InAppNotificationManager +import com.personalization.api.managers.ProductsManager import com.personalization.api.managers.RecommendationManager import com.personalization.api.managers.SearchManager import com.personalization.api.managers.TrackEventManager import com.personalization.features.inAppNotification.impl.InAppNotificationManagerImpl +import com.personalization.features.products.impl.ProductsManagerImpl import com.personalization.features.recommendation.impl.RecommendationManagerImpl import com.personalization.features.search.impl.SearchManagerImpl import com.personalization.features.trackEvent.impl.TrackEventManagerImpl @@ -51,6 +53,14 @@ class SdkModule { sendNetworkMethodUseCase = sendNetworkMethodUseCase ) + @Singleton + @Provides + fun provideProductsManager( + sendNetworkMethodUseCase: SendNetworkMethodUseCase + ): ProductsManager = ProductsManagerImpl( + sendNetworkMethodUseCase = sendNetworkMethodUseCase + ) + @Singleton @Provides fun provideTrackEventManager( diff --git a/personalization-sdk/src/main/kotlin/com/personalization/features/products/impl/ProductsManagerImpl.kt b/personalization-sdk/src/main/kotlin/com/personalization/features/products/impl/ProductsManagerImpl.kt new file mode 100644 index 00000000..8afd8dab --- /dev/null +++ b/personalization-sdk/src/main/kotlin/com/personalization/features/products/impl/ProductsManagerImpl.kt @@ -0,0 +1,72 @@ +package com.personalization.features.products.impl + +import com.personalization.Params +import com.personalization.api.OnApiCallbackListener +import com.personalization.api.managers.ProductsManager +import com.personalization.sdk.domain.usecases.network.SendNetworkMethodUseCase +import javax.inject.Inject +import org.json.JSONObject + +internal class ProductsManagerImpl @Inject constructor( + private val sendNetworkMethodUseCase: SendNetworkMethodUseCase, +) : ProductsManager { + + override fun getProductsList( + brands: String?, + merchants: String?, + categories: String?, + locations: String?, + limit: Int?, + page: Int?, + filters: Map?, + listener: OnApiCallbackListener? + ) { + sendNetworkMethodUseCase.getAsync( + method = GET_PRODUCT_LIST_REQUEST, + params = Params().buildParams( + brands = brands, + merchants = merchants, + categories = categories, + locations = locations, + limit = limit, + page = page, + filters = filters, + ).build(), + listener = listener + ) + } + + private fun Params.buildParams( + brands: String?, + merchants: String?, + categories: String?, + locations: String?, + limit: Int?, + page: Int?, + filters: Map?, + ): Params = this.apply { + limit?.let { put(LIMIT_KEY, it) } + page?.let { put(PAGE_KEY, it) } + locations?.let { put(LOCATION_KEY, it) } + brands?.let { put(BRANDS_KEY, it) } + merchants?.let { put(MERCHANTS_KEY, it) } + categories?.let { put(CATEGORIES_KEY, it) } + + filters?.takeIf { it.isNotEmpty() }?.let { + val filtersJson = JSONObject(it).toString() + put(FILTERS_KEY, filtersJson) + } + } + + companion object { + const val GET_PRODUCT_LIST_REQUEST = "products" + + private const val LIMIT_KEY = "limit" + private const val PAGE_KEY = "page" + private const val LOCATION_KEY = "locations" + private const val BRANDS_KEY = "brands" + private const val MERCHANTS_KEY = "merchants" + private const val CATEGORIES_KEY = "categories" + private const val FILTERS_KEY = "" + } +} diff --git a/personalization-sdk/src/main/kotlin/com/personalization/features/recommendation/impl/RecommendationManagerImpl.kt b/personalization-sdk/src/main/kotlin/com/personalization/features/recommendation/impl/RecommendationManagerImpl.kt index 03d15817..1a9c2540 100644 --- a/personalization-sdk/src/main/kotlin/com/personalization/features/recommendation/impl/RecommendationManagerImpl.kt +++ b/personalization-sdk/src/main/kotlin/com/personalization/features/recommendation/impl/RecommendationManagerImpl.kt @@ -4,11 +4,11 @@ import com.google.gson.Gson import com.personalization.Params import com.personalization.api.OnApiCallbackListener import com.personalization.api.managers.RecommendationManager -import com.personalization.api.responses.recommendation.GetRecommendationResponse import com.personalization.api.responses.recommendation.GetExtendedRecommendationResponse +import com.personalization.api.responses.recommendation.GetRecommendationResponse import com.personalization.sdk.domain.usecases.network.SendNetworkMethodUseCase -import org.json.JSONObject import javax.inject.Inject +import org.json.JSONObject internal class RecommendationManagerImpl @Inject constructor( private val sendNetworkMethodUseCase: SendNetworkMethodUseCase @@ -22,18 +22,23 @@ internal class RecommendationManagerImpl @Inject constructor( ) { params.put(EXTENDED_PARAMETER, false) - getRecommendation(recommenderCode, params, object : OnApiCallbackListener() { - override fun onSuccess(response: JSONObject?) { - response?.let { - val getRecommendationResponse = Gson().fromJson(it.toString(), GetRecommendationResponse::class.java) - onGetRecommendation(getRecommendationResponse) + getRecommendation( + recommenderCode = recommenderCode, + params = params, + listener = object : OnApiCallbackListener() { + override fun onSuccess(response: JSONObject?) { + response?.let { + val getRecommendationResponse = + Gson().fromJson(it.toString(), GetRecommendationResponse::class.java) + onGetRecommendation(getRecommendationResponse) + } } - } - override fun onError(code: Int, msg: String?) { - onError(code, msg) + override fun onError(code: Int, msg: String?) { + onError(code, msg) + } } - }) + ) } override fun getExtendedRecommendation( @@ -44,18 +49,25 @@ internal class RecommendationManagerImpl @Inject constructor( ) { params.put(EXTENDED_PARAMETER, true) - getRecommendation(recommenderCode, params, object : OnApiCallbackListener() { - override fun onSuccess(response: JSONObject?) { - response?.let { - val getExtendedRecommendationResponse = Gson().fromJson(it.toString(), GetExtendedRecommendationResponse::class.java) - onGetExtendedRecommendation.invoke(getExtendedRecommendationResponse) + getRecommendation( + recommenderCode = recommenderCode, + params = params, + listener = object : OnApiCallbackListener() { + override fun onSuccess(response: JSONObject?) { + response?.let { + val getExtendedRecommendationResponse = Gson().fromJson( + it.toString(), + GetExtendedRecommendationResponse::class.java + ) + onGetExtendedRecommendation.invoke(getExtendedRecommendationResponse) + } } - } - override fun onError(code: Int, msg: String?) { - onError(code, msg) + override fun onError(code: Int, msg: String?) { + onError(code, msg) + } } - }) + ) } override fun getRecommendation(recommenderCode: String, params: Params, listener: OnApiCallbackListener) { diff --git a/personalization-sdk/src/main/kotlin/com/personalization/sdk/data/di/RepositoriesModule.kt b/personalization-sdk/src/main/kotlin/com/personalization/sdk/data/di/RepositoriesModule.kt index d8720528..c4cce075 100644 --- a/personalization-sdk/src/main/kotlin/com/personalization/sdk/data/di/RepositoriesModule.kt +++ b/personalization-sdk/src/main/kotlin/com/personalization/sdk/data/di/RepositoriesModule.kt @@ -33,4 +33,5 @@ abstract class RepositoriesModule { @Binds abstract fun bindNotificationRepository(impl: NotificationRepositoryImpl): NotificationRepository + }