001package ca.uhn.fhir.parser.json; 002 003/* 004 * #%L 005 * HAPI FHIR - Core Library 006 * %% 007 * Copyright (C) 2014 - 2017 University Health Network 008 * %% 009 * Licensed under the Apache License, Version 2.0 (the "License"); 010 * you may not use this file except in compliance with the License. 011 * You may obtain a copy of the License at 012 * 013 * http://www.apache.org/licenses/LICENSE-2.0 014 * 015 * Unless required by applicable law or agreed to in writing, software 016 * distributed under the License is distributed on an "AS IS" BASIS, 017 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 018 * See the License for the specific language governing permissions and 019 * limitations under the License. 020 * #L% 021 */ 022 023import java.io.IOException; 024import java.io.Writer; 025import java.math.BigDecimal; 026import java.math.BigInteger; 027import java.util.Stack; 028 029import org.slf4j.Logger; 030import org.slf4j.LoggerFactory; 031 032import com.google.gson.stream.JsonWriter; 033 034public class GsonWriter extends JsonLikeWriter { 035 private static final Logger log = LoggerFactory.getLogger(GsonWriter.class); 036 037 private JsonWriter eventWriter; 038 private enum BlockType { 039 NONE, OBJECT, ARRAY 040 } 041 private BlockType blockType = BlockType.NONE; 042 private Stack<BlockType> blockStack = new Stack<BlockType>(); 043 044 public GsonWriter () { 045 super(); 046 } 047 public GsonWriter (Writer writer) { 048 setWriter(writer); 049 } 050 051 @Override 052 public JsonLikeWriter init() throws IOException { 053 eventWriter = new JsonWriter(getWriter()); 054 eventWriter.setSerializeNulls(true); 055 if (isPrettyPrint()) { 056 eventWriter.setIndent(" "); 057 } 058 blockType = BlockType.NONE; 059 blockStack.clear(); 060 return this; 061 } 062 063 @Override 064 public JsonLikeWriter flush() throws IOException { 065 if (blockType != BlockType.NONE) { 066 log.error("JsonLikeStreamWriter.flush() called but JSON document is not finished"); 067 } 068 eventWriter.flush(); 069 getWriter().flush(); 070 return this; 071 } 072 073 @Override 074 public void close() throws IOException { 075 eventWriter.close(); 076 getWriter().close(); 077 } 078 079 @Override 080 public JsonLikeWriter beginObject() throws IOException { 081 blockStack.push(blockType); 082 blockType = BlockType.OBJECT; 083 eventWriter.beginObject(); 084 return this; 085 } 086 087 @Override 088 public JsonLikeWriter beginArray() throws IOException { 089 blockStack.push(blockType); 090 blockType = BlockType.ARRAY; 091 eventWriter.beginArray(); 092 return this; 093 } 094 095 @Override 096 public JsonLikeWriter beginObject(String name) throws IOException { 097 blockStack.push(blockType); 098 blockType = BlockType.OBJECT; 099 eventWriter.name(name); 100 eventWriter.beginObject(); 101 return this; 102 } 103 104 @Override 105 public JsonLikeWriter beginArray(String name) throws IOException { 106 blockStack.push(blockType); 107 blockType = BlockType.ARRAY; 108 eventWriter.name(name); 109 eventWriter.beginArray(); 110 return this; 111 } 112 113 @Override 114 public JsonLikeWriter write(String value) throws IOException { 115 eventWriter.value(value); 116 return this; 117 } 118 119 @Override 120 public JsonLikeWriter write(BigInteger value) throws IOException { 121 eventWriter.value(value); 122 return this; 123 } 124 125 @Override 126 public JsonLikeWriter write(BigDecimal value) throws IOException { 127 eventWriter.value(value); 128 return this; 129 } 130 131 @Override 132 public JsonLikeWriter write(long value) throws IOException { 133 eventWriter.value(value); 134 return this; 135 } 136 137 @Override 138 public JsonLikeWriter write(double value) throws IOException { 139 eventWriter.value(value); 140 return this; 141 } 142 143 @Override 144 public JsonLikeWriter write(Boolean value) throws IOException { 145 eventWriter.value(value); 146 return this; 147 } 148 149 @Override 150 public JsonLikeWriter write(boolean value) throws IOException { 151 eventWriter.value(value); 152 return this; 153 } 154 155 @Override 156 public JsonLikeWriter writeNull() throws IOException { 157 eventWriter.nullValue(); 158 return this; 159 } 160 161 @Override 162 public JsonLikeWriter write(String name, String value) throws IOException { 163 eventWriter.name(name); 164 eventWriter.value(value); 165 return this; 166 } 167 168 @Override 169 public JsonLikeWriter write(String name, BigInteger value) throws IOException { 170 eventWriter.name(name); 171 eventWriter.value(value); 172 return this; 173 } 174 @Override 175 public JsonLikeWriter write(String name, BigDecimal value) throws IOException { 176 eventWriter.name(name); 177 eventWriter.value(value); 178 return this; 179 } 180 181 @Override 182 public JsonLikeWriter write(String name, long value) throws IOException { 183 eventWriter.name(name); 184 eventWriter.value(value); 185 return this; 186 } 187 188 @Override 189 public JsonLikeWriter write(String name, double value) throws IOException { 190 eventWriter.name(name); 191 eventWriter.value(value); 192 return this; 193 } 194 195 @Override 196 public JsonLikeWriter write(String name, Boolean value) throws IOException { 197 eventWriter.name(name); 198 eventWriter.value(value); 199 return this; 200 } 201 202 @Override 203 public JsonLikeWriter write(String name, boolean value) throws IOException { 204 eventWriter.name(name); 205 eventWriter.value(value); 206 return this; 207 } 208 209 @Override 210 public JsonLikeWriter writeNull(String name) throws IOException { 211 eventWriter.name(name); 212 eventWriter.nullValue(); 213 return this; 214 } 215 216 @Override 217 public JsonLikeWriter endObject() throws IOException { 218 if (blockType == BlockType.NONE) { 219 log.error("JsonLikeStreamWriter.endObject(); called with no active JSON document"); 220 } else { 221 if (blockType != BlockType.OBJECT) { 222 log.error("JsonLikeStreamWriter.endObject(); called outside a JSON object. (Use endArray() instead?)"); 223 eventWriter.endArray(); 224 } else { 225 eventWriter.endObject(); 226 } 227 blockType = blockStack.pop(); 228 } 229 return this; 230 } 231 232 @Override 233 public JsonLikeWriter endArray() throws IOException { 234 if (blockType == BlockType.NONE) { 235 log.error("JsonLikeStreamWriter.endArray(); called with no active JSON document"); 236 } else { 237 if (blockType != BlockType.ARRAY) { 238 log.error("JsonLikeStreamWriter.endArray(); called outside a JSON array. (Use endObject() instead?)"); 239 eventWriter.endObject(); 240 } else { 241 eventWriter.endArray(); 242 } 243 blockType = blockStack.pop(); 244 } 245 return this; 246 } 247 248 @Override 249 public JsonLikeWriter endBlock() throws IOException { 250 if (blockType == BlockType.NONE) { 251 log.error("JsonLikeStreamWriter.endBlock(); called with no active JSON document"); 252 } else { 253 if (blockType == BlockType.ARRAY) { 254 eventWriter.endArray(); 255 } else { 256 eventWriter.endObject(); 257 } 258 blockType = blockStack.pop(); 259 } 260 return this; 261 } 262 263}