Skip to content

Commit 52e135e

Browse files
committed
Add htmx_inline_validation.sc
1 parent f29bc5a commit 52e135e

File tree

1 file changed

+69
-0
lines changed

1 file changed

+69
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
//> using scala "3.3.1"
2+
//> using dep ba.sake::sharaf:0.0.22
3+
4+
import io.undertow.Undertow
5+
import ba.sake.sharaf.*, routing.*
6+
import ba.sake.formson.FormDataRW
7+
8+
object views {
9+
import scalatags.Text.all.*
10+
import ba.sake.hepek.html.HtmlPage
11+
import ba.sake.hepek.htmx.*
12+
13+
class IndexView(formData: ContactForm) extends HtmlPage with HtmxDependencies:
14+
override def bodyContent = div(
15+
h3("Signup Form"),
16+
contactForm(formData)
17+
)
18+
19+
override def stylesInline = List("""
20+
.error-message {
21+
color:red;
22+
}
23+
.error input {
24+
box-shadow: 0 0 3px #CC0000;
25+
}
26+
.valid input {
27+
box-shadow: 0 0 3px #36cc00;
28+
}
29+
""")
30+
31+
def contactForm(formData: ContactForm) = form(hx.post := "/contact", hx.swap := "outerHTML")(
32+
emailField(formData.email, false),
33+
div(label("First Name")(input(name := "firstName", value := formData.firstName))),
34+
div(label("Last Name")(input(name := "lastName", value := formData.lastName))),
35+
button("Submit")
36+
)
37+
38+
def emailField(fieldValue: String, isError: Boolean) =
39+
div(hx.target := "this", hx.swap := "outerHTML", Option.when(isError)(cls := "error"))(
40+
label("Email Address")(
41+
input(name := "email", value := fieldValue, hx.post := "/contact/email", hx.indicator := "#ind"),
42+
img(id := "ind", src := "/img/bars.svg", cls := "htmx-indicator")
43+
),
44+
Option.when(isError)(div(cls := "error-message")("That email is already taken. Please enter another email."))
45+
)
46+
47+
}
48+
49+
case class ContactForm(email: String, firstName: String, lastName: String) derives FormDataRW
50+
51+
val routes = Routes:
52+
case GET() -> Path() =>
53+
val formData = ContactForm("", "", "")
54+
Response.withBody(views.IndexView(formData))
55+
case POST() -> Path("contact", "email") =>
56+
val formData = Request.current.bodyForm[ContactForm]
57+
val isValid = formData.email == "[email protected]"
58+
Response.withBody(views.emailField(formData.email, !isValid))
59+
case POST() -> Path("contact") =>
60+
val formData = Request.current.bodyForm[ContactForm]
61+
Response.withBody(views.contactForm(formData))
62+
63+
Undertow.builder
64+
.addHttpListener(8181, "localhost")
65+
.setHandler(SharafHandler(routes))
66+
.build
67+
.start()
68+
69+
println(s"Server started at http://localhost:8181")

0 commit comments

Comments
 (0)