// ĠCopyright Ġ 2 0 2 0 ĠSt rix py rr Ċ // Ċ // ĠLicensed Ġunder Ġthe ĠApache ĠLicense , ĠVersion Ġ 2 . 0 Ġ( the Ġ" License "); Ċ // Ġyou Ġmay Ġnot Ġuse Ġthis Ġfile Ġexcept Ġin Ġcompliance Ġwith Ġthe ĠLicense . Ċ // ĠYou Ġmay Ġobtain Ġa Ġcopy Ġof Ġthe ĠLicense Ġat Ċ // Ċ // ĠĠĠĠ Ġhttp :// www . apache . org / licenses / LICENSE - 2 . 0 Ċ // Ċ // ĠUnless Ġrequired Ġby Ġapplicable Ġlaw Ġor Ġagreed Ġto Ġin Ġwriting , Ġsoftware Ċ // Ġdistributed Ġunder Ġthe ĠLicense Ġis Ġdistributed Ġon Ġan Ġ" AS ĠIS " ĠBASIS , Ċ // ĠWITHOUT ĠWARRANTIES ĠOR ĠCONDITIONS ĠOF ĠANY ĠKIND , Ġeither Ġexpress Ġor Ġimplied . Ċ // ĠSee Ġthe ĠLicense Ġfor Ġthe Ġspecific Ġlanguage Ġgoverning Ġpermissions Ġand Ċ // Ġlimitations Ġunder Ġthe ĠLicense . Ċ package Ġst rix py rr . specular . models . factory Ċ Ċ import Ġst rix py rr . specular . is Derived From Ċ import Ġst rix py rr . specular . models . annotations . Attribute Annotation Ċ import Ġst rix py rr . specular . models . annotations . Attribute Label Ċ import Ġst rix py rr . specular . models . annotations . AttributeValue Ċ import Ġst rix py rr . specular . models . building . I Attribute Container Builder Ċ import Ġst rix py rr . specular . models . factory . Annotation Transformer . Attribute Provider Ċ import Ġst rix py rr . specular . models . factory . internal . enum Fields Ċ import Ġkotlin . reflect . K Annotated Element Ċ import Ġkotlin . reflect . K Class Ċ import Ġkotlin . reflect . K Property 1 Ċ import Ġkotlin . reflect . full .* Ċ Ċ /** Ċ Ġ* ĠTrans forms Ġa Ġ[ Annotation ] Ġinto Ġan Ġ[ Attribute Provider ], Ġwhich Ġreturns Ġattributes Ċ Ġ* Ġfrom Ġ[ Annotation ] s Ġto Ġbe Ġmanip ulated Ġby Ġa Ġmodel . Ċ Ġ* Ġ@ since Ġ 0 . 5 Ċ Ġ*/ Ċ open Ġclass ĠAnnotation Transformer Ċ { Ċ ĉ private Ġval Ġattribute Lookup Ġ= ĠHashMap < K Class <* >, ĠAnnotation . () Ġ-> ĠAny ? >( 1 6 ); ĊĉĊ ĉ // ĠOk , Ġthe Ġ" in " Ġsyntax Ġis Ġe pic . Ċ ĉ fun Ġis Attribute ( annotation Type : ĠK Class < out ĠAnnotation >) Ġ= Ċĉ ĉ annotation Type Ġin Ġattribute Lookup Ġ|| Ċĉ ĉ annotation Type Ċĉĉ ĉ . has Annotation < Attribute Annotation >(); ĊĉĊ ĉ open Ġfun Ġ< L Ġ: ĠAny > Ġtransform ( Ċĉ ĉ annotated : ĠK Annotated Element , Ċĉ ĉ label Type : ĠK Class < L >, Ċĉ ĉ builder : ĠI Attribute Container Builder < L > Ċ ĉ ) Ġ= Ġtransform ( annotated . annotations , Ġlabel Type , Ġbuilder ); ĊĉĊ ĉ @ Suppress (" UN CHECK ED _ CAST ") Ċ ĉ open Ġfun Ġ< L Ġ: ĠAny > Ġtransform ( Ċĉ ĉ annotations : ĠList < Annotation >, Ċĉ ĉ label Type : ĠK Class < L >, Ċĉ ĉ builder : ĠI Attribute Container Builder < L > Ċ ĉ ) Ċ ĉ { Ċĉ ĉ for Ġ( annotation Ġin Ġannotations ) Ċĉ ĉ { Ċĉĉ ĉ val Ġtype Ġ= Ġannotation . annotation Class ; ĊĉĉĉĊĉĉ ĉ if Ġ( is Attribute ( type )) Ċĉĉ ĉ { Ċĉĉĉ ĉ val Ġlabel Ġ= Ġget Label ( type , Ġlabel Type ) Ġ?: Ġthrow ĠException (" A Ġsuitable Ġlabel Ġcould Ġnot Ġbe Ġfound ."); ĊĉĉĉĉĊĉĉĉ ĉ builder [ label ] Ġ= Ġannotation . getValue ( type ); Ċĉĉ ĉ } Ċĉ ĉ } Ċ ĉ } ĊĉĊ ĉ protected Ġopen Ġfun Ġ< L Ġ: ĠAny > Ġget Label ( type : ĠK Class < out ĠAnnotation >, Ġlabel Type : ĠK Class < L >): ĠL ? Ċ ĉ { Ċĉ ĉ val Ġname Ġ= Ġlabel Type . safe Cast ( type . simple Name ); ĊĉĉĊĉ ĉ if Ġ( name Ġ!= Ġnull ) Ġreturn Ġname ; ĊĉĉĊĉ ĉ if Ġ( label Type . is Derived From < Enum <* >> ()) Ċĉ ĉ { Ċĉĉ ĉ for Ġ( enum Ġin Ġlabel Type . enum Fields ) Ċĉĉ ĉ { Ċĉĉĉ ĉ val Ġcallback Type Ġ= Ġenum . find Annotation < Attribute Label >() ?. attribute ; ĊĉĉĉĉĊĉĉĉ ĉ // ĠIf Ġthe Ġannotation Ġpoints Ġback Ġto Ġthe Ġprovided Ġannotation Ġtype ... Ċĉĉĉ ĉ if Ġ( type Ġ== Ġcallback Type ) Ġreturn Ġlabel Type . cast ( enum ); Ċĉĉ ĉ } Ċĉ ĉ } ĊĉĉĊĉ ĉ if Ġ( label Type . is Se aled ) Ċĉ ĉ { Ċĉĉ ĉ TODO (" Se aled Ġclasses Ġare Ġnot Ġsupported Ġas Ġlabels Ġyet .") Ċĉ ĉ } ĊĉĉĊĉ ĉ return Ġnull ; Ċ ĉ } ĊĉĊ ĉ @ Suppress (" UN CHECK ED _ CAST ") Ċ ĉ protected Ġopen Ġfun ĠAnnotation . getValue ( type : ĠK Class < out ĠAnnotation >): ĠAny ? Ċ ĉ { Ċĉ ĉ val Ġget From Lookup Ġ= Ġattribute Lookup [ type ]; ĊĉĉĊĉ ĉ if Ġ( get From Lookup Ġ!= Ġnull ) Ġreturn Ġget From Lookup (); ĊĉĉĊĉ ĉ val Ġget Ġ= Ġ( getValue Property ( type )?. getter Ġ?: Ġ{ Ġtrue Ġ}) Ġas ĠAnnotation . () Ġ-> ĠAny ?; ĊĉĉĊĉ ĉ attribute Lookup [ type ] Ġ= Ġget ; ĊĉĉĊĉ ĉ return Ġget (); Ċ ĉ } ĊĉĊ ĉ protected Ġopen Ġfun ĠgetValue Property ( type : ĠK Class < out ĠAnnotation >): ĠK Property 1 < out ĠAnnotation , Ġ* >? Ċ ĉ { Ċĉ ĉ val Ġparameters Ġ= Ġtype . member Properties ; ĊĉĉĊĉ ĉ for Ġ( parameter Ġin Ġparameters ) Ċĉĉ ĉ if Ġ( parameter . has Annotation < AttributeValue >()) Ċĉĉĉ ĉ return Ġparameter ; ĊĉĉĊĉ ĉ return Ġparameters . find Ġ{ Ġit . name Ġ== Ġ" value " Ġ}; Ċ ĉ } ĊĉĊ ĉ // ĠTODO : ĠRemove Ġbelow Ġthis Ġline . ĊĉĊ ĉ inline Ġfun Ġ< re ified ĠA Ġ: ĠAnnotation , ĠL > Ġtransform ( label : ĠL ) Ġ= Ġtransform ( A :: class , Ġlabel ); ĊĉĊ ĉ open Ġfun Ġ< A Ġ: ĠAnnotation , ĠL > Ġtransform ( annotation Type : ĠK Class < A >, Ġlabel : ĠL ): ĠI Attribute Provider < A , ĠL > Ċ ĉ { Ċĉ ĉ val Ġproperties Ġ= Ġannotation Type . member Properties ; Ċĉ ĉ val Ġproperty Ġ= Ġproperties . find Ġ{ ĊĉĉĉĉĉĉĠĠ Ġit . has Annotation < AttributeValue >() ĊĉĉĉĉĉĠĠ Ġ} Ġ?: Ġproperties . find Ġ{ Ċĉĉĉĉĉĉĉ ĉ it . name Ġ== Ġ" value " Ċĉĉĉĉĉĉ ĉ }; ĊĉĉĊĉ ĉ return Ġif Ġ( property Ġ!= Ġnull ) Ċĉĉ ĉ transform ( annotation Type , Ġlabel , Ġproperty :: get ); Ċĉ ĉ else Ġtransform ( annotation Type , Ġlabel ) Ġ{ Ġtrue Ġ}; Ċ ĉ } ĊĉĊ ĉ inline Ġfun Ġ< re ified ĠA Ġ: ĠAnnotation , ĠL > Ġtransform ( Ċĉ ĉ label : ĠL , Ċĉ ĉ no inline Ġvalue : ĠA . () Ġ-> ĠAny ? Ċ ĉ ) Ġ= Ġtransform ( A :: class , Ġlabel , Ġvalue ); ĊĉĊ ĉ open Ġfun Ġ< A Ġ: ĠAnnotation , ĠL > Ġtransform ( Ċĉ ĉ annotation Type : ĠK Class < A >, Ċĉ ĉ label : ĠL , Ċĉ ĉ value : ĠA . () Ġ-> ĠAny ? Ċ ĉ ): ĠI Attribute Provider < A , ĠL > Ċĉ ĉ = ĠAttribute Provider ( annotation Type , Ġlabel , Ġvalue ); ĊĉĊ ĉ protected Ġclass ĠAttribute Provider < A Ġ: ĠAnnotation , ĠL >( Ċĉ ĉ override Ġval Ġtype : ĠK Class < A >, Ċĉ ĉ override Ġval Ġlabel : ĠL , Ċĉ ĉ private Ġval Ġvalue : ĠA . () Ġ-> ĠAny ? Ċ ĉ ): ĠI Attribute Provider < A , ĠL > Ċ ĉ { Ċĉ ĉ override Ġfun ĠgetValue ( annotation : ĠA ) Ġ= Ġannotation . value (); Ċ ĉ } Ċ } Ċ Ċ /** Ċ Ġ* Ġ@ since Ġ 0 . 5 Ċ Ġ*/ Ċ interface ĠI Attribute Provider < A Ġ: ĠAnnotation , ĠL > Ċ { Ċ ĉ val Ġtype : ĠK Class < A >; Ċ ĉ val Ġlabel : ĠL ; ĊĉĊ ĉ fun ĠgetValue ( annotation : ĠA ): ĠAny ?; Ċ }