2 * Copyright (c) 2014 Cisco Systems, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
8 package org.opendaylight.yangtools.yang.data.codec.gson;
10 import com.google.common.annotations.Beta;
11 import com.google.common.base.Preconditions;
12 import com.google.common.cache.CacheBuilder;
13 import com.google.common.cache.CacheLoader;
14 import com.google.common.cache.LoadingCache;
16 import org.opendaylight.yangtools.yang.data.impl.codec.TypeDefinitionAwareCodec;
17 import org.opendaylight.yangtools.yang.model.api.SchemaContext;
18 import org.opendaylight.yangtools.yang.model.api.TypeDefinition;
19 import org.opendaylight.yangtools.yang.model.api.type.LeafrefTypeDefinition;
20 import org.opendaylight.yangtools.yang.model.util.IdentityrefType;
21 import org.opendaylight.yangtools.yang.model.util.InstanceIdentifierType;
22 import org.slf4j.Logger;
23 import org.slf4j.LoggerFactory;
26 * Factory for creating JSON equivalents of codecs. Each instance of this object is bound to
27 * a particular {@link SchemaContext}, but can be reused by multiple {@link JSONNormalizedNodeStreamWriter}s.
30 public final class JSONCodecFactory {
31 private static final Logger LOG = LoggerFactory.getLogger(JSONCodecFactory.class);
32 private static final JSONCodec<Object> LEAFREF_DEFAULT_CODEC = new JSONLeafrefCodec();
33 private static final JSONCodec<Object> NULL_CODEC = new JSONCodec<Object>() {
35 public Object deserialize(final String input) {
40 public String serialize(final Object input) {
45 public boolean needQuotes() {
50 private static TypeDefinition<?> resolveBaseTypeFrom(final TypeDefinition<?> type) {
51 TypeDefinition<?> superType = type;
52 while (superType.getBaseType() != null) {
53 superType = superType.getBaseType();
58 private final LoadingCache<TypeDefinition<?>, JSONCodec<Object>> codecs =
59 CacheBuilder.newBuilder().softValues().build(new CacheLoader<TypeDefinition<?>, JSONCodec<Object>>() {
60 @SuppressWarnings("unchecked")
62 public JSONCodec<Object> load(final TypeDefinition<?> key) throws Exception {
63 final TypeDefinition<?> type = resolveBaseTypeFrom(key);
65 if (type instanceof InstanceIdentifierType) {
66 return (JSONCodec<Object>) iidCodec;
68 if (type instanceof IdentityrefType) {
69 return (JSONCodec<Object>) idrefCodec;
71 if (type instanceof LeafrefTypeDefinition) {
72 return LEAFREF_DEFAULT_CODEC;
75 final TypeDefinitionAwareCodec<Object, ? extends TypeDefinition<?>> codec = TypeDefinitionAwareCodec.from(type);
77 LOG.debug("Codec for type \"{}\" is not implemented yet.", type.getQName().getLocalName());
81 return AbstractJSONCodec.create(codec);
85 private final SchemaContext schemaContext;
86 private final JSONCodec<?> iidCodec;
87 private final JSONCodec<?> idrefCodec;
89 private JSONCodecFactory(final SchemaContext context) {
90 this.schemaContext = Preconditions.checkNotNull(context);
91 iidCodec = new JSONStringInstanceIdentifierCodec(context);
92 idrefCodec = new JSONStringIdentityrefCodec(context);
96 * Instantiate a new codec factory attached to a particular context.
98 * @param context SchemaContext to which the factory should be bound
99 * @return A codec factory instance.
101 public static JSONCodecFactory create(final SchemaContext context) {
102 return new JSONCodecFactory(context);
105 SchemaContext getSchemaContext() {
106 return schemaContext;
109 JSONCodec<Object> codecFor(final TypeDefinition<?> typeDefinition) {
110 return codecs.getUnchecked(typeDefinition);