Skip to content

Commit

Permalink
Add dict to endpoints params and response
Browse files Browse the repository at this point in the history
  • Loading branch information
wilmveel committed Jul 16, 2024
1 parent 13cf2a7 commit 4cb35c7
Show file tree
Hide file tree
Showing 2 changed files with 88 additions and 12 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -47,12 +47,26 @@ class EndpointParser(logger: Logger) : AbstractParser(logger) {
else -> raise(WrongTokenException<Method>(token))
}.also { eatToken().bind() }

val isDict = when (token.type) {
is LeftCurly -> true.also { eatToken().bind() }
else -> false
}

val requests = listOf(
when (token.type) {
is WirespecType -> parseReference(token.type as WirespecType, token.value).bind()
is WirespecType -> parseReference(token.type as WirespecType, token.value, isDict).bind()
else -> null
}
).map {
)
.also {
if (isDict) {
when (token.type) {
is RightCurly -> eatToken().bind()
else -> raise(WrongTokenException<RightCurly>(token).also { eatToken().bind() })
}
}
}
.map {
Endpoint.Request(
content = it?.let {
Endpoint.Content(
Expand Down Expand Up @@ -143,9 +157,20 @@ class EndpointParser(logger: Logger) : AbstractParser(logger) {
is Colon -> eatToken().bind()
else -> raise(WrongTokenException<Colon>(token))
}
val isDict = when (token.type) {
is LeftCurly -> true.also { eatToken().bind() }
else -> false
}
val reference = when (token.type) {
is WirespecType -> parseReference(token.type as WirespecType, token.value).bind()
is WirespecType -> parseReference(token.type as WirespecType, token.value, isDict).bind()
else -> raise(WrongTokenException<WirespecType>(token))
}.also {
if (isDict) {
when (token.type) {
is RightCurly -> eatToken().bind()
else -> raise(WrongTokenException<RightCurly>(token).also { eatToken().bind() })
}
}
}
when (token.type) {
is RightCurly -> eatToken().bind()
Expand Down Expand Up @@ -182,35 +207,63 @@ class EndpointParser(logger: Logger) : AbstractParser(logger) {
}
eatToken().bind()
token.log()
val isDict = when (token.type) {
is LeftCurly -> true.also { eatToken().bind() }
else -> false
}
val content = when (token.type) {
is WirespecType -> parseContent(token.type as WirespecType, token.value).bind()
is WirespecType -> parseContent(token.type as WirespecType, token.value, isDict).bind()
else -> raise(WrongTokenException<WirespecType>(token))
}.also {
if (isDict) {
when (token.type) {
is RightCurly -> eatToken().bind()
else -> raise(WrongTokenException<RightCurly>(token).also { eatToken().bind() })
}
}
}
Endpoint.Response(status = statusCode, headers = emptyList(), content = content)
}

private fun TokenProvider.parseContent(wsType: WirespecType, value: String) = either {
private fun TokenProvider.parseContent(wsType: WirespecType, value: String, isDict:Boolean) = either {
token.log()
val reference = parseReference(wsType, value).bind()
if(reference is Reference.Unit) null
val reference = parseReference(wsType, value, isDict).bind()
if (reference is Reference.Unit) null
else Endpoint.Content(
type = "application/json",
reference = reference,
)
}

private fun TokenProvider.parseReference(wsType: WirespecType, value: String) = either {
private fun TokenProvider.parseReference(wsType: WirespecType, value: String, isDict: Boolean) = either {
val previousToken = token
eatToken().bind()
token.log()
val isIterable = (token.type is Brackets).also { if (it) eatToken().bind() }
when (wsType) {
is WsString -> Reference.Primitive(Reference.Primitive.Type.String, isIterable)
is WsString -> Reference.Primitive(
type = Reference.Primitive.Type.String,
isIterable = isIterable,
isDictionary = isDict,
)

is WsInteger -> Reference.Primitive(Reference.Primitive.Type.Integer, isIterable)
is WsNumber -> Reference.Primitive(Reference.Primitive.Type.Number, isIterable)
is WsInteger -> Reference.Primitive(
type = Reference.Primitive.Type.Integer,
isIterable = isIterable,
isDictionary = isDict,
)

is WsNumber -> Reference.Primitive(
type = Reference.Primitive.Type.Number,
isIterable = isIterable,
isDictionary = isDict,
)

is WsBoolean -> Reference.Primitive(Reference.Primitive.Type.Boolean, isIterable)
is WsBoolean -> Reference.Primitive(
type = Reference.Primitive.Type.Boolean,
isIterable = isIterable,
isDictionary = isDict,
)

is WsUnit -> Reference.Unit(isIterable)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,9 @@ import community.flock.wirespec.compiler.core.parse.Field.Reference.Primitive.Ty
import community.flock.wirespec.compiler.core.tokenize.tokenize
import community.flock.wirespec.compiler.utils.noLogger
import io.kotest.assertions.arrow.core.shouldBeRight
import io.kotest.matchers.booleans.shouldBeTrue
import io.kotest.matchers.collections.shouldNotBeEmpty
import io.kotest.matchers.nulls.shouldBeNull
import io.kotest.matchers.nulls.shouldNotBeNull
import io.kotest.matchers.shouldBe
import io.kotest.matchers.types.shouldBeInstanceOf
Expand Down Expand Up @@ -193,4 +195,25 @@ class ParseEndpointTest {
}
}
}

@Test
fun testDictionaryResponse() {
val source = """
endpoint GetTodos GET /todos ? {done:{String}} # {token:{String}} -> {
200 -> {String}
}
""".trimIndent()

WirespecSpec.tokenize(source)
.let(parser()::parse)
.shouldBeRight()
.also { it.size shouldBe 1 }[0]
.shouldBeInstanceOf<Endpoint>().run {
responses.shouldNotBeEmpty()
responses.first().content?.reference?.isDictionary?.shouldBeTrue()
query.first().reference.isDictionary.shouldBeTrue()
headers.first().reference.isDictionary.shouldBeTrue()
}

}
}

0 comments on commit 4cb35c7

Please sign in to comment.