Skip to content

Commit cfe79a9

Browse files
authored
Merge pull request mouredev#2448 from blackriper/main
Reto#12-kotlin
2 parents e66e60e + 221c92e commit cfe79a9

File tree

1 file changed

+325
-0
lines changed

1 file changed

+325
-0
lines changed
Lines changed: 325 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,325 @@
1+
import kotlinx.serialization.ExperimentalSerializationApi
2+
import kotlinx.serialization.KSerializer
3+
import kotlinx.serialization.Serializable
4+
import kotlinx.serialization.descriptors.PrimitiveKind
5+
import kotlinx.serialization.descriptors.PrimitiveSerialDescriptor
6+
import kotlinx.serialization.encodeToString
7+
import kotlinx.serialization.encoding.Decoder
8+
import kotlinx.serialization.encoding.Encoder
9+
import kotlinx.serialization.json.Json
10+
import nl.adaptivity.xmlutil.serialization.XML
11+
import java.io.File
12+
import java.io.FileWriter
13+
import java.io.PrintWriter
14+
import java.util.*
15+
16+
/*
17+
Al proceso de convertir la informacion en un cierto formato se le conoce como serializacion
18+
esto nos permite convertir alguna estructura de kotlin en un formato de salida (json, xml, etc).
19+
20+
para sealizar kotlin utiliza una libreria auxilar llamada kotlinx.serialization.
21+
este tambien nos provee de un modulo para poder serializar xml.
22+
23+
Serializar: proceso de convertir un objeto de kotlin a un formato de salida json o xml
24+
25+
Desializar: proceso de convertir un formato json o xml a un objeto de kotlin
26+
27+
para mas informacion visita:
28+
https://kotlinlang.org/docs/serialization.html
29+
https://github.com/rharter/kotlinx-serialization-xml
30+
31+
*/
32+
33+
34+
35+
@OptIn(ExperimentalSerializationApi::class)
36+
fun jsonFile(){
37+
val src="src/main/resources/blackriper.json"
38+
// crear clase para serializar y deserealizar
39+
@Serializable
40+
data class User(val name: String, val age: Int, val birdday: String,val programingLenguages: List<String>)
41+
42+
// escribir file json
43+
PrintWriter(FileWriter(src)).use {
44+
val prettyJson = Json {
45+
prettyPrint = true
46+
prettyPrintIndent = " "
47+
}
48+
val user=User("Rodolfo", 29, "20/05/1994", listOf("kotlin","go","python"))
49+
it.write(prettyJson.encodeToString(user))
50+
}
51+
52+
// leer fichero json
53+
File(src).readText().let {
54+
val user = Json.decodeFromString<User>(it)
55+
println(user)
56+
}
57+
58+
// borrar fichero
59+
File(src).delete()
60+
61+
}
62+
63+
fun xmlFile() {
64+
val src="src/main/resources/blackriper.xml"
65+
// crear data class
66+
@Serializable
67+
data class User(val name: String, val age: Int, val birdday: String,val programingLenguages: List<String>)
68+
// crear fichero xml
69+
PrintWriter(FileWriter(src)).use {
70+
val user=User("Rodolfo", 29, "20/05/1994", listOf("kotlin","go","swift"))
71+
it.write(XML.encodeToString(user))
72+
}
73+
74+
// leer fichero xml
75+
File(src).readText().let {
76+
val user = XML.decodeFromString<User>(it)
77+
println(user)
78+
}
79+
80+
// borrar fichero
81+
File(src).delete()
82+
83+
}
84+
85+
// reto extra con json y xml
86+
87+
// crear custom serializer para UUID
88+
object UUIDSerializer : KSerializer<UUID> {
89+
override val descriptor = PrimitiveSerialDescriptor("UUID", PrimitiveKind.STRING)
90+
91+
override fun deserialize(decoder: Decoder): UUID {
92+
return UUID.fromString(decoder.decodeString())
93+
}
94+
95+
override fun serialize(encoder: Encoder, value: UUID) {
96+
encoder.encodeString(value.toString())
97+
}
98+
}
99+
100+
101+
@Serializable
102+
data class Product(
103+
@Serializable(with = UUIDSerializer::class)
104+
val sku: UUID,
105+
var name: String,
106+
var cant: Int,
107+
var price: Double)
108+
109+
@Serializable
110+
data class StoreProducts(val products: List<Product>)
111+
112+
enum class FileType {
113+
JSON,
114+
XML
115+
}
116+
117+
interface Store{
118+
fun addProduct(product: Product)
119+
fun removeProduct(name: String)
120+
fun updateProduct(sku: UUID, product:Product)
121+
fun showAllProducts()
122+
fun searchProductByName(name: String):Product
123+
fun calculateTotalSold()
124+
fun deleteFile()
125+
}
126+
127+
class SoldSore(private val fileName:String,private val type:FileType):Store{
128+
private val products= mutableListOf<Product>()
129+
private val fileProduct=File("src/main/resources/$fileName")
130+
private val src="src/main/resources/$fileName"
131+
132+
init {
133+
if (fileProduct.exists()){
134+
when(type){
135+
FileType.JSON -> fileProduct.readText().let {
136+
val productsFile = Json.decodeFromString<StoreProducts>(it)
137+
productsFile.products.forEach { product ->
138+
products.add(product)
139+
}
140+
}
141+
FileType.XML -> fileProduct.readText().let {
142+
val productsFile = XML.decodeFromString<StoreProducts>(it)
143+
productsFile.products.forEach { product ->
144+
products.add(product)
145+
}
146+
}
147+
}
148+
149+
}
150+
}
151+
152+
override fun addProduct(product: Product) {
153+
products.add(product)
154+
saveFile()
155+
}
156+
157+
override fun removeProduct(name: String) {
158+
val product=products.first { it.name==name }
159+
val result=products.removeIf{it.sku==product.sku}
160+
if (result) {
161+
println("Product deleted successfully")
162+
saveFile()
163+
} else {
164+
println("Failed to delete the product")
165+
}
166+
}
167+
168+
override fun updateProduct(sku: UUID, product: Product) {
169+
products.first { it.sku == sku }.apply {
170+
this.name = product.name
171+
this.cant = product.cant
172+
this.price = product.price
173+
}
174+
saveFile()
175+
}
176+
177+
override fun showAllProducts() {
178+
val header="""
179+
-----------------------
180+
sku name cant price
181+
-----------------------
182+
""".trimIndent()
183+
println(header)
184+
when(type){
185+
FileType.JSON -> {
186+
File(src).readText().let {
187+
val products = Json.decodeFromString<StoreProducts>(it)
188+
for (product in products.products) {
189+
println("${product.sku} ${product.name} ${product.cant} ${product.price}")
190+
}
191+
}
192+
}
193+
FileType.XML -> {
194+
File(src).readText().let {
195+
val products = XML.decodeFromString<StoreProducts>(it)
196+
for (product in products.products) {
197+
println("${product.sku} ${product.name} ${product.cant} ${product.price}")
198+
}
199+
}
200+
}
201+
}
202+
203+
204+
}
205+
206+
override fun searchProductByName(name: String): Product =
207+
products.first { it.name==name }
208+
209+
override fun calculateTotalSold() {
210+
val header="""
211+
------------------------------------------------------------
212+
sku name cant price Subtotal
213+
-------------------------------------------------------------
214+
""".trimIndent()
215+
println(header)
216+
products.forEach {
217+
println("${it.sku} ${it.name} ${it.cant} ${it.price} ${"%.2f".format(it.cant*it.price)}")
218+
}
219+
val total=products.sumOf { it.cant*it.price }
220+
println("Total sold: $total")
221+
}
222+
223+
override fun deleteFile() {
224+
val result= File(src).delete()
225+
if (result) {
226+
println("File deleted successfully")
227+
}else {
228+
println("Failed to delete the file")
229+
}
230+
}
231+
232+
@OptIn(ExperimentalSerializationApi::class)
233+
private fun saveFile(){
234+
when(type){
235+
FileType.JSON -> {
236+
PrintWriter(FileWriter(fileProduct)).use {
237+
val prettyJson = Json {
238+
prettyPrint = true
239+
prettyPrintIndent = " "
240+
}
241+
val store=StoreProducts(products)
242+
it.write(prettyJson.encodeToString(store))
243+
}
244+
}
245+
FileType.XML -> {
246+
PrintWriter(FileWriter(fileProduct)).use {
247+
val store=StoreProducts(products)
248+
it.write(XML.encodeToString(store))
249+
}
250+
}
251+
}
252+
}
253+
254+
}
255+
256+
fun oxxoStore() {
257+
// modificar si se quiere usar json o xml
258+
val oxxo = SoldSore("products.xml", FileType.XML)
259+
260+
do {
261+
println("1. Add product")
262+
println("2. Remove product")
263+
println("3. Update product")
264+
println("4. Show all products")
265+
println("5. Search product by name")
266+
println("6. Calculate total sold")
267+
println("7. Exit")
268+
println("Choose an option:")
269+
val option = readLine()!!.toInt()
270+
when (option) {
271+
1 -> {
272+
println("Enter name:")
273+
val name = readLine()!!.lowercase()
274+
println("Enter cant:")
275+
val cant = readLine()!!.toInt()
276+
println("Enter price:")
277+
val price = readLine()!!.toDouble()
278+
val sku = UUID.randomUUID()
279+
val product = Product(sku, name, cant, price)
280+
oxxo.addProduct(product)
281+
}
282+
283+
2 -> {
284+
println("Enter name:")
285+
val name = readLine()!!.lowercase()
286+
oxxo.removeProduct(name)
287+
}
288+
289+
3 -> {
290+
println("Enter name product:")
291+
val oldname = readLine()!!.lowercase()
292+
val prod = oxxo.searchProductByName(oldname)
293+
println("update name (${prod.name}):")
294+
val name = if (readLine().isNullOrEmpty()) prod.name else readLine()!!.lowercase()
295+
println("update cat (${prod.cant}):")
296+
val cant = if (readLine().isNullOrEmpty()) prod.cant else readLine()!!.toInt()
297+
println("update price (${prod.price}):")
298+
val price = if (readLine().isNullOrEmpty()) prod.price else readLine()!!.toDouble()
299+
val product = Product(prod.sku, name, cant, price)
300+
oxxo.updateProduct(prod.sku, product)
301+
}
302+
303+
4 -> oxxo.showAllProducts()
304+
305+
5 -> {
306+
println("Enter name:")
307+
val name = readLine()!!.lowercase()
308+
val product = oxxo.searchProductByName(name)
309+
println("sku: ${product.sku} name: ${product.name} cant: ${product.cant} price: ${product.price}")
310+
}
311+
312+
6 -> oxxo.calculateTotalSold()
313+
314+
}
315+
} while (option != 7)
316+
317+
oxxo.deleteFile()
318+
}
319+
320+
321+
fun main() {
322+
//jsonFile()
323+
//xmlFile()
324+
oxxoStore()
325+
}

0 commit comments

Comments
 (0)