Skip to content

Commit da2f8d6

Browse files
committed
refactor & documentation: documentation for necessary places, and small refactoring
1 parent a0e0f44 commit da2f8d6

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

44 files changed

+393
-310
lines changed
Lines changed: 69 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,85 @@
11
package com.patika.getir_lite.data
22

33
import com.patika.getir_lite.model.BaseResponse
4-
import com.patika.getir_lite.model.BasketWithProducts
4+
import com.patika.getir_lite.data.local.model.BasketWithProducts
5+
import com.patika.getir_lite.data.local.model.StatusEntity
56
import com.patika.getir_lite.model.CountType
7+
import com.patika.getir_lite.model.ProductType
68
import com.patika.getir_lite.model.Order
79
import com.patika.getir_lite.model.ProductWithCount
810
import kotlinx.coroutines.flow.Flow
9-
import kotlinx.coroutines.flow.StateFlow
1011

12+
/**
13+
* Defines the interface for handling product and order data operations. Implementations of this interface
14+
* should manage data fetching, caching, and business logic associated with product management in the application.
15+
*/
1116
interface ProductRepository {
12-
val dataSyncResult: StateFlow<List<DataSyncResult>>
17+
18+
/**
19+
* Retrieves a flow of all products filtered by [ProductType.PRODUCT].
20+
*
21+
* @return A [Flow] emitting a list of [ProductWithCount] reflecting the current state of available products.
22+
*/
1323
fun getProductsAsFlow(): Flow<List<ProductWithCount>>
14-
suspend fun syncWithRemote(): BaseResponse<Unit>
24+
25+
/**
26+
* Initiates a fetch for product data from remote sources, typically involving network requests to an API.
27+
* This method should handle synchronization of local data with remote data.
28+
*
29+
* @return A [BaseResponse] indicating the success or failure of the fetch operation.
30+
*/
31+
suspend fun fetchDataFromRemote(): BaseResponse<Unit>
32+
33+
/**
34+
* Retrieves a flow of suggested products, often used for displaying recommendations or promotions.
35+
*
36+
* @return A [Flow] emitting a list of [ProductWithCount] reflecting the current state of suggested products.
37+
*/
1538
fun getSuggestedProductsAsFlow(): Flow<List<ProductWithCount>>
39+
40+
/**
41+
* Retrieves a flow of the current active basket or order, providing continuous updates as the basket's state changes.
42+
*
43+
* @return A [Flow] emitting an [Order] representing the active basket, or null if no basket is active.
44+
*/
1645
fun getBasketAsFlow(): Flow<Order?>
46+
47+
/**
48+
* Retrieves a flow of the current basket along with detailed product information contained within it.
49+
* This is particularly useful for checkout screens where detailed information about each item in the basket is required.
50+
*
51+
* @return A [Flow] emitting a [BasketWithProducts] representing the active basket with its associated products, or null if no basket is active.
52+
*/
1753
fun getBasketWithProductsAsFlow(): Flow<BasketWithProducts?>
54+
55+
/**
56+
* Retrieves a flow of a specific product by its ID, providing continuous updates as the product's details or state changes.
57+
*
58+
* @param productId The unique identifier of the product to fetch.
59+
* @return A [Flow] emitting [ProductWithCount] for the specified product, or null if the product does not exist.
60+
*/
1861
fun getProductAsFlow(productId: Long): Flow<ProductWithCount?>
19-
suspend fun updateItemCount(productId: Long, countType: CountType)
62+
63+
/**
64+
* Updates the item count for a specific product in an active basket, handling either increment or decrement operations.
65+
* This method is intended to facilitate immediate updates to basket contents based on user actions.
66+
*
67+
* @param productId The product ID whose count will be updated.
68+
* @param countType The type of count update to perform (add one or subtract one).
69+
* @return A [Result] encapsulating the success or failure of the update operation.
70+
*/
71+
suspend fun updateItemCount(productId: Long, countType: CountType): Result<Unit>
72+
73+
/**
74+
* Clears all items from the active basket, typically invoked when a user cancels the basket or completes an order.
75+
* This operation may also trigger updates to associated data such as inventory levels or user profiles.
76+
*
77+
* @return A [Boolean] indicating whether the basket was successfully cleared.
78+
*/
2079
suspend fun clearBasket(): Boolean
80+
81+
/**
82+
* Get the current status of the database
83+
*/
84+
suspend fun getStatus(): List<StatusEntity?>
2185
}

app/src/main/java/com/patika/getir_lite/data/local/ProductDatabase.kt

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,17 @@ import androidx.room.TypeConverters
66
import com.patika.getir_lite.data.local.model.ItemEntity
77
import com.patika.getir_lite.data.local.model.ProductEntity
88
import com.patika.getir_lite.data.local.model.OrderEntity
9+
import com.patika.getir_lite.data.local.model.StatusEntity
910
import com.patika.getir_lite.util.BigDecimalConverter
1011

12+
/**
13+
* This class defines the Room database setup including the entities involved and the database version.
14+
* It also specifies a type converter to handle specific data types that Room cannot handle natively.
15+
*
16+
* @property productDto Provides access to [ProductDao], which contains methods for accessing and manipulating product-related data stored in the database.
17+
*/
1118
@Database(
12-
entities = [OrderEntity::class, ProductEntity::class, ItemEntity::class],
19+
entities = [OrderEntity::class, ProductEntity::class, ItemEntity::class, StatusEntity::class],
1320
version = 1,
1421
exportSchema = false
1522
)

app/src/main/java/com/patika/getir_lite/model/BasketWithProducts.kt renamed to app/src/main/java/com/patika/getir_lite/data/local/model/BasketWithProducts.kt

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,7 @@
1-
package com.patika.getir_lite.model
1+
package com.patika.getir_lite.data.local.model
22

33
import androidx.room.Embedded
44
import androidx.room.Relation
5-
import com.patika.getir_lite.data.local.model.ItemEntity
6-
import com.patika.getir_lite.data.local.model.ItemWithProduct
7-
import com.patika.getir_lite.data.local.model.OrderEntity
85

96
data class BasketWithProducts(
107
@Embedded val order: OrderEntity,

app/src/main/java/com/patika/getir_lite/data/local/model/ItemWithProduct.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,5 +20,5 @@ fun ItemWithProduct.toProductWithCount() = ProductWithCount(
2020
attribute = product.attribute,
2121
imageURL = product.imageURL,
2222
count = item.count,
23-
productType = product.productType
23+
type = product.productType
2424
)

app/src/main/java/com/patika/getir_lite/data/remote/RemoteDataSource.kt

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,14 @@ import kotlinx.coroutines.withContext
1515
import retrofit2.Response
1616
import javax.inject.Inject
1717

18+
/**
19+
* A data source for fetching product-related data from a remote server.
20+
* This class implements the [RemoteRepository] interface, providing methods to fetch product and suggested product data
21+
* and handling the conversion of network responses into application-specific response types.
22+
*
23+
* @property productApi The API service interface for making network requests.
24+
* @property ioDispatcher A [CoroutineDispatcher] for running operations on a background thread, typically I/O operations like network requests.
25+
*/
1826
class RemoteDataSource @Inject constructor(
1927
private val productApi: ProductApi,
2028
@Dispatcher(IO) private val ioDispatcher: CoroutineDispatcher

app/src/main/java/com/patika/getir_lite/data/remote/RemoteRepository.kt

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,23 @@ import com.patika.getir_lite.data.remote.model.ProductDto
44
import com.patika.getir_lite.data.remote.model.SuggestedProductDto
55
import com.patika.getir_lite.model.BaseResponse
66

7+
/**
8+
* Interface defining the methods for fetching data from a remote server. Implementations should handle
9+
* network interactions to retrieve product and suggested product data, returning it in a standardized response format.
10+
*/
711
interface RemoteRepository {
12+
13+
/**
14+
* Fetches a list of products from the remote server.
15+
*
16+
* @return A [BaseResponse] containing a list of [ProductDto] if the fetch is successful, encapsulating the data or error state.
17+
*/
818
suspend fun getProductDtos(): BaseResponse<List<ProductDto>>
19+
20+
/**
21+
* Fetches a list of suggested products from the remote server.
22+
*
23+
* @return A [BaseResponse] containing a list of [SuggestedProductDto] if the fetch is successful, encapsulating the data or error state.
24+
*/
925
suspend fun getSuggestedProductDtos(): BaseResponse<List<SuggestedProductDto>>
1026
}

app/src/main/java/com/patika/getir_lite/fake/FakeProductDataSource.kt

Lines changed: 36 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
package com.patika.getir_lite.fake
22

3-
import com.patika.getir_lite.data.DataSyncResult
43
import com.patika.getir_lite.data.ProductRepository
54
import com.patika.getir_lite.data.local.model.ItemEntity
65
import com.patika.getir_lite.data.local.model.ItemWithProduct
@@ -10,63 +9,53 @@ import com.patika.getir_lite.data.local.model.ProductEntity
109
import com.patika.getir_lite.data.local.model.toDomainModel
1110
import com.patika.getir_lite.fake.data.fakeProductWithCounts
1211
import com.patika.getir_lite.model.BaseResponse
13-
import com.patika.getir_lite.model.BasketWithProducts
12+
import com.patika.getir_lite.data.local.model.BasketWithProducts
13+
import com.patika.getir_lite.data.local.model.StatusEntity
1414
import com.patika.getir_lite.model.CountType
1515
import com.patika.getir_lite.model.Order
1616
import com.patika.getir_lite.model.ProductType
1717
import com.patika.getir_lite.model.ProductWithCount
1818
import kotlinx.coroutines.flow.Flow
19-
import kotlinx.coroutines.flow.MutableStateFlow
20-
import kotlinx.coroutines.flow.StateFlow
2119
import kotlinx.coroutines.flow.flow
2220
import java.math.BigDecimal
2321

22+
/**
23+
* A mock implementation of [ProductRepository] for use in tests or development environments.
24+
* This class simulates the behavior of a real product repository by storing and managing in-memory lists of products and orders.
25+
*/
2426
class FakeProductDataSource : ProductRepository {
2527
private val localProducts = fakeProductWithCounts.toMutableList()
2628
val orders = mutableListOf<OrderEntity>()
2729
private val items = mutableListOf<ItemEntity>()
2830

29-
private val _dataSyncResult = MutableStateFlow<List<DataSyncResult>>(emptyList())
30-
override val dataSyncResult: StateFlow<List<DataSyncResult>> = _dataSyncResult
31-
32-
override suspend fun syncWithRemote(): BaseResponse<Unit> {
31+
override suspend fun fetchDataFromRemote(): BaseResponse<Unit> {
3332
return BaseResponse.Success(Unit)
3433
}
3534

3635
override fun getProductsAsFlow(): Flow<List<ProductWithCount>> = flow {
37-
emit(localProducts.filter { it.productType == ProductType.PRODUCT })
36+
emit(localProducts.filter { it.type == ProductType.PRODUCT })
3837
}
3938

4039
override fun getSuggestedProductsAsFlow(): Flow<List<ProductWithCount>> = flow {
41-
emit(localProducts.filter { it.productType == ProductType.SUGGESTED_PRODUCT })
40+
emit(localProducts.filter { it.type == ProductType.SUGGESTED_PRODUCT })
4241
}
4342

4443
override fun getBasketAsFlow(): Flow<Order?> = flow {
4544
emit(orders.firstOrNull { it.orderStatus == OrderStatus.ON_BASKET }?.toDomainModel())
4645
}
4746

48-
fun ProductWithCount.toProductEntity(): ProductEntity {
49-
return ProductEntity(
50-
id = productId,
51-
productId = "",
52-
name = name,
53-
price = price,
54-
attribute = attribute ?: "",
55-
imageURL = imageURL,
56-
productType = productType,
57-
)
58-
}
59-
6047
override fun getBasketWithProductsAsFlow(): Flow<BasketWithProducts?> = flow {
6148
val order = orders.firstOrNull { it.orderStatus == OrderStatus.ON_BASKET }
6249
?: return@flow emit(null)
50+
6351
val items = items.filter { it.orderId == order.id }
6452
val products = localProducts.filter { product ->
6553
items.any { it.productId == product.productId }
6654
}
55+
6756
val itemWithProducts = items.map { item ->
6857
val product = products.find { it.productId == item.productId }
69-
?: throw Exception("Product not found")
58+
?: throw Exception("Product not found: ${item.productId}")
7059
ItemWithProduct(item, product.toProductEntity())
7160
}
7261
emit(BasketWithProducts(order, itemWithProducts))
@@ -96,22 +85,24 @@ class FakeProductDataSource : ProductRepository {
9685
items.add(item)
9786
}
9887

99-
val order = orders.find { it.id == orderId } ?: throw Exception("Order not found")
88+
val order = orders.find { it.id == orderId } ?: throw Exception("Order not found: $orderId")
10089
val updatedOrder =
10190
order.copy(totalPrice = (order.totalPrice.toDouble() + price.toDouble()).toBigDecimal())
10291
val orderIndex = orders.indexOf(order)
10392
orders[orderIndex] = updatedOrder
10493

10594
val product =
106-
localProducts.find { it.productId == productId } ?: throw Exception("Product not found")
95+
localProducts.find { it.productId == productId }
96+
?: throw Exception("Product not found $productId")
10797
val updatedProduct = product.copy(count = product.count + 1)
10898
val productIndex = localProducts.indexOf(product)
10999
localProducts[productIndex] = updatedProduct
110100
}
111101

112102
private fun decrementItemCount(productId: Long, orderId: Long, price: BigDecimal) {
113103
val itemEntity =
114-
getItemByProductAndOrder(productId, orderId) ?: throw Exception("Item not found")
104+
getItemByProductAndOrder(productId, orderId)
105+
?: throw Exception("Item not found: productId=$productId, orderId=$orderId")
115106
val c = itemEntity.count - 1
116107
val updatedItem = itemEntity.copy(count = c)
117108
val index = items.indexOf(itemEntity)
@@ -121,7 +112,7 @@ class FakeProductDataSource : ProductRepository {
121112
items.removeAt(index)
122113
}
123114

124-
val order = orders.find { it.id == orderId } ?: throw Exception("Order not found")
115+
val order = orders.find { it.id == orderId } ?: throw Exception("Order not found: $orderId")
125116
val updatedOrder =
126117
order.copy(totalPrice = (order.totalPrice.toDouble() - price.toDouble()).toBigDecimal())
127118
val orderIndex = orders.indexOf(order)
@@ -134,10 +125,10 @@ class FakeProductDataSource : ProductRepository {
134125
localProducts[productIndex] = updatedProduct
135126
}
136127

137-
override suspend fun updateItemCount(productId: Long, countType: CountType) {
128+
override suspend fun updateItemCount(productId: Long, countType: CountType) = runCatching {
138129
val getActiveOrder = orders.firstOrNull { it.orderStatus == OrderStatus.ON_BASKET }
139130
val productPrice = localProducts.find { it.productId == productId }?.price
140-
?: throw Exception("Product not found")
131+
?: throw Exception("Product not found: $productId")
141132
val orderId = getActiveOrder?.id ?: run {
142133
val id = (0..100000).random().toLong()
143134
val orderEntity = OrderEntity(id = id, OrderStatus.ON_BASKET)
@@ -171,4 +162,20 @@ class FakeProductDataSource : ProductRepository {
171162

172163
return true
173164
}
165+
166+
override suspend fun getStatus(): List<StatusEntity?> {
167+
return emptyList()
168+
}
169+
170+
private fun ProductWithCount.toProductEntity(): ProductEntity {
171+
return ProductEntity(
172+
id = productId,
173+
productId = "",
174+
name = name,
175+
price = price,
176+
attribute = attribute ?: "",
177+
imageURL = imageURL,
178+
productType = type,
179+
)
180+
}
174181
}

app/src/main/java/com/patika/getir_lite/fake/data/FakeBasketWithProducts.kt

Lines changed: 0 additions & 25 deletions
This file was deleted.

app/src/main/java/com/patika/getir_lite/fake/data/FakeItem.kt

Lines changed: 0 additions & 12 deletions
This file was deleted.

app/src/main/java/com/patika/getir_lite/fake/data/FakeOrder.kt

Lines changed: 0 additions & 22 deletions
This file was deleted.

0 commit comments

Comments
 (0)