From 28010f7091edf33b42eac50328cb087a3372047c Mon Sep 17 00:00:00 2001
From: Xera <ddosmukhamedovali@gmail.com>
Date: Tue, 5 Nov 2024 00:30:40 +0100
Subject: [PATCH] Added connection to mongoDB and API endpoints, tried adding
 deleteTask() function, the program does not work now :c

---
 .idea/uiDesigner.xml                          | 124 ++++++++++
 .../kotlin/todo/model/ApiListResponse.kt      |  32 +++
 site/src/jsMain/kotlin/todo/AppEntry.kt       |  17 --
 .../todo/components/widgets/HeaderLayout.kt   |  68 ++++++
 .../todo/components/widgets/LoadingSpinner.kt |   7 -
 .../todo/components/widgets/TodoCard.kt       |  25 --
 .../todo/components/widgets/TodoForm.kt       |  37 ---
 .../todo/components/widgets/TodoStyles.kt     |  72 ------
 site/src/jsMain/kotlin/todo/data/ApiCalls.kt  |  44 ++++
 .../jsMain/kotlin/todo/navigation/Screen.kt   |   7 +
 site/src/jsMain/kotlin/todo/pages/Index.kt    | 225 +++++++++++-------
 site/src/jvmMain/kotlin/todo/api/Add.kt       |  21 --
 site/src/jvmMain/kotlin/todo/api/Id.kt        |  17 --
 site/src/jvmMain/kotlin/todo/api/List.kt      |  19 --
 site/src/jvmMain/kotlin/todo/api/Remove.kt    |  21 --
 site/src/jvmMain/kotlin/todo/api/Tasks.kt     |  51 ++++
 site/src/jvmMain/kotlin/todo/api/tasks        |   0
 site/src/jvmMain/kotlin/todo/api/tasks.kt     |  10 -
 site/src/jvmMain/kotlin/todo/data/MongoDb.kt  |   1 +
 ...MongoDbImplementation.kt => MongoDbImp.kt} |  16 +-
 20 files changed, 476 insertions(+), 338 deletions(-)
 create mode 100644 .idea/uiDesigner.xml
 create mode 100644 site/src/commonMain/kotlin/todo/model/ApiListResponse.kt
 create mode 100644 site/src/jsMain/kotlin/todo/components/widgets/HeaderLayout.kt
 delete mode 100644 site/src/jsMain/kotlin/todo/components/widgets/LoadingSpinner.kt
 delete mode 100644 site/src/jsMain/kotlin/todo/components/widgets/TodoCard.kt
 delete mode 100644 site/src/jsMain/kotlin/todo/components/widgets/TodoForm.kt
 delete mode 100644 site/src/jsMain/kotlin/todo/components/widgets/TodoStyles.kt
 create mode 100644 site/src/jsMain/kotlin/todo/data/ApiCalls.kt
 create mode 100644 site/src/jsMain/kotlin/todo/navigation/Screen.kt
 delete mode 100644 site/src/jvmMain/kotlin/todo/api/Add.kt
 delete mode 100644 site/src/jvmMain/kotlin/todo/api/Id.kt
 delete mode 100644 site/src/jvmMain/kotlin/todo/api/List.kt
 delete mode 100644 site/src/jvmMain/kotlin/todo/api/Remove.kt
 create mode 100644 site/src/jvmMain/kotlin/todo/api/Tasks.kt
 delete mode 100644 site/src/jvmMain/kotlin/todo/api/tasks
 delete mode 100644 site/src/jvmMain/kotlin/todo/api/tasks.kt
 rename site/src/jvmMain/kotlin/todo/data/{MongoDbImplementation.kt => MongoDbImp.kt} (66%)

diff --git a/.idea/uiDesigner.xml b/.idea/uiDesigner.xml
new file mode 100644
index 0000000..2b63946
--- /dev/null
+++ b/.idea/uiDesigner.xml
@@ -0,0 +1,124 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project version="4">
+  <component name="Palette2">
+    <group name="Swing">
+      <item class="com.intellij.uiDesigner.HSpacer" tooltip-text="Horizontal Spacer" icon="/com/intellij/uiDesigner/icons/hspacer.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="1" hsize-policy="6" anchor="0" fill="1" />
+      </item>
+      <item class="com.intellij.uiDesigner.VSpacer" tooltip-text="Vertical Spacer" icon="/com/intellij/uiDesigner/icons/vspacer.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="6" hsize-policy="1" anchor="0" fill="2" />
+      </item>
+      <item class="javax.swing.JPanel" icon="/com/intellij/uiDesigner/icons/panel.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="3" hsize-policy="3" anchor="0" fill="3" />
+      </item>
+      <item class="javax.swing.JScrollPane" icon="/com/intellij/uiDesigner/icons/scrollPane.svg" removable="false" auto-create-binding="false" can-attach-label="true">
+        <default-constraints vsize-policy="7" hsize-policy="7" anchor="0" fill="3" />
+      </item>
+      <item class="javax.swing.JButton" icon="/com/intellij/uiDesigner/icons/button.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="3" anchor="0" fill="1" />
+        <initial-values>
+          <property name="text" value="Button" />
+        </initial-values>
+      </item>
+      <item class="javax.swing.JRadioButton" icon="/com/intellij/uiDesigner/icons/radioButton.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="3" anchor="8" fill="0" />
+        <initial-values>
+          <property name="text" value="RadioButton" />
+        </initial-values>
+      </item>
+      <item class="javax.swing.JCheckBox" icon="/com/intellij/uiDesigner/icons/checkBox.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="3" anchor="8" fill="0" />
+        <initial-values>
+          <property name="text" value="CheckBox" />
+        </initial-values>
+      </item>
+      <item class="javax.swing.JLabel" icon="/com/intellij/uiDesigner/icons/label.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="0" anchor="8" fill="0" />
+        <initial-values>
+          <property name="text" value="Label" />
+        </initial-values>
+      </item>
+      <item class="javax.swing.JTextField" icon="/com/intellij/uiDesigner/icons/textField.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="0" hsize-policy="6" anchor="8" fill="1">
+          <preferred-size width="150" height="-1" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JPasswordField" icon="/com/intellij/uiDesigner/icons/passwordField.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="0" hsize-policy="6" anchor="8" fill="1">
+          <preferred-size width="150" height="-1" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JFormattedTextField" icon="/com/intellij/uiDesigner/icons/formattedTextField.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="0" hsize-policy="6" anchor="8" fill="1">
+          <preferred-size width="150" height="-1" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JTextArea" icon="/com/intellij/uiDesigner/icons/textArea.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="6" hsize-policy="6" anchor="0" fill="3">
+          <preferred-size width="150" height="50" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JTextPane" icon="/com/intellij/uiDesigner/icons/textPane.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="6" hsize-policy="6" anchor="0" fill="3">
+          <preferred-size width="150" height="50" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JEditorPane" icon="/com/intellij/uiDesigner/icons/editorPane.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="6" hsize-policy="6" anchor="0" fill="3">
+          <preferred-size width="150" height="50" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JComboBox" icon="/com/intellij/uiDesigner/icons/comboBox.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="0" hsize-policy="2" anchor="8" fill="1" />
+      </item>
+      <item class="javax.swing.JTable" icon="/com/intellij/uiDesigner/icons/table.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="6" hsize-policy="6" anchor="0" fill="3">
+          <preferred-size width="150" height="50" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JList" icon="/com/intellij/uiDesigner/icons/list.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="6" hsize-policy="2" anchor="0" fill="3">
+          <preferred-size width="150" height="50" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JTree" icon="/com/intellij/uiDesigner/icons/tree.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="6" hsize-policy="6" anchor="0" fill="3">
+          <preferred-size width="150" height="50" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JTabbedPane" icon="/com/intellij/uiDesigner/icons/tabbedPane.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="3" hsize-policy="3" anchor="0" fill="3">
+          <preferred-size width="200" height="200" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JSplitPane" icon="/com/intellij/uiDesigner/icons/splitPane.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="3" hsize-policy="3" anchor="0" fill="3">
+          <preferred-size width="200" height="200" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JSpinner" icon="/com/intellij/uiDesigner/icons/spinner.svg" removable="false" auto-create-binding="true" can-attach-label="true">
+        <default-constraints vsize-policy="0" hsize-policy="6" anchor="8" fill="1" />
+      </item>
+      <item class="javax.swing.JSlider" icon="/com/intellij/uiDesigner/icons/slider.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="6" anchor="8" fill="1" />
+      </item>
+      <item class="javax.swing.JSeparator" icon="/com/intellij/uiDesigner/icons/separator.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="6" hsize-policy="6" anchor="0" fill="3" />
+      </item>
+      <item class="javax.swing.JProgressBar" icon="/com/intellij/uiDesigner/icons/progressbar.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="6" anchor="0" fill="1" />
+      </item>
+      <item class="javax.swing.JToolBar" icon="/com/intellij/uiDesigner/icons/toolbar.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="6" anchor="0" fill="1">
+          <preferred-size width="-1" height="20" />
+        </default-constraints>
+      </item>
+      <item class="javax.swing.JToolBar$Separator" icon="/com/intellij/uiDesigner/icons/toolbarSeparator.svg" removable="false" auto-create-binding="false" can-attach-label="false">
+        <default-constraints vsize-policy="0" hsize-policy="0" anchor="0" fill="1" />
+      </item>
+      <item class="javax.swing.JScrollBar" icon="/com/intellij/uiDesigner/icons/scrollbar.svg" removable="false" auto-create-binding="true" can-attach-label="false">
+        <default-constraints vsize-policy="6" hsize-policy="0" anchor="0" fill="2" />
+      </item>
+    </group>
+  </component>
+</project>
\ No newline at end of file
diff --git a/site/src/commonMain/kotlin/todo/model/ApiListResponse.kt b/site/src/commonMain/kotlin/todo/model/ApiListResponse.kt
new file mode 100644
index 0000000..82c1a95
--- /dev/null
+++ b/site/src/commonMain/kotlin/todo/model/ApiListResponse.kt
@@ -0,0 +1,32 @@
+package todo.model
+
+import kotlinx.serialization.DeserializationStrategy
+import kotlinx.serialization.SerialName
+import kotlinx.serialization.Serializable
+import kotlinx.serialization.json.JsonContentPolymorphicSerializer
+import kotlinx.serialization.json.JsonElement
+import kotlinx.serialization.json.jsonObject
+
+@Serializable(ListResponseSerializer::class)
+sealed class ApiListResponse {
+    @Serializable
+    @SerialName("loading")
+    object Loading: ApiListResponse()
+
+    @Serializable
+    @SerialName("success")
+    data class Success(val data: List<Task>) : ApiListResponse()
+
+    @Serializable
+    @SerialName("error")
+    data class Error(val message: String): ApiListResponse()
+}
+
+
+object ListResponseSerializer: JsonContentPolymorphicSerializer<ApiListResponse>(ApiListResponse::class){
+    override fun selectDeserializer(element: JsonElement) = when {
+        "data" in element.jsonObject -> ApiListResponse.Success.serializer()
+        "message" in element.jsonObject -> ApiListResponse.Error.serializer()
+        else -> ApiListResponse.Loading.serializer()
+    }
+}
\ No newline at end of file
diff --git a/site/src/jsMain/kotlin/todo/AppEntry.kt b/site/src/jsMain/kotlin/todo/AppEntry.kt
index c176351..a3d7032 100644
--- a/site/src/jsMain/kotlin/todo/AppEntry.kt
+++ b/site/src/jsMain/kotlin/todo/AppEntry.kt
@@ -36,23 +36,6 @@ fun initSiteStyles(ctx: InitSilkContext) = ctx.stylesheet.apply {
             .justifyContent(JustifyContent.Center)
             .alignItems(AlignItems.Center)
     }
-
-    /*ctx.theme.palettes.light.background = Colors.White
-    ctx.theme.palettes.light.color = Colors.Black
-    ctx.theme.palettes.light.link.default = Colors.Red
-    ctx.theme.palettes.light.link.visited = Colors.DarkRed
-    ctx.theme.palettes.light.button.default = Colors.WhiteSmoke
-    ctx.theme.palettes.light.button.hover = Colors.Gold
-
-    ctx.theme.palettes.dark.background = Colors.Black
-    ctx.theme.palettes.dark.color = Colors.White
-    ctx.theme.palettes.dark.link.default = Colors.Purple
-    ctx.theme.palettes.dark.link.visited = Colors.BlueViolet
-    ctx.theme.palettes.dark.button.default = Colors.Black
-    ctx.theme.palettes.dark.button.hover = Colors.Gold*/
-
-
-
 }
 
 
diff --git a/site/src/jsMain/kotlin/todo/components/widgets/HeaderLayout.kt b/site/src/jsMain/kotlin/todo/components/widgets/HeaderLayout.kt
new file mode 100644
index 0000000..c9c45e6
--- /dev/null
+++ b/site/src/jsMain/kotlin/todo/components/widgets/HeaderLayout.kt
@@ -0,0 +1,68 @@
+package todo.components.widgets
+
+import androidx.compose.runtime.Composable
+import androidx.compose.web.events.SyntheticMouseEvent
+import todo.navigation.Screen
+import com.varabyte.kobweb.compose.css.Cursor
+import com.varabyte.kobweb.compose.foundation.layout.Arrangement
+import com.varabyte.kobweb.compose.foundation.layout.Box
+import com.varabyte.kobweb.compose.foundation.layout.Column
+import com.varabyte.kobweb.compose.foundation.layout.Row
+import com.varabyte.kobweb.compose.ui.Alignment
+import com.varabyte.kobweb.compose.ui.Modifier
+import com.varabyte.kobweb.compose.ui.graphics.Colors
+import com.varabyte.kobweb.compose.ui.modifiers.*
+import com.varabyte.kobweb.core.PageContext
+import com.varabyte.kobweb.silk.components.text.SpanText
+import kotlinx.serialization.json.JsonNull.content
+import org.jetbrains.compose.web.css.px
+
+@Composable
+fun HeaderLayout(
+    context: PageContext,
+    content: @Composable () -> Unit
+) {
+    Box(
+        modifier = Modifier.fillMaxSize()
+    ) {
+        Row(
+            modifier = Modifier
+                .background(Colors.Navy)
+                .padding(20.px)
+                .fillMaxWidth()
+                .height(150.px),
+            verticalAlignment = Alignment.CenterVertically,
+            horizontalArrangement = Arrangement.Start
+        ) {
+            SpanText(
+                text = "Home Page",
+                modifier = Modifier
+                    .color(Colors.White)
+                    .cursor(Cursor.Pointer)
+                    .margin(40.px)
+                    .fontSize(24.px)
+                    .onClick { (context.router.navigateTo(Screen.HomePage.route)) }
+            )
+            SpanText(
+                text = "Task List",
+                modifier = Modifier
+                    .color(Colors.White)
+                    .cursor(Cursor.Pointer)
+                    .margin(40.px)
+                    .fontSize(24.px)
+                    .onClick { (context.router.navigateTo(Screen.HomePage.route)) }
+            )
+
+
+        }
+        Column(
+            modifier = Modifier
+                .fillMaxSize()
+                .margin(150.px),
+            verticalArrangement = Arrangement.Center,
+            horizontalAlignment = Alignment.CenterHorizontally
+        ) {
+            content()
+        }
+    }
+}
\ No newline at end of file
diff --git a/site/src/jsMain/kotlin/todo/components/widgets/LoadingSpinner.kt b/site/src/jsMain/kotlin/todo/components/widgets/LoadingSpinner.kt
deleted file mode 100644
index 6b6c199..0000000
--- a/site/src/jsMain/kotlin/todo/components/widgets/LoadingSpinner.kt
+++ /dev/null
@@ -1,7 +0,0 @@
-package todo.components.widgets
-
-import androidx.compose.runtime.Composable
-import org.jetbrains.compose.web.dom.Img
-
-@Composable
-fun LoadingSpinner() = Img("/loader.gif")
diff --git a/site/src/jsMain/kotlin/todo/components/widgets/TodoCard.kt b/site/src/jsMain/kotlin/todo/components/widgets/TodoCard.kt
deleted file mode 100644
index 36b1029..0000000
--- a/site/src/jsMain/kotlin/todo/components/widgets/TodoCard.kt
+++ /dev/null
@@ -1,25 +0,0 @@
-package todo.components.widgets
-
-import androidx.compose.runtime.Composable
-import com.varabyte.kobweb.silk.style.toAttrs
-import org.jetbrains.compose.web.dom.A
-
-@Composable
-fun TodoCard(onClick: (() -> Unit)? = null, content: @Composable () -> Unit) {
-    val styles = mutableListOf(TodoStyle, TodoContainerStyle, TodoTextStyle)
-    if (onClick != null) {
-        styles.add(TodoClickableStyle)
-    }
-
-    // Use "A" so the item supports a11y (you can tab on it and press enter to click it)
-    A(href = "#", attrs = styles.toAttrs {
-        tabIndex(0) // Make this item tabbable
-
-        onClick { evt ->
-            evt.preventDefault() // We are using "A" for its a11y side effects but don't want its actual behavior
-            onClick?.invoke()
-        }
-    }) {
-        content()
-    }
-}
diff --git a/site/src/jsMain/kotlin/todo/components/widgets/TodoForm.kt b/site/src/jsMain/kotlin/todo/components/widgets/TodoForm.kt
deleted file mode 100644
index 45dee42..0000000
--- a/site/src/jsMain/kotlin/todo/components/widgets/TodoForm.kt
+++ /dev/null
@@ -1,37 +0,0 @@
-package todo.components.widgets
-
-import androidx.compose.runtime.*
-import com.varabyte.kobweb.silk.style.toAttrs
-import org.jetbrains.compose.web.attributes.InputType
-import org.jetbrains.compose.web.attributes.name
-import org.jetbrains.compose.web.attributes.onSubmit
-import org.jetbrains.compose.web.attributes.placeholder
-import org.jetbrains.compose.web.dom.Form
-import org.jetbrains.compose.web.dom.Input
-
-@Composable
-fun TodoForm(placeholder: String, loading: Boolean, submitTodo: (String) -> Unit) {
-    if (loading) {
-        TodoCard {
-            LoadingSpinner()
-        }
-    } else {
-        var todo by remember { mutableStateOf("") }
-        Form(attrs = listOf(TodoStyle, TodoContainerStyle).toAttrs {
-            onSubmit { evt ->
-                evt.preventDefault()
-                submitTodo(todo)
-            }
-        }) {
-            Input(
-                InputType.Text,
-                attrs = listOf(TodoStyle, TodoTextStyle, TodoInputStyle)
-                    .toAttrs {
-                        placeholder(placeholder)
-                        name("todo")
-                        onChange { todo = it.value }
-                    }
-            )
-        }
-    }
-}
\ No newline at end of file
diff --git a/site/src/jsMain/kotlin/todo/components/widgets/TodoStyles.kt b/site/src/jsMain/kotlin/todo/components/widgets/TodoStyles.kt
deleted file mode 100644
index 5666822..0000000
--- a/site/src/jsMain/kotlin/todo/components/widgets/TodoStyles.kt
+++ /dev/null
@@ -1,72 +0,0 @@
-package todo.components.widgets
-
-import com.varabyte.kobweb.compose.css.*
-import com.varabyte.kobweb.compose.css.AlignItems
-import com.varabyte.kobweb.compose.css.Transition
-import com.varabyte.kobweb.compose.ui.Modifier
-import com.varabyte.kobweb.compose.ui.graphics.Color
-import com.varabyte.kobweb.compose.ui.graphics.Colors
-import com.varabyte.kobweb.compose.ui.modifiers.*
-import com.varabyte.kobweb.silk.style.CssStyle
-import com.varabyte.kobweb.silk.style.base
-import com.varabyte.kobweb.silk.style.selectors.hover
-import com.varabyte.kobweb.silk.style.selectors.placeholderShown
-import org.jetbrains.compose.web.css.*
-import todo.BORDER_COLOR
-
-private val INTERACT_COLOR = Color.rgb(0x00, 0x70, 0xf3)
-
-/** Common styles for all todo widgets */
-val TodoStyle = CssStyle.base {
-    Modifier
-        .width(85.percent)
-        .height(5.cssRem)
-        .border(1.px, LineStyle.Solid, BORDER_COLOR)
-        .borderRadius(10.px)
-        .transition(Transition.group(listOf("color", "border-color"), 0.15.s, TransitionTimingFunction.Ease))
-        .textDecorationLine(TextDecorationLine.None)
-}
-
-/** Styles for the bordered, outer container (the form component has an inner and outer layer) */
-val TodoContainerStyle = CssStyle.base {
-    Modifier
-        .margin(0.5.cssRem)
-        .border(1.px, LineStyle.Solid, BORDER_COLOR)
-        .display(DisplayStyle.Flex)
-        .textAlign(TextAlign.Left)
-        .alignItems(AlignItems.Center)
-}
-
-/** Styles for the text parts of todo widgets */
-val TodoTextStyle = CssStyle.base {
-    Modifier
-        .padding(1.5.cssRem)
-        .fontSize(1.25.cssRem)
-        // We use "A" tags for accessibility, but we want our colors to come from our container
-        .color(Color("inherit"))
-}
-
-/** Styles for the input element which handles user input */
-val TodoInputStyle = CssStyle {
-    base {
-        Modifier
-            .fillMaxWidth()
-            .backgroundColor(Colors.Transparent)
-            .border(0.px)
-    }
-
-    placeholderShown {
-        Modifier.fontStyle(FontStyle.Italic)
-    }
-}
-
-/** Styles for mouse interaction with todo widgets */
-val TodoClickableStyle = CssStyle {
-    hover {
-        Modifier
-            .color(INTERACT_COLOR)
-            .cursor(Cursor.Pointer)
-            .border { color(INTERACT_COLOR) }
-            .textDecorationLine(TextDecorationLine.LineThrough)
-    }
-}
diff --git a/site/src/jsMain/kotlin/todo/data/ApiCalls.kt b/site/src/jsMain/kotlin/todo/data/ApiCalls.kt
new file mode 100644
index 0000000..6d09609
--- /dev/null
+++ b/site/src/jsMain/kotlin/todo/data/ApiCalls.kt
@@ -0,0 +1,44 @@
+package todo.data
+
+import todo.model.Task
+import com.varabyte.kobweb.browser.api
+import kotlinx.browser.window
+import kotlinx.serialization.decodeFromString
+import kotlinx.serialization.encodeToString
+import kotlinx.serialization.json.Json
+import todo.model.ApiListResponse
+
+
+suspend fun addTask(task: Task): String {
+    return window.api.tryPost(
+        apiPath = "addtask",
+        body = Json.encodeToString(task).encodeToByteArray()
+    )?.decodeToString().toString()
+}
+
+suspend fun getAllTasks(
+    onSuccess: (ApiListResponse) -> Unit,
+    onError: (Exception) -> Unit
+) {
+    try {
+        val result = window.api.tryGet(
+            apiPath = "getalltasks"
+        )?.decodeToString()
+        if (result != null) {
+            onSuccess(Json.decodeFromString(result))
+        } else {
+            onError(Exception("Something went wrong"))
+        }
+    }catch (e: Exception){
+        console.log("It's here")
+        println(e)
+        onError(e)
+    }
+}
+
+/*suspend fun deleteTask(taskID: String): String {
+    return window.api.tryPost(
+        apiPath = "deletetask",
+        body = Json.encodeToString(taskID).encodeToByteArray()
+    )?.decodeToString().toString()
+}*/
diff --git a/site/src/jsMain/kotlin/todo/navigation/Screen.kt b/site/src/jsMain/kotlin/todo/navigation/Screen.kt
new file mode 100644
index 0000000..803583b
--- /dev/null
+++ b/site/src/jsMain/kotlin/todo/navigation/Screen.kt
@@ -0,0 +1,7 @@
+package todo.navigation
+
+
+sealed class Screen(val route: String) {
+    object HomePage: Screen(route = "/")
+    object TasksListPage: Screen(route = "/tasks")
+}
diff --git a/site/src/jsMain/kotlin/todo/pages/Index.kt b/site/src/jsMain/kotlin/todo/pages/Index.kt
index 3c16547..2a93ffe 100644
--- a/site/src/jsMain/kotlin/todo/pages/Index.kt
+++ b/site/src/jsMain/kotlin/todo/pages/Index.kt
@@ -17,6 +17,7 @@ import com.varabyte.kobweb.compose.ui.modifiers.alignItems
 import com.varabyte.kobweb.compose.ui.modifiers.verticalAlign
 import com.varabyte.kobweb.compose.ui.toAttrs
 import com.varabyte.kobweb.core.Page
+import com.varabyte.kobweb.core.rememberPageContext
 import com.varabyte.kobweb.silk.components.navigation.Link
 import com.varabyte.kobweb.silk.components.text.SpanText
 import com.varabyte.kobweb.silk.style.CssStyle
@@ -24,13 +25,13 @@ import com.varabyte.kobweb.silk.style.base
 import com.varabyte.kobweb.silk.style.selectors.hover
 import com.varabyte.kobweb.silk.style.toModifier
 import com.varabyte.kobweb.silk.theme.colors.ColorMode
-import com.varabyte.kobweb.silk.theme.colors.ColorSchemes
-import com.varabyte.kobweb.silk.theme.colors.palette.link
-import com.varabyte.kobweb.silk.theme.colors.palette.toPalette
+
+import kotlinx.browser.document
 import kotlinx.browser.window
 import kotlinx.coroutines.launch
 import kotlinx.serialization.decodeFromString
 import kotlinx.serialization.json.Json
+import org.jetbrains.compose.web.attributes.InputType
 import org.jetbrains.compose.web.css.*
 import org.jetbrains.compose.web.css.AlignContent
 import org.jetbrains.compose.web.css.AlignSelf
@@ -38,24 +39,14 @@ import org.jetbrains.compose.web.dom.Footer
 import org.jetbrains.compose.web.dom.*
 import org.jetbrains.compose.web.dom.Span
 import org.jetbrains.compose.web.dom.Text
-import todo.components.widgets.LoadingSpinner
-import todo.components.widgets.TodoCard
-import todo.components.widgets.TodoForm
+import org.w3c.dom.HTMLInputElement
+import todo.components.widgets.HeaderLayout
+import todo.data.addTask
+import todo.data.getAllTasks
+import todo.model.ApiListResponse
+import todo.model.Task
 import todo.model.TodoItem
 
-private suspend fun loadAndReplaceTodos(id: String, todos: SnapshotStateList<TodoItem>) {
-    return window.api.get("list?owner=$id").let { listBytes ->
-        Snapshot.withMutableSnapshot {
-            todos.clear()
-            todos.addAll(Json.decodeFromString(listBytes.decodeToString()))
-        }
-    }
-}
-
-/*val TitleStyle = CssStyle.base {
-    Modifier
-
-}*/
 
 // ====== STYLES ======
 
@@ -67,6 +58,7 @@ val HeaderStyle = CssStyle.base {
         .fontSize(80.px)
         .fontWeight(FontWeight.Bold)
         .fillMaxWidth()
+        .margin(bottom = 50.px)
 
 }
 
@@ -83,31 +75,46 @@ val ButtonStyle = CssStyle {
     }
 }
 
+val TaskStyle = CssStyle.base {
+    Modifier
+        .cursor(Cursor.Pointer)
+        .padding(20.px)
+        .background(Colors.WhiteSmoke)
+        .fontSize(36.px)
+        .fillMaxWidth()
+        .margin(5.px)
+        .maxWidth(800.px)
+}
+
 
 @Page
 
 @Composable
 fun HomePage() {
+    val context = rememberPageContext()
+    val scope = rememberCoroutineScope()
     var id by remember { mutableStateOf("") }
-    var ready by remember { mutableStateOf(false) }
     var loadingCount by remember { mutableStateOf(1) } // How many API requests are occurring at the same time
     val todos = remember { mutableStateListOf<TodoItem>() }
     val coroutineScope = rememberCoroutineScope()
     var colorMode by ColorMode.currentState
 
+    var response by remember { mutableStateOf<ApiListResponse>(ApiListResponse.Loading) }
 
 
     LaunchedEffect(Unit) {
-        check(!ready && loadingCount == 1)
-        id = window.localStorage.getItem("id") ?: run {
-            window.api.get("id").decodeToString().also {
-                window.localStorage.setItem("id", it)
-            }
-        }
 
-        loadAndReplaceTodos(id, todos)
-        loadingCount--
-        ready = true
+        getAllTasks(
+            onSuccess = {
+                if (it is ApiListResponse.Success) {
+                    response = it
+                }
+            },
+            onError = {
+                println("Error")
+                response = ApiListResponse.Error(it.message.toString())
+            }
+        )
     }
 
     Column(
@@ -115,99 +122,139 @@ fun HomePage() {
         horizontalAlignment = Alignment.CenterHorizontally,
         verticalArrangement = Arrangement.Top,
     ) {
-        if (!ready) {
-            Box(Modifier.fillMaxWidth().margin(top = 2.cssRem), contentAlignment = Alignment.TopCenter) {
-                LoadingSpinner()
-            }
-            return@Column
-        }
 
-        // ========  H E A D E R  ========
-        Header(HeaderStyle.toModifier().toAttrs()
-                ) {
+
+
+// ========  H E A D E R  ========
+        Header(
+
+            HeaderStyle.toModifier().toAttrs()
+        ) {
             Row {
                 Span(
                     HeaderStyle.toModifier()
                         //.justifySelf(JustifySelf.Left)
                         .toAttrs(),
                 ) {
-                    Text("To do:")
+                    Text("To do list")
                 }
                 Button(ButtonStyle.toModifier()
                     .onClick { colorMode = colorMode.opposite }
-                    //.justifySelf(JustifySelf.Right)
                     .toAttrs()
                 ) {
                     Text(value = "Change theme")
                 }
             }
         }
+        // ===== Input form =====
 
 
-        Column(Modifier.fillMaxSize()) {
-            Column(
-                Modifier.fillMaxWidth().maxWidth(800.px).align(Alignment.CenterHorizontally),
-                horizontalAlignment = Alignment.CenterHorizontally
-            ) {
-                TodoForm("Type a TODO and press ENTER", loadingCount > 0) { todo ->
-                    coroutineScope.launch {
-                        loadingCount++
-                        window.api.post("add?owner=$id&todo=$todo")
-                        loadAndReplaceTodos(id, todos)
-                        loadingCount--
+
+        Row(
+            verticalAlignment = Alignment.CenterVertically,
+            horizontalArrangement = Arrangement.Center
+        ) {
+            Input(
+                type = InputType.Text,
+                attrs = Modifier
+                    .id("todoInput")
+                    .width(320.px)
+                    .height(50.px)
+                    .color(Color.navi)
+                    .backgroundColor(Colors.LightGray)
+                    .padding(24.px)
+                    .fontSize(24.px)
+                    .margin(right = 50.px)
+                    .outline(width = 0.px)
+                    .border(width = 0.px)
+                    .fontStyle(FontStyle.Italic)
+                    .toAttrs {
+                        attr("placeholder", "Enter a todo")
                     }
-                }
+            )
 
-                todos.forEachIndexed { i, todo ->
-                    TodoCard(onClick = {
-                        coroutineScope.launch {
-                            loadingCount++
-                            todos.removeAt(i)
-                            window.api.post("remove?owner=$id&todo=${todo.id}")
-                            loadAndReplaceTodos(id, todos)
-                            loadingCount--
+            Button(
+                attrs = Modifier
+                    .onClick {
+                        val todo: String = (document.getElementById("todoInput") as HTMLInputElement).value
+                        scope.launch {
+                            addTask(
+                                Task(
+                                    task = todo
+                                )
+                            )
                         }
-                    }) {
-                        Text(todo.text)
                     }
-                }
-            }
+                    .height(54.px)
+                    .backgroundColor(Colors.White)
+                    .padding(leftRight = 50.px)
+                    .cursor(Cursor.Pointer)
+                    .toAttrs()
+            ) {
 
-            Column(
-                modifier = Modifier.fillMaxSize(),
-                verticalArrangement = Arrangement.Center,
-                horizontalAlignment = Alignment.CenterHorizontally
 
-            ) {
-                Row(verticalAlignment = Alignment.CenterVertically ) {
-                    P(attrs = Modifier
+                    SpanText(
+                        modifier = Modifier
+                            .fontSize(18.px)
+                            .fontWeight(FontWeight.Medium)
+                            .color(Colors.Black),
+                        text = "Create"
+                    )
 
-                        .fontSize(40.px)
-                        .toAttrs()
 
-                    ) {
-                        Text(value = "SUIIIIIII")
-                    }
 
                 }
             }
 
-            Spacer()
-
-            //  ====== FOOTER ======
-            Footer {
-                Row(Modifier
-                    .fontSize(20.px)
-                    .color(Colors.Grey)) {
-                    SpanText("Web application by ")
-                    Link(
-                        "https://github.com/Xera08",
-                        "Xera08",
-                    )
+        Column(
+            modifier = Modifier
+                .margin(40.px)
+                .fillMaxWidth(),
+            verticalArrangement = Arrangement.Top,
+            horizontalAlignment = Alignment.CenterHorizontally
+        ) {
+            when (response) {
+                is ApiListResponse.Success -> {
+                    (response as ApiListResponse.Success).data.forEach { task ->
+                        Row(
+                            verticalAlignment = Alignment.CenterVertically,
+                            horizontalArrangement = Arrangement.Center,
+                            modifier = TaskStyle.toModifier()
+                        ) {
+                            SpanText(
+                                text = task.task,
+                                modifier = TaskStyle.toModifier()
+                            )
+                            Button(ButtonStyle.toModifier()
+                                /*.onClick {
+                                    scope.launch {
+                                        deleteTask(task._id)
+                                    }
+                                }*/
+                                .toAttrs()
+                            ) {
+                                Text(value = "Delete")
+                            }
+                        }
+                    }
+                }
+
+                else -> {
+                    console.log("Nothing to display")
                 }
+
             }
         }
 
+        }
+
+
+        Spacer()
+
+
     }
-}
+
+
+
+
 
diff --git a/site/src/jvmMain/kotlin/todo/api/Add.kt b/site/src/jvmMain/kotlin/todo/api/Add.kt
deleted file mode 100644
index 4ce2da9..0000000
--- a/site/src/jvmMain/kotlin/todo/api/Add.kt
+++ /dev/null
@@ -1,21 +0,0 @@
-package todo.api
-
-import com.varabyte.kobweb.api.Api
-import com.varabyte.kobweb.api.ApiContext
-import com.varabyte.kobweb.api.data.getValue
-import com.varabyte.kobweb.api.http.HttpMethod
-import todo.model.TodoStore
-
-@Api
-fun addTodo(ctx: ApiContext) {
-    if (ctx.req.method != HttpMethod.POST) return
-
-    val ownerId = ctx.req.params["owner"]
-    val todo = ctx.req.params["todo"]
-    if (ownerId == null || todo == null) {
-        return
-    }
-
-    ctx.data.getValue<TodoStore>().add(ownerId, todo)
-    ctx.res.status = 200
-}
\ No newline at end of file
diff --git a/site/src/jvmMain/kotlin/todo/api/Id.kt b/site/src/jvmMain/kotlin/todo/api/Id.kt
deleted file mode 100644
index d5f19f9..0000000
--- a/site/src/jvmMain/kotlin/todo/api/Id.kt
+++ /dev/null
@@ -1,17 +0,0 @@
-package todo.api
-
-import com.varabyte.kobweb.api.Api
-import com.varabyte.kobweb.api.ApiContext
-import com.varabyte.kobweb.api.http.HttpMethod
-import com.varabyte.kobweb.api.http.setBodyText
-import java.util.*
-
-/**
- * Instead of generating an ID on the client (where there's no UUID library by default), we just ask the server to do
- * it. It's doing it anyways for its own stuff!
- */
-@Api
-fun generateId(ctx: ApiContext) {
-    if (ctx.req.method != HttpMethod.GET) return
-    ctx.res.setBodyText(UUID.randomUUID().toString())
-}
\ No newline at end of file
diff --git a/site/src/jvmMain/kotlin/todo/api/List.kt b/site/src/jvmMain/kotlin/todo/api/List.kt
deleted file mode 100644
index b4808a1..0000000
--- a/site/src/jvmMain/kotlin/todo/api/List.kt
+++ /dev/null
@@ -1,19 +0,0 @@
-package todo.api
-
-import com.varabyte.kobweb.api.Api
-import com.varabyte.kobweb.api.ApiContext
-import com.varabyte.kobweb.api.data.getValue
-import com.varabyte.kobweb.api.http.HttpMethod
-import com.varabyte.kobweb.api.http.setBodyText
-import kotlinx.serialization.encodeToString
-import kotlinx.serialization.json.Json
-import todo.model.TodoStore
-
-@Api
-fun listTodos(ctx: ApiContext) {
-    if (ctx.req.method != HttpMethod.GET) return
-    val ownerId = ctx.req.params["owner"] ?: return
-
-    val todos = ctx.data.getValue<TodoStore>()
-    ctx.res.setBodyText(Json.encodeToString(todos[ownerId]))
-}
diff --git a/site/src/jvmMain/kotlin/todo/api/Remove.kt b/site/src/jvmMain/kotlin/todo/api/Remove.kt
deleted file mode 100644
index 7c31452..0000000
--- a/site/src/jvmMain/kotlin/todo/api/Remove.kt
+++ /dev/null
@@ -1,21 +0,0 @@
-package todo.api
-
-import com.varabyte.kobweb.api.Api
-import com.varabyte.kobweb.api.ApiContext
-import com.varabyte.kobweb.api.data.getValue
-import com.varabyte.kobweb.api.http.HttpMethod
-import todo.model.TodoStore
-
-@Api
-fun removeTodo(ctx: ApiContext) {
-    if (ctx.req.method != HttpMethod.POST) return
-
-    val ownerId = ctx.req.params["owner"]
-    val todoId = ctx.req.params["todo"]
-    if (ownerId == null || todoId == null) {
-        return
-    }
-
-    ctx.data.getValue<TodoStore>().remove(ownerId, todoId)
-    ctx.res.status = 200
-}
\ No newline at end of file
diff --git a/site/src/jvmMain/kotlin/todo/api/Tasks.kt b/site/src/jvmMain/kotlin/todo/api/Tasks.kt
new file mode 100644
index 0000000..2f1fb9b
--- /dev/null
+++ b/site/src/jvmMain/kotlin/todo/api/Tasks.kt
@@ -0,0 +1,51 @@
+package todo.api
+
+import com.varabyte.kobweb.api.Api
+import com.varabyte.kobweb.api.ApiContext
+import com.varabyte.kobweb.api.data.getValue
+import com.varabyte.kobweb.api.http.setBodyText
+import kotlinx.serialization.decodeFromString
+import kotlinx.serialization.encodeToString
+import kotlinx.serialization.json.Json
+import org.bson.codecs.ObjectIdGenerator
+import todo.data.MongoDbImp
+import todo.model.ApiListResponse
+import todo.model.Task
+
+
+@Api(routeOverride = "addtask")
+suspend fun addTask(context: ApiContext) {
+    try {
+        val task = context.req.body?.decodeToString()?.let { Json.decodeFromString<Task>(it) }
+        val newTask = task?.copy(_id = ObjectIdGenerator().generate().toString())
+        val responseBody = Json.encodeToString(newTask?.let { context.data.getValue<MongoDbImp>().addTask(it) })
+        context.res.setBodyText(responseBody)
+    }catch (e: Exception) {
+        context.res.setBodyText(Json.encodeToString(e))
+    }
+
+}
+
+
+@Api(routeOverride = "getalltasks")
+suspend fun getAllTasks(context: ApiContext) {
+    try {
+        val myTasks = context.data.getValue<MongoDbImp>().getAllTasks()
+        context.res.setBodyText(Json.encodeToString(ApiListResponse.Success(data = myTasks)))
+    }catch (e: Exception){
+        context.res.setBodyText(Json.encodeToString(ApiListResponse.Error(message = e.message.toString())))
+    }
+}
+
+/*
+@Api(routeOverride = "deletetask")
+suspend fun deleteTask(context: ApiContext) {
+    try {
+        val task = context.req.body?.decodeToString()?.let { Json.decodeFromString<Task>(it) }
+        val responseBody = Json.encodeToString(task?.let { context.data.getValue<MongoDbImp>().deleteTask(it._id) })
+        context.res.setBodyText(responseBody)
+    }catch (e: Exception) {
+        context.res.setBodyText(Json.encodeToString(e))
+    }
+
+}*/
diff --git a/site/src/jvmMain/kotlin/todo/api/tasks b/site/src/jvmMain/kotlin/todo/api/tasks
deleted file mode 100644
index e69de29..0000000
diff --git a/site/src/jvmMain/kotlin/todo/api/tasks.kt b/site/src/jvmMain/kotlin/todo/api/tasks.kt
deleted file mode 100644
index f27e427..0000000
--- a/site/src/jvmMain/kotlin/todo/api/tasks.kt
+++ /dev/null
@@ -1,10 +0,0 @@
-package todo.api
-
-import com.varabyte.kobweb.api.Api
-import com.varabyte.kobweb.api.ApiContext
-
-
-@Api(routeOverride = "addtask")
-suspend fun addTask(context: ApiContext) {
-
-}
\ No newline at end of file
diff --git a/site/src/jvmMain/kotlin/todo/data/MongoDb.kt b/site/src/jvmMain/kotlin/todo/data/MongoDb.kt
index 3ef5439..3c8c744 100644
--- a/site/src/jvmMain/kotlin/todo/data/MongoDb.kt
+++ b/site/src/jvmMain/kotlin/todo/data/MongoDb.kt
@@ -5,4 +5,5 @@ import todo.model.Task
 interface MongoDb {
     suspend fun getAllTasks(): List<Task>
     suspend fun addTask(task: Task): Boolean
+    /*suspend fun deleteTask(taskID: String): Boolean*/
 }
\ No newline at end of file
diff --git a/site/src/jvmMain/kotlin/todo/data/MongoDbImplementation.kt b/site/src/jvmMain/kotlin/todo/data/MongoDbImp.kt
similarity index 66%
rename from site/src/jvmMain/kotlin/todo/data/MongoDbImplementation.kt
rename to site/src/jvmMain/kotlin/todo/data/MongoDbImp.kt
index 6b1304e..b0ad57f 100644
--- a/site/src/jvmMain/kotlin/todo/data/MongoDbImplementation.kt
+++ b/site/src/jvmMain/kotlin/todo/data/MongoDbImp.kt
@@ -1,23 +1,27 @@
 package todo.data
 
+import com.mongodb.client.model.Filters
 import com.mongodb.kotlin.client.coroutine.MongoClient
 import com.varabyte.kobweb.api.data.add
+import com.varabyte.kobweb.api.init.InitApi
 import com.varabyte.kobweb.api.init.InitApiContext
 import kotlinx.coroutines.flow.toList
 import todo.model.Task
 
+@InitApi
 fun initializeMongo(context: InitApiContext) {
     System.setProperty(
         "org.litote.mongo.test.mapping.service",
         "org.litote.kmongo.serialization.SerializationClassMappingTypeService"
     )
-    context.data.add(MongoDbImplementation())
+    context.data.add(MongoDbImp())
 }
 
-class MongoDbImplementation():MongoDb {
+
+class MongoDbImp(): MongoDb {
 
     private val client = MongoClient.create()
-    private val database = client.getDatabase("tasks")
+    private val database = client.getDatabase("todolist")
     private val tasksCollection = database.getCollection<Task>("tasks")
 
 
@@ -30,4 +34,10 @@ class MongoDbImplementation():MongoDb {
     override suspend fun addTask(task: Task): Boolean {
         return tasksCollection.insertOne(task).wasAcknowledged()
     }
+
+    /*override suspend fun deleteTask(taskID: String): Boolean {
+        val filter = Filters.eq("_id", taskID)
+
+        return tasksCollection.deleteOne(filter).wasAcknowledged()
+    }*/
 }
\ No newline at end of file
-- 
GitLab