001/* 002 * ============================================================================ 003 * Copyright © 2002-2026 by Thomas Thrien. 004 * All Rights Reserved. 005 * ============================================================================ 006 * Licensed to the public under the agreements of the GNU Lesser General Public 007 * License, version 3.0 (the "License"). You may obtain a copy of the License at 008 * 009 * http://www.gnu.org/licenses/lgpl.html 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 013 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 014 * License for the specific language governing permissions and limitations 015 * under the License. 016 */ 017 018package org.tquadrat.foundation.jsonbuilder; 019 020import static org.apiguardian.api.API.Status.STABLE; 021 022import java.util.Formattable; 023import java.util.Formatter; 024 025import org.apiguardian.api.API; 026import org.tquadrat.foundation.annotation.ClassVersion; 027 028/** 029 * <p>{@summary This interface describes the base for all the JSON 030 * datatypes.}</p> 031 * <p>{@code JSONValue} implements 032 * {@link Formattable} 033 * for the implementation of pretty-printed output through 034 * {@code String.format( "%s", value )} or similar.</p> 035 * <p>{@link #formatTo(Formatter,int,int,int)} 036 * ignores the arguments {@code flags} and {@code precision}, while the 037 * {@code width} argument is used internally. Therefore, a call like 038 * {@code String.format( "%10s", value )} may result in some unexpected 039 * output.</p> 040 * 041 * @extauthor Thomas Thrien - thomas.thrien@tquadrat.org 042 * @version $Id: JSONValue.java 1258 2026-06-04 18:33:06Z tquadrat $ 043 * @since 0.25.0 044 * 045 * @UMLGraph.link 046 */ 047@ClassVersion( sourceVersion = "$Id: JSONValue.java 1258 2026-06-04 18:33:06Z tquadrat $" ) 048@API( status = STABLE, since = "0.25.0" ) 049public sealed interface JSONValue extends Formattable 050 permits JSONArray, JSONLiteral, JSONNumber, JSONObject, JSONString 051{ 052 /*---------*\ 053 ====** Methods **========================================================== 054 \*---------*/ 055 /** 056 * <p>{@summary Returns this JSON value as 057 * {@link JSONArray}, 058 * assuming that this value represents a JSON array.} If this is not the 059 * case, an 060 * {@link IllegalStateException} 061 * is thrown. 062 * 063 * @return This {@code JSONValue} instance as a 064 * {@link JSONArray}. 065 * @throws IllegalStateException This JSON value is not a JSON array. 066 */ 067 @SuppressWarnings( "ClassReferencesSubclass" ) 068 public default JSONArray asArray() 069 { 070 if( !isArray() ) throw new IllegalStateException( "Not a JSONArray: %s".formatted( this.toString() ) ); 071 072 //---* Done *---------------------------------------------------------- 073 return (JSONArray) this; 074 } // asArray() 075 076 /** 077 * <p>{@summary Returns this JSON value as 078 * {@linkplain JSONLiteral JSON literals} 079 * {@link JSONLiteral#FALSE false} 080 * or 081 * {@link JSONLiteral#TRUE true}, 082 * assuming that this value represents a JSON Boolean.} If this is not the 083 * case, an 084 * {@link IllegalStateException} 085 * is thrown. 086 * 087 * @return This {@code JSONValue} instance as a 088 * {@link JSONLiteral}. 089 * @throws IllegalStateException This JSON value is not a JSON Boolean. 090 */ 091 @SuppressWarnings( "ClassReferencesSubclass" ) 092 public default JSONLiteral asBoolean() 093 { 094 if( !isBoolean() ) throw new IllegalStateException( "Not a JSON Boolean: %s".formatted( this.toString() ) ); 095 096 //---* Done *---------------------------------------------------------- 097 return (JSONLiteral) this; 098 } // asBoolean() 099 100 /** 101 * <p>{@summary Returns this JSON value as 102 * {@link JSONNumber}, 103 * assuming that this value represents a JSON number.} If this is not the 104 * case, an 105 * {@link IllegalStateException} 106 * is thrown. 107 * 108 * @return This {@code JSONValue} instance as a 109 * {@link JSONNumber}. 110 * @throws IllegalStateException This JSON value is not a JSON String. 111 */ 112 @SuppressWarnings( "ClassReferencesSubclass" ) 113 public default JSONNumber asNumber() 114 { 115 if( !isNumber() ) throw new IllegalStateException( "Not a JSONNumber: %s".formatted( this.toString() ) ); 116 117 //---* Done *---------------------------------------------------------- 118 return (JSONNumber) this; 119 } // asNumber() 120 121 /** 122 * <p>{@summary Returns this JSON value as 123 * {@link JSONObject}, 124 * assuming that this value represents a JSON object.} If this is not the 125 * case, an 126 * {@link IllegalStateException} 127 * is thrown. 128 * 129 * @return This {@code JSONValue} instance as a 130 * {@link JSONObject}. 131 * @throws IllegalStateException This JSON value is not a JSON object. 132 */ 133 @SuppressWarnings( "ClassReferencesSubclass" ) 134 public default JSONObject asObject() 135 { 136 if( !isObject() ) throw new IllegalStateException( "Not a JSONObject: %s".formatted( this.toString() ) ); 137 138 //---* Done *---------------------------------------------------------- 139 return (JSONObject) this; 140 } // asObject() 141 142 /** 143 * <p>{@summary Returns this JSON value as 144 * {@link JSONString}, 145 * assuming that this value represents a JSON String.} If this is not the 146 * case, an 147 * {@link IllegalStateException} 148 * is thrown. 149 * 150 * @return This {@code JSONValue} instance as a 151 * {@link JSONString}. 152 * @throws IllegalStateException This JSON value is not a JSON String. 153 */ 154 @SuppressWarnings( "ClassReferencesSubclass" ) 155 public default JSONString asString() 156 { 157 if( !isString() ) throw new IllegalStateException( "Not a JSONString: %s".formatted( this.toString() ) ); 158 159 //---* Done *---------------------------------------------------------- 160 return (JSONString) this; 161 } // asString() 162 163 /** 164 * {@inheritDoc} 165 */ 166 @Override 167 public void formatTo( final Formatter formatter, final int flags, final int width, final int precision ); 168 169 /** 170 * <p>{@summary Detects whether this value represents a boolean 171 * value.}</p> 172 * 173 * @return {@true} if this value represents either the 174 * {@linkplain JSONLiteral JSON literal} 175 * {@link JSONLiteral#TRUE true} 176 * or 177 * {@link JSONLiteral#FALSE}. 178 */ 179 public default boolean isBoolean() { return false; } 180 181 /** 182 * <p>{@summary Detects whether this value represents a JSON array.} If 183 * this is the case, this value is an instance of 184 * {@link JSONArray}.</p> 185 * 186 * @return {@true} if this value is an instance of 187 * {@link JSONArray}, {@false} otherwise. 188 */ 189 @SuppressWarnings( {"InstanceofThis", "ClassReferencesSubclass"} ) 190 public default boolean isArray() { return this instanceof JSONArray; } 191 192 /** 193 * <p>{@summary Detects whether this value represents the JSON literal 194 * {@false}.}</p> 195 * 196 * @return {@true} if this value represents the 197 * {@linkplain JSONLiteral JSON literal} 198 * {@link JSONLiteral#FALSE false}. 199 */ 200 public default boolean isFalse() { return false; } 201 202 /** 203 * <p>{@summary Detects whether this value represents the JSON literal 204 * {@null}.} 205 * 206 * @return {@true} if this value represents the 207 * {@linkplain JSONLiteral JSON literal} 208 * {@link JSONLiteral#NULL null}. 209 */ 210 public default boolean isNull() { return false; } 211 212 /** 213 * <p>{@summary Detects whether this value represents a JSON number.} If 214 * this is the case, this value is an instance of 215 * {@link JSONNumber}.</p> 216 * 217 * @return {@true} if this value is an instance of 218 * {@link JSONObject}, {@false} otherwise. 219 */ 220 @SuppressWarnings( {"InstanceofThis", "ClassReferencesSubclass"} ) 221 public default boolean isNumber() { return this instanceof JSONNumber; } 222 223 /** 224 * <p>{@summary Detects whether this value represents a JSON object.} If 225 * this is the case, this value is an instance of 226 * {@link JSONObject}.</p> 227 * 228 * @return {@true} if this value is an instance of 229 * {@link JSONObject}, {@false} otherwise. 230 */ 231 @SuppressWarnings( {"InstanceofThis", "ClassReferencesSubclass"} ) 232 public default boolean isObject() { return this instanceof JSONObject; } 233 234 /** 235 * <p>{@summary Detects whether this value represents a JSON string.} If 236 * this is the case, this value is an instance of 237 * {@link JSONString}.</p> 238 * 239 * @return {@true} if this value is an instance of 240 * {@link JSONString}, {@false} otherwise. 241 */ 242 @SuppressWarnings( {"InstanceofThis", "ClassReferencesSubclass"} ) 243 public default boolean isString() { return this instanceof JSONString; } 244 245 /** 246 * <p>{@summary Detects whether this value represents the JSON literal 247 * {@true}.}</p> 248 * 249 * @return {@true} if this value represents the 250 * {@linkplain JSONLiteral JSON literal} 251 * {@link JSONLiteral#TRUE true}. 252 */ 253 public default boolean isTrue() { return false; } 254 255 /** 256 * {@inheritDoc} 257 */ 258 @Override 259 public String toString(); 260} 261// interface JSONValue 262 263/* 264 * End of File 265 */