1 /* 2 * Copyright (C) 2008 Google Inc. 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.google.gson; 18 19 import com.google.gson.internal.Streams; 20 import com.google.gson.stream.JsonWriter; 21 import java.io.IOException; 22 import java.io.StringWriter; 23 import java.math.BigDecimal; 24 import java.math.BigInteger; 25 26 /** 27 * A class representing an element of JSON. It could either be a {@link JsonObject}, a 28 * {@link JsonArray}, a {@link JsonPrimitive} or a {@link JsonNull}. 29 * 30 * @author Inderjeet Singh 31 * @author Joel Leitch 32 */ 33 public abstract class JsonElement { 34 /** 35 * @deprecated Creating custom {@code JsonElement} subclasses is highly discouraged 36 * and can lead to undefined behavior.<br> 37 * This constructor is only kept for backward compatibility. 38 */ 39 @Deprecated JsonElement()40 public JsonElement() { 41 } 42 43 /** 44 * Returns a deep copy of this element. Immutable elements like primitives 45 * and nulls are not copied. 46 * 47 * @since 2.8.2 48 */ deepCopy()49 public abstract JsonElement deepCopy(); 50 51 /** 52 * Provides a check for verifying if this element is a JSON array or not. 53 * 54 * @return true if this element is of type {@link JsonArray}, false otherwise. 55 */ isJsonArray()56 public boolean isJsonArray() { 57 return this instanceof JsonArray; 58 } 59 60 /** 61 * Provides a check for verifying if this element is a JSON object or not. 62 * 63 * @return true if this element is of type {@link JsonObject}, false otherwise. 64 */ isJsonObject()65 public boolean isJsonObject() { 66 return this instanceof JsonObject; 67 } 68 69 /** 70 * Provides a check for verifying if this element is a primitive or not. 71 * 72 * @return true if this element is of type {@link JsonPrimitive}, false otherwise. 73 */ isJsonPrimitive()74 public boolean isJsonPrimitive() { 75 return this instanceof JsonPrimitive; 76 } 77 78 /** 79 * Provides a check for verifying if this element represents a null value or not. 80 * 81 * @return true if this element is of type {@link JsonNull}, false otherwise. 82 * @since 1.2 83 */ isJsonNull()84 public boolean isJsonNull() { 85 return this instanceof JsonNull; 86 } 87 88 /** 89 * Convenience method to get this element as a {@link JsonObject}. If this element is of some 90 * other type, an {@link IllegalStateException} will result. Hence it is best to use this method 91 * after ensuring that this element is of the desired type by calling {@link #isJsonObject()} 92 * first. 93 * 94 * @return this element as a {@link JsonObject}. 95 * @throws IllegalStateException if this element is of another type. 96 */ getAsJsonObject()97 public JsonObject getAsJsonObject() { 98 if (isJsonObject()) { 99 return (JsonObject) this; 100 } 101 throw new IllegalStateException("Not a JSON Object: " + this); 102 } 103 104 /** 105 * Convenience method to get this element as a {@link JsonArray}. If this element is of some 106 * other type, an {@link IllegalStateException} will result. Hence it is best to use this method 107 * after ensuring that this element is of the desired type by calling {@link #isJsonArray()} 108 * first. 109 * 110 * @return this element as a {@link JsonArray}. 111 * @throws IllegalStateException if this element is of another type. 112 */ getAsJsonArray()113 public JsonArray getAsJsonArray() { 114 if (isJsonArray()) { 115 return (JsonArray) this; 116 } 117 throw new IllegalStateException("Not a JSON Array: " + this); 118 } 119 120 /** 121 * Convenience method to get this element as a {@link JsonPrimitive}. If this element is of some 122 * other type, an {@link IllegalStateException} will result. Hence it is best to use this method 123 * after ensuring that this element is of the desired type by calling {@link #isJsonPrimitive()} 124 * first. 125 * 126 * @return this element as a {@link JsonPrimitive}. 127 * @throws IllegalStateException if this element is of another type. 128 */ getAsJsonPrimitive()129 public JsonPrimitive getAsJsonPrimitive() { 130 if (isJsonPrimitive()) { 131 return (JsonPrimitive) this; 132 } 133 throw new IllegalStateException("Not a JSON Primitive: " + this); 134 } 135 136 /** 137 * Convenience method to get this element as a {@link JsonNull}. If this element is of some 138 * other type, an {@link IllegalStateException} will result. Hence it is best to use this method 139 * after ensuring that this element is of the desired type by calling {@link #isJsonNull()} 140 * first. 141 * 142 * @return this element as a {@link JsonNull}. 143 * @throws IllegalStateException if this element is of another type. 144 * @since 1.2 145 */ getAsJsonNull()146 public JsonNull getAsJsonNull() { 147 if (isJsonNull()) { 148 return (JsonNull) this; 149 } 150 throw new IllegalStateException("Not a JSON Null: " + this); 151 } 152 153 /** 154 * Convenience method to get this element as a boolean value. 155 * 156 * @return this element as a primitive boolean value. 157 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 158 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 159 * more than a single element. 160 */ getAsBoolean()161 public boolean getAsBoolean() { 162 throw new UnsupportedOperationException(getClass().getSimpleName()); 163 } 164 165 /** 166 * Convenience method to get this element as a {@link Number}. 167 * 168 * @return this element as a {@link Number}. 169 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}, 170 * or cannot be converted to a number. 171 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 172 * more than a single element. 173 */ getAsNumber()174 public Number getAsNumber() { 175 throw new UnsupportedOperationException(getClass().getSimpleName()); 176 } 177 178 /** 179 * Convenience method to get this element as a string value. 180 * 181 * @return this element as a string value. 182 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 183 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 184 * more than a single element. 185 */ getAsString()186 public String getAsString() { 187 throw new UnsupportedOperationException(getClass().getSimpleName()); 188 } 189 190 /** 191 * Convenience method to get this element as a primitive double value. 192 * 193 * @return this element as a primitive double value. 194 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 195 * @throws NumberFormatException if the value contained is not a valid double. 196 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 197 * more than a single element. 198 */ getAsDouble()199 public double getAsDouble() { 200 throw new UnsupportedOperationException(getClass().getSimpleName()); 201 } 202 203 /** 204 * Convenience method to get this element as a primitive float value. 205 * 206 * @return this element as a primitive float value. 207 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 208 * @throws NumberFormatException if the value contained is not a valid float. 209 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 210 * more than a single element. 211 */ getAsFloat()212 public float getAsFloat() { 213 throw new UnsupportedOperationException(getClass().getSimpleName()); 214 } 215 216 /** 217 * Convenience method to get this element as a primitive long value. 218 * 219 * @return this element as a primitive long value. 220 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 221 * @throws NumberFormatException if the value contained is not a valid long. 222 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 223 * more than a single element. 224 */ getAsLong()225 public long getAsLong() { 226 throw new UnsupportedOperationException(getClass().getSimpleName()); 227 } 228 229 /** 230 * Convenience method to get this element as a primitive integer value. 231 * 232 * @return this element as a primitive integer value. 233 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 234 * @throws NumberFormatException if the value contained is not a valid integer. 235 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 236 * more than a single element. 237 */ getAsInt()238 public int getAsInt() { 239 throw new UnsupportedOperationException(getClass().getSimpleName()); 240 } 241 242 /** 243 * Convenience method to get this element as a primitive byte value. 244 * 245 * @return this element as a primitive byte value. 246 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 247 * @throws NumberFormatException if the value contained is not a valid byte. 248 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 249 * more than a single element. 250 * @since 1.3 251 */ getAsByte()252 public byte getAsByte() { 253 throw new UnsupportedOperationException(getClass().getSimpleName()); 254 } 255 256 /** 257 * Convenience method to get the first character of the string value of this element. 258 * 259 * @return the first character of the string value. 260 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}, 261 * or if its string value is empty. 262 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 263 * more than a single element. 264 * @since 1.3 265 * @deprecated This method is misleading, as it does not get this element as a char but rather as 266 * a string's first character. 267 */ 268 @Deprecated getAsCharacter()269 public char getAsCharacter() { 270 throw new UnsupportedOperationException(getClass().getSimpleName()); 271 } 272 273 /** 274 * Convenience method to get this element as a {@link BigDecimal}. 275 * 276 * @return this element as a {@link BigDecimal}. 277 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 278 * @throws NumberFormatException if this element is not a valid {@link BigDecimal}. 279 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 280 * more than a single element. 281 * @since 1.2 282 */ getAsBigDecimal()283 public BigDecimal getAsBigDecimal() { 284 throw new UnsupportedOperationException(getClass().getSimpleName()); 285 } 286 287 /** 288 * Convenience method to get this element as a {@link BigInteger}. 289 * 290 * @return this element as a {@link BigInteger}. 291 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 292 * @throws NumberFormatException if this element is not a valid {@link BigInteger}. 293 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 294 * more than a single element. 295 * @since 1.2 296 */ getAsBigInteger()297 public BigInteger getAsBigInteger() { 298 throw new UnsupportedOperationException(getClass().getSimpleName()); 299 } 300 301 /** 302 * Convenience method to get this element as a primitive short value. 303 * 304 * @return this element as a primitive short value. 305 * @throws UnsupportedOperationException if this element is not a {@link JsonPrimitive} or {@link JsonArray}. 306 * @throws NumberFormatException if the value contained is not a valid short. 307 * @throws IllegalStateException if this element is of the type {@link JsonArray} but contains 308 * more than a single element. 309 */ getAsShort()310 public short getAsShort() { 311 throw new UnsupportedOperationException(getClass().getSimpleName()); 312 } 313 314 /** 315 * Returns a String representation of this element. 316 */ 317 @Override toString()318 public String toString() { 319 try { 320 StringWriter stringWriter = new StringWriter(); 321 JsonWriter jsonWriter = new JsonWriter(stringWriter); 322 jsonWriter.setLenient(true); 323 Streams.write(this, jsonWriter); 324 return stringWriter.toString(); 325 } catch (IOException e) { 326 throw new AssertionError(e); 327 } 328 } 329 } 330