/* * Copyright 2016 Sai Pullabhotla. * * 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 com.jmethods.catatumbo.mappers; import java.util.HashMap; import java.util.Map; import com.google.cloud.datastore.BooleanValue; import com.google.cloud.datastore.DoubleValue; import com.google.cloud.datastore.EntityValue; import com.google.cloud.datastore.FullEntity; import com.google.cloud.datastore.IncompleteKey; import com.google.cloud.datastore.KeyValue; import com.google.cloud.datastore.LatLng; import com.google.cloud.datastore.LatLngValue; import com.google.cloud.datastore.LongValue; import com.google.cloud.datastore.NullValue; import com.google.cloud.datastore.StringValue; import com.google.cloud.datastore.Value; import com.google.cloud.datastore.ValueBuilder; import com.jmethods.catatumbo.DatastoreKey; import com.jmethods.catatumbo.DefaultDatastoreKey; import com.jmethods.catatumbo.GeoLocation; import com.jmethods.catatumbo.Mapper; import com.jmethods.catatumbo.MappingException; /** * An implementation of {@link Mapper} for mapping select set of primitive/wrapper types to the * Cloud Datastore. The primary purpose if this mapper is to aid with mapping Lists, Sets and Maps * when the collections are not parameterized. * * @author Sai Pullabhotla * */ public class CatchAllMapper implements Mapper { /** * Singleton instance */ private static final CatchAllMapper INSTANCE = new CatchAllMapper(); /** * Creates a new instance of <code>CatchAllMapper</code>. */ private CatchAllMapper() { // Do nothing } /** * Returns the singleton instance of this mapper. * * @return the singleton instance of this mapper. */ public static Mapper getInstance() { return INSTANCE; } @Override public ValueBuilder<?, ?, ?> toDatastore(Object input) { ValueBuilder<?, ?, ?> builder; if (input == null) { builder = NullValue.newBuilder(); } else if (input instanceof Long) { builder = LongValue.newBuilder((long) input); } else if (input instanceof Double) { builder = DoubleValue.newBuilder((double) input); } else if (input instanceof Boolean) { builder = BooleanValue.newBuilder((boolean) input); } else if (input instanceof String) { builder = StringValue.newBuilder((String) input); } else if (input instanceof DatastoreKey) { builder = KeyValue.newBuilder(((DatastoreKey) input).nativeKey()); } else if (input instanceof GeoLocation) { GeoLocation geoLocation = (GeoLocation) input; builder = LatLngValue .newBuilder(LatLng.of(geoLocation.getLatitude(), geoLocation.getLongitude())); } else if (input instanceof Map) { @SuppressWarnings("unchecked") Map<String, ?> map = (Map<String, ?>) input; FullEntity.Builder<IncompleteKey> entityBuilder = FullEntity.newBuilder(); for (Map.Entry<String, ?> entry : map.entrySet()) { String key = entry.getKey(); entityBuilder.set(key, toDatastore(entry.getValue()).build()); } builder = EntityValue.newBuilder(entityBuilder.build()); } else { throw new MappingException(String.format("Unsupported type: %s", input.getClass().getName())); } return builder; } @Override public Object toModel(Value<?> input) { Object javaValue; if (input instanceof NullValue) { javaValue = null; } else if (input instanceof StringValue) { javaValue = input.get(); } else if (input instanceof LongValue) { javaValue = input.get(); } else if (input instanceof DoubleValue) { javaValue = input.get(); } else if (input instanceof BooleanValue) { javaValue = input.get(); } else if (input instanceof KeyValue) { javaValue = new DefaultDatastoreKey(((KeyValue) input).get()); } else if (input instanceof LatLngValue) { LatLng latLong = ((LatLngValue) input).get(); javaValue = new GeoLocation(latLong.getLatitude(), latLong.getLongitude()); } else if (input instanceof EntityValue) { EntityValue entityValue = (EntityValue) input; FullEntity<?> entity = entityValue.get(); Map<String, Object> map = new HashMap<>(); for (String property : entity.getNames()) { map.put(property, toModel(entity.getValue(property))); } javaValue = map; } else { throw new MappingException(String.format("Unsupported type %s", input.getClass().getName())); } return javaValue; } }