Created
May 2, 2015 19:56
-
-
Save xasima/e88fd1d284bf15c916e0 to your computer and use it in GitHub Desktop.
Thrift, json, and scrooge scala to test scrooge(thrift) - argounaut(json) bijection
This file contains hidden or 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
| /** | |
| * Generated by Scrooge | |
| * version: 3.14.1 | |
| * rev: a996c1128a032845c508102d62e65fc0aa7a5f41 | |
| * built at: 20140501-114707 | |
| */ | |
| package com.xxx.services | |
| import com.twitter.scrooge.{ | |
| TFieldBlob, ThriftException, ThriftStruct, ThriftStructCodec3, ThriftStructFieldInfo, ThriftUtil} | |
| import org.apache.thrift.protocol._ | |
| import org.apache.thrift.transport.{TMemoryBuffer, TTransport} | |
| import java.nio.ByteBuffer | |
| import java.util.Arrays | |
| import scala.collection.immutable.{Map => immutable$Map} | |
| import scala.collection.mutable.Builder | |
| import scala.collection.mutable.{ | |
| ArrayBuffer => mutable$ArrayBuffer, Buffer => mutable$Buffer, | |
| HashMap => mutable$HashMap, HashSet => mutable$HashSet} | |
| import scala.collection.{Map, Set} | |
| /** | |
| * Etagged identifier that helps to | |
| * fetched most recent data. This needs to distinguish if | |
| * the local cached version differs from the remote | |
| */ | |
| object ETag extends ThriftStructCodec3[ETag] { | |
| private val NoPassthroughFields = immutable$Map.empty[Short, TFieldBlob] | |
| val Struct = new TStruct("ETag") | |
| val IdField = new TField("id", TType.STRING, 1) | |
| val IdFieldManifest = implicitly[Manifest[String]] | |
| val RefIdField = new TField("refId", TType.STRING, 2) | |
| val RefIdFieldManifest = implicitly[Manifest[String]] | |
| val ModifiedDateField = new TField("modifiedDate", TType.STRING, 3) | |
| val ModifiedDateFieldManifest = implicitly[Manifest[String]] | |
| val ExpiresDateField = new TField("expiresDate", TType.STRING, 4) | |
| val ExpiresDateFieldManifest = implicitly[Manifest[String]] | |
| val ExpiresPeriodField = new TField("expiresPeriod", TType.STRING, 5) | |
| val ExpiresPeriodFieldManifest = implicitly[Manifest[String]] | |
| /** | |
| * Field information in declaration order. | |
| */ | |
| lazy val fieldInfos: scala.List[ThriftStructFieldInfo] = scala.List[ThriftStructFieldInfo]( | |
| new ThriftStructFieldInfo( | |
| IdField, | |
| false, | |
| IdFieldManifest, | |
| None, | |
| None, | |
| immutable$Map( | |
| ), | |
| immutable$Map( | |
| ) | |
| ), | |
| new ThriftStructFieldInfo( | |
| RefIdField, | |
| false, | |
| RefIdFieldManifest, | |
| None, | |
| None, | |
| immutable$Map( | |
| ), | |
| immutable$Map( | |
| ) | |
| ), | |
| new ThriftStructFieldInfo( | |
| ModifiedDateField, | |
| true, | |
| ModifiedDateFieldManifest, | |
| None, | |
| None, | |
| immutable$Map( | |
| ), | |
| immutable$Map( | |
| ) | |
| ), | |
| new ThriftStructFieldInfo( | |
| ExpiresDateField, | |
| true, | |
| ExpiresDateFieldManifest, | |
| None, | |
| None, | |
| immutable$Map( | |
| ), | |
| immutable$Map( | |
| ) | |
| ), | |
| new ThriftStructFieldInfo( | |
| ExpiresPeriodField, | |
| true, | |
| ExpiresPeriodFieldManifest, | |
| None, | |
| None, | |
| immutable$Map( | |
| ), | |
| immutable$Map( | |
| ) | |
| ) | |
| ) | |
| lazy val structAnnotations: immutable$Map[String, String] = | |
| immutable$Map[String, String]( | |
| ) | |
| /** | |
| * Checks that all required fields are non-null. | |
| */ | |
| def validate(_item: ETag) { | |
| } | |
| override def encode(_item: ETag, _oproto: TProtocol) { | |
| _item.write(_oproto) | |
| } | |
| override def decode(_iprot: TProtocol): ETag = { | |
| var id: String = null | |
| var refId: String = null | |
| var modifiedDate: Option[String] = None | |
| var expiresDate: Option[String] = None | |
| var expiresPeriod: Option[String] = None | |
| var _passthroughFields: Builder[(Short, TFieldBlob), immutable$Map[Short, TFieldBlob]] = null | |
| var _done = false | |
| _iprot.readStructBegin() | |
| while (!_done) { | |
| val _field = _iprot.readFieldBegin() | |
| if (_field.`type` == TType.STOP) { | |
| _done = true | |
| } else { | |
| _field.id match { | |
| case 1 => | |
| _field.`type` match { | |
| case TType.STRING => { | |
| id = readIdValue(_iprot) | |
| } | |
| case _actualType => | |
| val _expectedType = TType.STRING | |
| throw new TProtocolException( | |
| "Received wrong type for field 'id' (expected=%s, actual=%s).".format( | |
| ttypeToHuman(_expectedType), | |
| ttypeToHuman(_actualType) | |
| ) | |
| ) | |
| } | |
| case 2 => | |
| _field.`type` match { | |
| case TType.STRING => { | |
| refId = readRefIdValue(_iprot) | |
| } | |
| case _actualType => | |
| val _expectedType = TType.STRING | |
| throw new TProtocolException( | |
| "Received wrong type for field 'refId' (expected=%s, actual=%s).".format( | |
| ttypeToHuman(_expectedType), | |
| ttypeToHuman(_actualType) | |
| ) | |
| ) | |
| } | |
| case 3 => | |
| _field.`type` match { | |
| case TType.STRING => { | |
| modifiedDate = Some(readModifiedDateValue(_iprot)) | |
| } | |
| case _actualType => | |
| val _expectedType = TType.STRING | |
| throw new TProtocolException( | |
| "Received wrong type for field 'modifiedDate' (expected=%s, actual=%s).".format( | |
| ttypeToHuman(_expectedType), | |
| ttypeToHuman(_actualType) | |
| ) | |
| ) | |
| } | |
| case 4 => | |
| _field.`type` match { | |
| case TType.STRING => { | |
| expiresDate = Some(readExpiresDateValue(_iprot)) | |
| } | |
| case _actualType => | |
| val _expectedType = TType.STRING | |
| throw new TProtocolException( | |
| "Received wrong type for field 'expiresDate' (expected=%s, actual=%s).".format( | |
| ttypeToHuman(_expectedType), | |
| ttypeToHuman(_actualType) | |
| ) | |
| ) | |
| } | |
| case 5 => | |
| _field.`type` match { | |
| case TType.STRING => { | |
| expiresPeriod = Some(readExpiresPeriodValue(_iprot)) | |
| } | |
| case _actualType => | |
| val _expectedType = TType.STRING | |
| throw new TProtocolException( | |
| "Received wrong type for field 'expiresPeriod' (expected=%s, actual=%s).".format( | |
| ttypeToHuman(_expectedType), | |
| ttypeToHuman(_actualType) | |
| ) | |
| ) | |
| } | |
| case _ => | |
| if (_passthroughFields == null) | |
| _passthroughFields = immutable$Map.newBuilder[Short, TFieldBlob] | |
| _passthroughFields += (_field.id -> TFieldBlob.read(_field, _iprot)) | |
| } | |
| _iprot.readFieldEnd() | |
| } | |
| } | |
| _iprot.readStructEnd() | |
| new Immutable( | |
| id, | |
| refId, | |
| modifiedDate, | |
| expiresDate, | |
| expiresPeriod, | |
| if (_passthroughFields == null) | |
| NoPassthroughFields | |
| else | |
| _passthroughFields.result() | |
| ) | |
| } | |
| def apply( | |
| id: String, | |
| refId: String, | |
| modifiedDate: Option[String] = None, | |
| expiresDate: Option[String] = None, | |
| expiresPeriod: Option[String] = None | |
| ): ETag = | |
| new Immutable( | |
| id, | |
| refId, | |
| modifiedDate, | |
| expiresDate, | |
| expiresPeriod | |
| ) | |
| def unapply(_item: ETag): Option[scala.Product5[String, String, Option[String], Option[String], Option[String]]] = Some(_item) | |
| private def readIdValue(_iprot: TProtocol): String = { | |
| _iprot.readString() | |
| } | |
| private def writeIdField(id_item: String, _oprot: TProtocol) { | |
| _oprot.writeFieldBegin(IdField) | |
| writeIdValue(id_item, _oprot) | |
| _oprot.writeFieldEnd() | |
| } | |
| private def writeIdValue(id_item: String, _oprot: TProtocol) { | |
| _oprot.writeString(id_item) | |
| } | |
| private def readRefIdValue(_iprot: TProtocol): String = { | |
| _iprot.readString() | |
| } | |
| private def writeRefIdField(refId_item: String, _oprot: TProtocol) { | |
| _oprot.writeFieldBegin(RefIdField) | |
| writeRefIdValue(refId_item, _oprot) | |
| _oprot.writeFieldEnd() | |
| } | |
| private def writeRefIdValue(refId_item: String, _oprot: TProtocol) { | |
| _oprot.writeString(refId_item) | |
| } | |
| private def readModifiedDateValue(_iprot: TProtocol): String = { | |
| _iprot.readString() | |
| } | |
| private def writeModifiedDateField(modifiedDate_item: String, _oprot: TProtocol) { | |
| _oprot.writeFieldBegin(ModifiedDateField) | |
| writeModifiedDateValue(modifiedDate_item, _oprot) | |
| _oprot.writeFieldEnd() | |
| } | |
| private def writeModifiedDateValue(modifiedDate_item: String, _oprot: TProtocol) { | |
| _oprot.writeString(modifiedDate_item) | |
| } | |
| private def readExpiresDateValue(_iprot: TProtocol): String = { | |
| _iprot.readString() | |
| } | |
| private def writeExpiresDateField(expiresDate_item: String, _oprot: TProtocol) { | |
| _oprot.writeFieldBegin(ExpiresDateField) | |
| writeExpiresDateValue(expiresDate_item, _oprot) | |
| _oprot.writeFieldEnd() | |
| } | |
| private def writeExpiresDateValue(expiresDate_item: String, _oprot: TProtocol) { | |
| _oprot.writeString(expiresDate_item) | |
| } | |
| private def readExpiresPeriodValue(_iprot: TProtocol): String = { | |
| _iprot.readString() | |
| } | |
| private def writeExpiresPeriodField(expiresPeriod_item: String, _oprot: TProtocol) { | |
| _oprot.writeFieldBegin(ExpiresPeriodField) | |
| writeExpiresPeriodValue(expiresPeriod_item, _oprot) | |
| _oprot.writeFieldEnd() | |
| } | |
| private def writeExpiresPeriodValue(expiresPeriod_item: String, _oprot: TProtocol) { | |
| _oprot.writeString(expiresPeriod_item) | |
| } | |
| private def ttypeToHuman(byte: Byte) = { | |
| // from https://github.com/apache/thrift/blob/master/lib/java/src/org/apache/thrift/protocol/TType.java | |
| byte match { | |
| case TType.STOP => "STOP" | |
| case TType.VOID => "VOID" | |
| case TType.BOOL => "BOOL" | |
| case TType.BYTE => "BYTE" | |
| case TType.DOUBLE => "DOUBLE" | |
| case TType.I16 => "I16" | |
| case TType.I32 => "I32" | |
| case TType.I64 => "I64" | |
| case TType.STRING => "STRING" | |
| case TType.STRUCT => "STRUCT" | |
| case TType.MAP => "MAP" | |
| case TType.SET => "SET" | |
| case TType.LIST => "LIST" | |
| case TType.ENUM => "ENUM" | |
| case _ => "UNKNOWN" | |
| } | |
| } | |
| object Immutable extends ThriftStructCodec3[ETag] { | |
| override def encode(_item: ETag, _oproto: TProtocol) { _item.write(_oproto) } | |
| override def decode(_iprot: TProtocol): ETag = ETag.decode(_iprot) | |
| } | |
| /** | |
| * The default read-only implementation of ETag. You typically should not need to | |
| * directly reference this class; instead, use the ETag.apply method to construct | |
| * new instances. | |
| */ | |
| class Immutable( | |
| val id: String, | |
| val refId: String, | |
| val modifiedDate: Option[String], | |
| val expiresDate: Option[String], | |
| val expiresPeriod: Option[String], | |
| override val _passthroughFields: immutable$Map[Short, TFieldBlob] | |
| ) extends ETag { | |
| def this( | |
| id: String, | |
| refId: String, | |
| modifiedDate: Option[String] = None, | |
| expiresDate: Option[String] = None, | |
| expiresPeriod: Option[String] = None | |
| ) = this( | |
| id, | |
| refId, | |
| modifiedDate, | |
| expiresDate, | |
| expiresPeriod, | |
| Map.empty | |
| ) | |
| } | |
| /** | |
| * This Proxy trait allows you to extend the ETag trait with additional state or | |
| * behavior and implement the read-only methods from ETag using an underlying | |
| * instance. | |
| */ | |
| trait Proxy extends ETag { | |
| protected def _underlying_ETag: ETag | |
| override def id: String = _underlying_ETag.id | |
| override def refId: String = _underlying_ETag.refId | |
| override def modifiedDate: Option[String] = _underlying_ETag.modifiedDate | |
| override def expiresDate: Option[String] = _underlying_ETag.expiresDate | |
| override def expiresPeriod: Option[String] = _underlying_ETag.expiresPeriod | |
| override def _passthroughFields = _underlying_ETag._passthroughFields | |
| } | |
| } | |
| trait ETag | |
| extends ThriftStruct | |
| with scala.Product5[String, String, Option[String], Option[String], Option[String]] | |
| with java.io.Serializable | |
| { | |
| import ETag._ | |
| def id: String | |
| def refId: String | |
| def modifiedDate: Option[String] | |
| def expiresDate: Option[String] | |
| def expiresPeriod: Option[String] | |
| def _passthroughFields: immutable$Map[Short, TFieldBlob] = immutable$Map.empty | |
| def _1 = id | |
| def _2 = refId | |
| def _3 = modifiedDate | |
| def _4 = expiresDate | |
| def _5 = expiresPeriod | |
| /** | |
| * Gets a field value encoded as a binary blob using TCompactProtocol. If the specified field | |
| * is present in the passthrough map, that value is returend. Otherwise, if the specified field | |
| * is known and not optional and set to None, then the field is serialized and returned. | |
| */ | |
| def getFieldBlob(_fieldId: Short): Option[TFieldBlob] = { | |
| lazy val _buff = new TMemoryBuffer(32) | |
| lazy val _oprot = new TCompactProtocol(_buff) | |
| _passthroughFields.get(_fieldId) orElse { | |
| val _fieldOpt: Option[TField] = | |
| _fieldId match { | |
| case 1 => | |
| if (id ne null) { | |
| writeIdValue(id, _oprot) | |
| Some(ETag.IdField) | |
| } else { | |
| None | |
| } | |
| case 2 => | |
| if (refId ne null) { | |
| writeRefIdValue(refId, _oprot) | |
| Some(ETag.RefIdField) | |
| } else { | |
| None | |
| } | |
| case 3 => | |
| if (modifiedDate.isDefined) { | |
| writeModifiedDateValue(modifiedDate.get, _oprot) | |
| Some(ETag.ModifiedDateField) | |
| } else { | |
| None | |
| } | |
| case 4 => | |
| if (expiresDate.isDefined) { | |
| writeExpiresDateValue(expiresDate.get, _oprot) | |
| Some(ETag.ExpiresDateField) | |
| } else { | |
| None | |
| } | |
| case 5 => | |
| if (expiresPeriod.isDefined) { | |
| writeExpiresPeriodValue(expiresPeriod.get, _oprot) | |
| Some(ETag.ExpiresPeriodField) | |
| } else { | |
| None | |
| } | |
| case _ => None | |
| } | |
| _fieldOpt match { | |
| case Some(_field) => | |
| val _data = Arrays.copyOfRange(_buff.getArray, 0, _buff.length) | |
| Some(TFieldBlob(_field, _data)) | |
| case None => | |
| None | |
| } | |
| } | |
| } | |
| /** | |
| * Collects TCompactProtocol-encoded field values according to `getFieldBlob` into a map. | |
| */ | |
| def getFieldBlobs(ids: TraversableOnce[Short]): immutable$Map[Short, TFieldBlob] = | |
| (ids flatMap { id => getFieldBlob(id) map { id -> _ } }).toMap | |
| /** | |
| * Sets a field using a TCompactProtocol-encoded binary blob. If the field is a known | |
| * field, the blob is decoded and the field is set to the decoded value. If the field | |
| * is unknown and passthrough fields are enabled, then the blob will be stored in | |
| * _passthroughFields. | |
| */ | |
| def setField(_blob: TFieldBlob): ETag = { | |
| var id: String = this.id | |
| var refId: String = this.refId | |
| var modifiedDate: Option[String] = this.modifiedDate | |
| var expiresDate: Option[String] = this.expiresDate | |
| var expiresPeriod: Option[String] = this.expiresPeriod | |
| var _passthroughFields = this._passthroughFields | |
| _blob.id match { | |
| case 1 => | |
| id = readIdValue(_blob.read) | |
| case 2 => | |
| refId = readRefIdValue(_blob.read) | |
| case 3 => | |
| modifiedDate = Some(readModifiedDateValue(_blob.read)) | |
| case 4 => | |
| expiresDate = Some(readExpiresDateValue(_blob.read)) | |
| case 5 => | |
| expiresPeriod = Some(readExpiresPeriodValue(_blob.read)) | |
| case _ => _passthroughFields += (_blob.id -> _blob) | |
| } | |
| new Immutable( | |
| id, | |
| refId, | |
| modifiedDate, | |
| expiresDate, | |
| expiresPeriod, | |
| _passthroughFields | |
| ) | |
| } | |
| /** | |
| * If the specified field is optional, it is set to None. Otherwise, if the field is | |
| * known, it is reverted to its default value; if the field is unknown, it is subtracked | |
| * from the passthroughFields map, if present. | |
| */ | |
| def unsetField(_fieldId: Short): ETag = { | |
| var id: String = this.id | |
| var refId: String = this.refId | |
| var modifiedDate: Option[String] = this.modifiedDate | |
| var expiresDate: Option[String] = this.expiresDate | |
| var expiresPeriod: Option[String] = this.expiresPeriod | |
| _fieldId match { | |
| case 1 => | |
| id = null | |
| case 2 => | |
| refId = null | |
| case 3 => | |
| modifiedDate = None | |
| case 4 => | |
| expiresDate = None | |
| case 5 => | |
| expiresPeriod = None | |
| case _ => | |
| } | |
| new Immutable( | |
| id, | |
| refId, | |
| modifiedDate, | |
| expiresDate, | |
| expiresPeriod, | |
| _passthroughFields - _fieldId | |
| ) | |
| } | |
| /** | |
| * If the specified field is optional, it is set to None. Otherwise, if the field is | |
| * known, it is reverted to its default value; if the field is unknown, it is subtracked | |
| * from the passthroughFields map, if present. | |
| */ | |
| def unsetId: ETag = unsetField(1) | |
| def unsetRefId: ETag = unsetField(2) | |
| def unsetModifiedDate: ETag = unsetField(3) | |
| def unsetExpiresDate: ETag = unsetField(4) | |
| def unsetExpiresPeriod: ETag = unsetField(5) | |
| override def write(_oprot: TProtocol) { | |
| ETag.validate(this) | |
| _oprot.writeStructBegin(Struct) | |
| if (id ne null) writeIdField(id, _oprot) | |
| if (refId ne null) writeRefIdField(refId, _oprot) | |
| if (modifiedDate.isDefined) writeModifiedDateField(modifiedDate.get, _oprot) | |
| if (expiresDate.isDefined) writeExpiresDateField(expiresDate.get, _oprot) | |
| if (expiresPeriod.isDefined) writeExpiresPeriodField(expiresPeriod.get, _oprot) | |
| _passthroughFields.values foreach { _.write(_oprot) } | |
| _oprot.writeFieldStop() | |
| _oprot.writeStructEnd() | |
| } | |
| def copy( | |
| id: String = this.id, | |
| refId: String = this.refId, | |
| modifiedDate: Option[String] = this.modifiedDate, | |
| expiresDate: Option[String] = this.expiresDate, | |
| expiresPeriod: Option[String] = this.expiresPeriod, | |
| _passthroughFields: immutable$Map[Short, TFieldBlob] = this._passthroughFields | |
| ): ETag = | |
| new Immutable( | |
| id, | |
| refId, | |
| modifiedDate, | |
| expiresDate, | |
| expiresPeriod, | |
| _passthroughFields | |
| ) | |
| override def canEqual(other: Any): Boolean = other.isInstanceOf[ETag] | |
| override def equals(other: Any): Boolean = | |
| _root_.scala.runtime.ScalaRunTime._equals(this, other) && | |
| _passthroughFields == other.asInstanceOf[ETag]._passthroughFields | |
| override def hashCode: Int = _root_.scala.runtime.ScalaRunTime._hashCode(this) | |
| override def toString: String = _root_.scala.runtime.ScalaRunTime._toString(this) | |
| override def productArity: Int = 5 | |
| override def productElement(n: Int): Any = n match { | |
| case 0 => this.id | |
| case 1 => this.refId | |
| case 2 => this.modifiedDate | |
| case 3 => this.expiresDate | |
| case 4 => this.expiresPeriod | |
| case _ => throw new IndexOutOfBoundsException(n.toString) | |
| } | |
| override def productPrefix: String = "ETag" | |
| } |
This file contains hidden or 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
| // Trivial JSON representation of thrift pb304.Etag data. | |
| // The first type field may be omitted | |
| { "type":"ETag", | |
| "id": "idsampledata", | |
| "refId": "refIdSampleData" | |
| } |
This file contains hidden or 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
| // Sample definition of thrift structure to test | |
| // scrooge (thrift) - argounaut (json) bijection | |
| // This is the most trivial example, since | |
| // there are no list<>, no ENUM, no external types | |
| namespace java com.xxx.services | |
| /** | |
| * Etag identifier that helps to | |
| * fetch most recent data from remote | |
| * while controlling local cache expiration. | |
| */ | |
| struct ETag { | |
| /** Etag id */ | |
| 1: string id | |
| /** Identifier of the referenced data */ | |
| 2: string refId | |
| /** Modification date (2014-06-13T12:00) of the target item referenced by id */ | |
| 3: optional string modifiedDate | |
| /** Expiration date (2014-06-14T12:00) after which client is expected to refetched the data */ | |
| 4: optional string expiresDate | |
| /** Hours (+1h), days(+2d), or minutes(+3m) after which the data needs to be updated. */ | |
| 5: optional string expiresPeriod | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment