-
Notifications
You must be signed in to change notification settings - Fork 150
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge branch 'master' of github.com:lloydmeta/enumeratum
- Loading branch information
Showing
10 changed files
with
459 additions
and
4 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
14 changes: 14 additions & 0 deletions
14
enumeratum-argonaut/src/main/scala/enumeratum/ArgonautEnum.scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
package enumeratum | ||
|
||
import argonaut._ | ||
|
||
/** | ||
* Created by alonsodomin on 14/10/2016. | ||
*/ | ||
trait ArgonautEnum[A <: EnumEntry] { this: Enum[A] => | ||
|
||
implicit val argonautEncoder: EncodeJson[A] = Argonauter.encoder(this) | ||
|
||
implicit val argonautDecoder: DecodeJson[A] = Argonauter.decoder(this) | ||
|
||
} |
45 changes: 45 additions & 0 deletions
45
enumeratum-argonaut/src/main/scala/enumeratum/Argonauter.scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,45 @@ | ||
package enumeratum | ||
|
||
import argonaut._ | ||
import Argonaut._ | ||
|
||
/** | ||
* Created by alonsodomin on 14/10/2016. | ||
*/ | ||
object Argonauter { | ||
|
||
private def encoder0[A <: EnumEntry](f: A => String): EncodeJson[A] = | ||
stringEncoder.contramap(f) | ||
|
||
def encoder[A <: EnumEntry](enum: Enum[A]): EncodeJson[A] = | ||
encoder0[A](_.entryName) | ||
|
||
def encoderLowercase[A <: EnumEntry](enum: Enum[A]): EncodeJson[A] = | ||
encoder0[A](_.entryName.toLowerCase) | ||
|
||
def encoderUppercase[A <: EnumEntry](enum: Enum[A]): EncodeJson[A] = | ||
encoder0[A](_.entryName.toUpperCase) | ||
|
||
private def decoder0[A <: EnumEntry](enum: Enum[A])(f: String => Option[A]): DecodeJson[A] = | ||
DecodeJson { cursor => | ||
stringDecoder(cursor).flatMap { enumStr => | ||
f(enumStr) match { | ||
case Some(a) => okResult(a) | ||
case _ => failResult(s"$enumStr' is not a member of enum $enum", cursor.history) | ||
} | ||
} | ||
} | ||
|
||
def decoder[A <: EnumEntry](enum: Enum[A]): DecodeJson[A] = | ||
decoder0(enum)(enum.withNameOption) | ||
|
||
def decoderLowercaseOnly[A <: EnumEntry](enum: Enum[A]): DecodeJson[A] = | ||
decoder0(enum)(enum.withNameLowercaseOnlyOption) | ||
|
||
def decoderUppercaseOnly[A <: EnumEntry](enum: Enum[A]): DecodeJson[A] = | ||
decoder0(enum)(enum.withNameUppercaseOnlyOption) | ||
|
||
private val stringEncoder = implicitly[EncodeJson[String]] | ||
private val stringDecoder = implicitly[DecodeJson[String]] | ||
|
||
} |
75 changes: 75 additions & 0 deletions
75
enumeratum-argonaut/src/main/scala/enumeratum/values/ArgonautValueEnum.scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,75 @@ | ||
package enumeratum.values | ||
|
||
import argonaut._ | ||
import Argonaut._ | ||
|
||
/** | ||
* Created by alonsodomin on 14/10/2016. | ||
*/ | ||
sealed trait ArgonautValueEnum[ValueType, EntryType <: ValueEnumEntry[ValueType]] { | ||
this: ValueEnum[ValueType, EntryType] => | ||
|
||
implicit def argonautEncoder: EncodeJson[EntryType] | ||
implicit def argonautDecoder: DecodeJson[EntryType] | ||
|
||
} | ||
|
||
/** | ||
* ArgonautEnum for IntEnumEntry | ||
*/ | ||
trait IntArgonautEnum[EntryType <: IntEnumEntry] extends ArgonautValueEnum[Int, EntryType] { | ||
this: ValueEnum[Int, EntryType] => | ||
|
||
implicit val argonautEncoder: EncodeJson[EntryType] = Argonauter.encoder(this) | ||
implicit val argonautDecoder: DecodeJson[EntryType] = Argonauter.decoder(this) | ||
} | ||
|
||
/** | ||
* ArgonautEnum for LongEnumEntry | ||
*/ | ||
trait LongArgonautEnum[EntryType <: LongEnumEntry] extends ArgonautValueEnum[Long, EntryType] { | ||
this: ValueEnum[Long, EntryType] => | ||
|
||
implicit val argonautEncoder: EncodeJson[EntryType] = Argonauter.encoder(this) | ||
implicit val argonautDecoder: DecodeJson[EntryType] = Argonauter.decoder(this) | ||
} | ||
|
||
/** | ||
* ArgonautEnum for ShortEnumEntry | ||
*/ | ||
trait ShortArgonautEnum[EntryType <: ShortEnumEntry] extends ArgonautValueEnum[Short, EntryType] { | ||
this: ValueEnum[Short, EntryType] => | ||
|
||
implicit val argonautEncoder: EncodeJson[EntryType] = Argonauter.encoder(this) | ||
implicit val argonautDecoder: DecodeJson[EntryType] = Argonauter.decoder(this) | ||
} | ||
|
||
/** | ||
* ArgonautEnum for StringEnumEntry | ||
*/ | ||
trait StringArgonautEnum[EntryType <: StringEnumEntry] | ||
extends ArgonautValueEnum[String, EntryType] { this: ValueEnum[String, EntryType] => | ||
|
||
implicit val argonautEncoder: EncodeJson[EntryType] = Argonauter.encoder(this) | ||
implicit val argonautDecoder: DecodeJson[EntryType] = Argonauter.decoder(this) | ||
} | ||
|
||
/** | ||
* ArgonautEnum for CharEnumEntry | ||
*/ | ||
trait CharArgonautEnum[EntryType <: CharEnumEntry] extends ArgonautValueEnum[Char, EntryType] { | ||
this: ValueEnum[Char, EntryType] => | ||
|
||
implicit val argonautEncoder: EncodeJson[EntryType] = Argonauter.encoder(this) | ||
implicit val argonautDecoder: DecodeJson[EntryType] = Argonauter.decoder(this) | ||
} | ||
|
||
/** | ||
* ArgonautEnum for ByteEnumEntry | ||
*/ | ||
trait ByteArgonautEnum[EntryType <: ByteEnumEntry] extends ArgonautValueEnum[Byte, EntryType] { | ||
this: ValueEnum[Byte, EntryType] => | ||
|
||
implicit val argonautEncoder: EncodeJson[EntryType] = Argonauter.encoder(this) | ||
implicit val argonautDecoder: DecodeJson[EntryType] = Argonauter.decoder(this) | ||
} |
32 changes: 32 additions & 0 deletions
32
enumeratum-argonaut/src/main/scala/enumeratum/values/Argonauter.scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
package enumeratum.values | ||
|
||
import argonaut._ | ||
import Argonaut._ | ||
|
||
/** | ||
* Created by alonsodomin on 14/10/2016. | ||
*/ | ||
object Argonauter { | ||
|
||
def encoder[ValueType: EncodeJson, EntryType <: ValueEnumEntry[ValueType]]( | ||
enum: ValueEnum[ValueType, EntryType]): EncodeJson[EntryType] = { | ||
val encodeValue = implicitly[EncodeJson[ValueType]] | ||
EncodeJson { entry => | ||
encodeValue(entry.value) | ||
} | ||
} | ||
|
||
def decoder[ValueType: DecodeJson, EntryType <: ValueEnumEntry[ValueType]]( | ||
enum: ValueEnum[ValueType, EntryType]): DecodeJson[EntryType] = { | ||
val decodeValue = implicitly[DecodeJson[ValueType]] | ||
DecodeJson { cursor => | ||
decodeValue(cursor).flatMap { value => | ||
enum.withValueOpt(value) match { | ||
case Some(entry) => okResult(entry) | ||
case _ => failResult(s"$value is not a member of enum $enum", cursor.history) | ||
} | ||
} | ||
} | ||
} | ||
|
||
} |
19 changes: 19 additions & 0 deletions
19
enumeratum-argonaut/src/main/scala/enumeratum/values/package.scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
package enumeratum | ||
|
||
import argonaut.Argonaut._ | ||
import argonaut.{DecodeJson, EncodeJson} | ||
|
||
/** | ||
* Created by alonsodomin on 15/10/2016. | ||
*/ | ||
package object values { | ||
|
||
implicit val argonautByteEncoder: EncodeJson[Byte] = EncodeJson { byte => | ||
jNumber(byte.toShort) | ||
} | ||
|
||
implicit val argonautByteDecoder: DecodeJson[Byte] = DecodeJson { cursor => | ||
cursor.as[Short].map(_.toByte) | ||
} | ||
|
||
} |
63 changes: 63 additions & 0 deletions
63
enumeratum-argonaut/src/test/scala/enumeratum/ArgonautSpec.scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,63 @@ | ||
package enumeratum | ||
|
||
import org.scalatest.{FunSpec, Matchers} | ||
|
||
import argonaut._ | ||
import Argonaut._ | ||
|
||
/** | ||
* Created by alonsodomin on 14/10/2016. | ||
*/ | ||
class ArgonautSpec extends FunSpec with Matchers { | ||
|
||
describe("to JSON") { | ||
it("should work") { | ||
TrafficLight.values.foreach { value => | ||
value.asJson shouldBe value.entryName.asJson | ||
} | ||
} | ||
|
||
it("should work for lower case") { | ||
TrafficLight.values.foreach { value => | ||
value.asJson(Argonauter.encoderLowercase(TrafficLight)) shouldBe value.entryName.toLowerCase.asJson | ||
} | ||
} | ||
|
||
it("should work for upper case") { | ||
TrafficLight.values.foreach { value => | ||
value.asJson(Argonauter.encoderUppercase(TrafficLight)) shouldBe value.entryName.toUpperCase.asJson | ||
} | ||
} | ||
} | ||
|
||
describe("from JSON") { | ||
it("should parse enum members when given proper encoding") { | ||
TrafficLight.values.foreach { value => | ||
value.entryName.asJson.as[TrafficLight] shouldBe okResult(value) | ||
} | ||
} | ||
|
||
it("should parse enum members when given proper encoding for lower case") { | ||
TrafficLight.values.foreach { value => | ||
value.entryName.toLowerCase.asJson | ||
.as[TrafficLight](Argonauter.decoderLowercaseOnly(TrafficLight)) shouldBe okResult(value) | ||
} | ||
} | ||
|
||
it("should parse enum members when given proper encoding for upper case") { | ||
TrafficLight.values.foreach { value => | ||
value.entryName.toUpperCase.asJson | ||
.as[TrafficLight](Argonauter.decoderUppercaseOnly(TrafficLight)) shouldBe okResult(value) | ||
} | ||
} | ||
|
||
it("should fail to parse random JSON values to members") { | ||
val results = Seq("XXL".asJson, Int.MaxValue.asJson).map(_.as[TrafficLight]) | ||
results.foreach { res => | ||
res.result.isLeft shouldBe true | ||
res.history.map(_.toList) shouldBe Some(Nil) | ||
} | ||
} | ||
} | ||
|
||
} |
13 changes: 13 additions & 0 deletions
13
enumeratum-argonaut/src/test/scala/enumeratum/TrafficLight.scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
package enumeratum | ||
|
||
/** | ||
* Created by alonsodomin on 14/10/2016. | ||
*/ | ||
sealed trait TrafficLight extends EnumEntry | ||
object TrafficLight extends Enum[TrafficLight] with ArgonautEnum[TrafficLight] { | ||
case object Red extends TrafficLight | ||
case object Yellow extends TrafficLight | ||
case object Green extends TrafficLight | ||
|
||
val values = findValues | ||
} |
Oops, something went wrong.