Let’s define some refined types, which we can use later on. We need two things: a language code that obeys the restrictions of ISO-639-1, and a stronger definition for a product name. For the former, we use a regular expression, and for the latter, we simply expect a non-empty String.
12
type LanguageCode = String Refined MatchesRegex[W.`"^[a-z]{2}$"`.T]
type ProductName = String Refined NonEmpty
Refined types for models
Now, we can give our translation model another try.
1
final case class Translation(lang: LanguageCode, name: ProductName)
Translation model using refined types
Much better! While we’re at it, we can also write the JSON codecs using the refined module of the Circe library. We put them into the companion object of the model.