I was trying to serialize/deserialize JSON using GSON. The payload in question is ApiGatewayAuthorizerContext
. Inside it, there is a HashMap<String, String>
. But when doing from/to json
, the field naming strategy is not applied to the Keys.
@JsonIgnoreProperties(ignoreUnknown = true)
public class ApiGatewayAuthorizerContext {
//-------------------------------------------------------------
// Variables - Private
//-------------------------------------------------------------
private Map<String, String> contextProperties = new HashMap<>();
private String principalId;
private CognitoAuthorizerClaims claims;
}
Same with MultiValuedTreeMap<String, String>
in AwsProxyRequest
class too, which is a MultivaluedMap<Key, Value>
.
My field naming strategy is simple, replace -
with _
, for example, the payload below is not a valid JSON for many downstream components I use, and want to replace all '-', with '_'.
"MultiValueHeaders": {
"Accept": [
"application/json, text/plain, */*"
],
"Authorization": [
"Bearer ey...b9w"
],
"Content-Type": [
"application/json;charset=utf-8"
],
"Host": [
"aws-us-east-1-dev-dws-api.xxxxxxxx.com"
],
"User-Agent": [
"axios/0.20.0"
],
"X-Amzn-Trace-Id": [
"Root=1-xxxxxxxx-xxxxxxxxxxxxxxxx"
],
"X-Forwarded-For": [
"127.0.232.171"
],
"X-Forwarded-Port": [
"443"
],
"X-Forwarded-Proto": [
"https"
]
},
Any idea?
EDIT: Adding Field Naming Strategy.
public class ApiEventNamingStrategy implements FieldNamingStrategy {
/**
* Translates the field name into its {@link FieldNamingPolicy.UPPER_CAMEL_CASE} representation.
*
* @param field the field object that we are translating
* @return the translated field name.
*/
public String translateName(Field field) {
String fieldName = FieldNamingPolicy.UPPER_CAMEL_CASE.translateName(field);
if (fieldName.contains("-")) {
fieldName = fieldName.replace('-', '_');
}
return fieldName;
}
}
which is used to setFieldNamingStrategy
as shown below,
private static Gson gson =
(new GsonBuilder()).setFieldNamingStrategy(new ApiEventNamingStrategy()).create();
The result is, all the member variables other than the ones inside the Map
gets checked, and renamed. Seems setFieldNamingStrategy
wont look inside a Map
and rename the Keys
.
Now I'm looking at the registering a TypeAdapter
by utilizing registerTypeAdapterFactory
. Seems the the answer by @linfaxin here gson-wont-properly-serialise-a-class-that-extends-hashmap would come to rescue! But the problem is, where/how to and/or the right place to introduce the field naming strategy in the RetainFieldMapFactory
class, becasue I see a lot of avenues to hack it in.
Any ideas are most welcome!
btw, the values are populated by AWS APIGateway
AND a custom authorization lambda. No way I think I could change the behavior of the APIGateway
.