@@ -22,6 +22,7 @@ internal class PhpDeserializer {
2222 private static readonly Dictionary < Type , Dictionary < string , PropertyInfo > > PropertyInfoCache = new ( ) ;
2323
2424 private static Dictionary < Type , Dictionary < string , FieldInfo > > FieldInfoCache { get ; set ; } = new ( ) ;
25+ private static Dictionary < Type , Dictionary < string , FieldInfo > > EnumInfoCache { get ; set ; } = new ( ) ;
2526
2627 public PhpDeserializer ( string input , PhpDeserializationOptions options ) {
2728 _options = options ;
@@ -58,6 +59,7 @@ public static void ClearTypeCache() {
5859 /// </summary>
5960 public static void ClearPropertyInfoCache ( ) {
6061 PropertyInfoCache . Clear ( ) ;
62+ EnumInfoCache . Clear ( ) ;
6163 }
6264
6365 private object DeserializeToken ( PhpSerializeToken token ) {
@@ -254,16 +256,32 @@ private object DeserializeTokenFromSimpleType(Type givenType, PhpSerializeToken
254256 return Enum . Parse ( targetType , token . Value ) ;
255257 }
256258
257- var foundFieldInfo = targetType
258- . GetFields ( )
259- . Select ( fieldInfo => new { fieldInfo , phpPropertyAttribute = fieldInfo . GetCustomAttribute < PhpPropertyAttribute > ( ) } )
260- . FirstOrDefault ( c => c . fieldInfo . Name == token . Value || c . phpPropertyAttribute != null && c . phpPropertyAttribute . Name == token . Value )
261- ? . fieldInfo ;
259+
260+ FieldInfo foundFieldInfo = null ;
261+ if ( this . _options . TypeCache . HasFlag ( TypeCacheFlag . PropertyInfo ) ) {
262+ if ( ! EnumInfoCache . ContainsKey ( targetType ) ) {
263+ EnumInfoCache . Add ( targetType , new ( ) ) ;
264+ }
265+ if ( EnumInfoCache [ targetType ] . ContainsKey ( token . Value ) ) {
266+ foundFieldInfo = EnumInfoCache [ targetType ] [ token . Value ] ;
267+ }
268+ }
262269
263270 if ( foundFieldInfo == null ) {
264- throw new DeserializationException (
265- $ "Exception encountered while trying to assign '{ token . Value } ' to type '{ targetType . Name } '. " +
266- $ "The value could not be matched to an enum member.") ;
271+ foundFieldInfo = targetType
272+ . GetFields ( )
273+ . Select ( fieldInfo => new { fieldInfo , phpPropertyAttribute = fieldInfo . GetCustomAttribute < PhpPropertyAttribute > ( ) } )
274+ . FirstOrDefault ( c => c . fieldInfo . Name == token . Value || c . phpPropertyAttribute != null && c . phpPropertyAttribute . Name == token . Value )
275+ ? . fieldInfo ;
276+ if ( this . _options . TypeCache . HasFlag ( TypeCacheFlag . PropertyInfo ) ) {
277+ EnumInfoCache [ targetType ] . Add ( token . Value , foundFieldInfo ) ;
278+ }
279+ }
280+
281+ if ( foundFieldInfo == null ) {
282+ throw new DeserializationException (
283+ $ "Exception encountered while trying to assign '{ token . Value } ' to type '{ targetType . Name } '. " +
284+ $ "The value could not be matched to an enum member.") ;
267285 }
268286
269287 return foundFieldInfo . GetRawConstantValue ( ) ;
0 commit comments