001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 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, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.apache.juneau.bean.swagger; 018 019import static org.apache.juneau.commons.utils.Shorts.*; 020import static org.apache.juneau.marshall.internal.ConverterUtils.*; 021 022import java.util.*; 023 024import org.apache.juneau.commons.collections.*; 025 026/** 027 * A metadata object that allows for more fine-tuned XML model definitions. 028 * 029 * <p> 030 * The Xml Object is a metadata object that allows for more fine-tuned XML model definitions in Swagger 2.0. When using 031 * arrays, XML element names are not inferred (for singular/plural forms) and the name property should be used to add 032 * that information. This object is used to control how schema properties are serialized to XML. 033 * 034 * <h5 class='section'>Swagger Specification:</h5> 035 * <p> 036 * The Xml Object is composed of the following fields: 037 * <ul class='spaced-list'> 038 * <li><c>name</c> (string) - Replaces the name of the element/attribute used for the described schema property 039 * <li><c>namespace</c> (string) - The URI of the namespace definition 040 * <li><c>prefix</c> (string) - The prefix to be used for the name 041 * <li><c>attribute</c> (boolean) - Declares whether the property definition translates to an attribute instead of an element 042 * <li><c>wrapped</c> (boolean) - May be used only for an array definition. Signifies whether the array is wrapped 043 * </ul> 044 * 045 * <h5 class='section'>Example:</h5> 046 * <p class='bjava'> 047 * <jc>// Construct using SwaggerBuilder.</jc> 048 * Xml <jv>xml</jv> = <jsm>xml</jsm>() 049 * .name(<js>"foo"</js>) 050 * .namespace(<js>"http://foo"</js>) 051 * 052 * <jc>// Serialize using JsonSerializer.</jc> 053 * String <jv>json</jv> = Json.<jsm>from</jsm>(<jv>xml</jv>); 054 * 055 * <jc>// Or just use toString() which does the same as above.</jc> 056 * <jv>json</jv> = <jv>xml</jv>.toString(); 057 * </p> 058 * <p class='bjson'> 059 * <jc>// Output</jc> 060 * { 061 * <js>"name"</js>: <js>"foo"</js>, 062 * <js>"namespace"</js>: <js>"http://foo"</js> 063 * } 064 * </p> 065 * 066 * <h5 class='section'>See Also:</h5><ul> 067 * <li class='link'><a class="doclink" href="https://swagger.io/specification/v2/#xml-object">Swagger 2.0 Specification > XML Object</a> 068 * <li class='link'><a class="doclink" href="https://swagger.io/docs/specification/2-0/describing-models/">Swagger Describing Models</a> 069 * <li class='link'><a class="doclink" href="https://juneau.apache.org/docs/topics/JuneauBeanSwagger2">juneau-bean-swagger-v2</a> 070 * </ul> 071 */ 072@SuppressWarnings({ 073 "java:S1192" // Duplicated literals (argument/property names) read more clearly inline than as constants 074}) 075public class Xml extends SwaggerElement { 076 077 private String name; 078 private String namespace; 079 private String prefix; 080 private Boolean attribute; 081 private Boolean wrapped; 082 083 /** 084 * Default constructor. 085 */ 086 public Xml() {} 087 088 /** 089 * Copy constructor. 090 * 091 * @param copyFrom The object to copy. 092 */ 093 public Xml(Xml copyFrom) { 094 super(copyFrom); 095 096 this.attribute = copyFrom.attribute; 097 this.name = copyFrom.name; 098 this.namespace = copyFrom.namespace; 099 this.prefix = copyFrom.prefix; 100 this.wrapped = copyFrom.wrapped; 101 } 102 103 /** 104 * Make a deep copy of this object. 105 * 106 * @return A deep copy of this object. 107 */ 108 public Xml copy() { 109 return new Xml(this); 110 } 111 112 @Override /* Overridden from SwaggerElement */ 113 public <T> T get(String property, Class<T> type) { 114 reqnn("property", property); 115 return switch (property) { 116 case "attribute" -> toType(getAttribute(), type); 117 case "name" -> toType(getName(), type); 118 case "namespace" -> toType(getNamespace(), type); 119 case "prefix" -> toType(getPrefix(), type); 120 case "wrapped" -> toType(getWrapped(), type); 121 default -> super.get(property, type); 122 }; 123 } 124 125 /** 126 * Bean property getter: <property>attribute</property>. 127 * 128 * <p> 129 * Declares whether the property definition translates to an attribute instead of an element. 130 * 131 * @return The property value, or <jk>null</jk> if it is not set. 132 */ 133 public Boolean getAttribute() { return attribute; } 134 135 /** 136 * Bean property getter: <property>name</property>. 137 * 138 * <p> 139 * The name of the element/attribute used for the described schema property. 140 * 141 * @return The property value, or <jk>null</jk> if it is not set. 142 */ 143 public String getName() { return name; } 144 145 /** 146 * Bean property getter: <property>namespace</property>. 147 * 148 * <p> 149 * The URL of the namespace definition. 150 * 151 * @return The property value, or <jk>null</jk> if it is not set. 152 */ 153 public String getNamespace() { return namespace; } 154 155 /** 156 * Bean property getter: <property>prefix</property>. 157 * 158 * <p> 159 * The prefix to be used for the name. 160 * 161 * @return The property value, or <jk>null</jk> if it is not set. 162 */ 163 public String getPrefix() { return prefix; } 164 165 /** 166 * Bean property getter: <property>wrapped</property>. 167 * 168 * <p> 169 * Signifies whether the array is wrapped (for example, 170 * <c><books><book/><book/><books></c>) or unwrapped 171 * (<c><book/><book/></c>). 172 * <br>The definition takes effect only when defined alongside <c>type</c> being <c>array</c> 173 * (outside the <c>items</c>). 174 * 175 * @return The property value, or <jk>null</jk> if it is not set. 176 */ 177 public Boolean getWrapped() { return wrapped; } 178 179 @Override /* Overridden from SwaggerElement */ 180 public Set<String> keySet() { 181 // @formatter:off 182 var s = stb(String.class) 183 .addIf(nn(attribute), "attribute") 184 .addIf(nn(name), "name") 185 .addIf(nn(namespace), "namespace") 186 .addIf(nn(prefix), "prefix") 187 .addIf(nn(wrapped), "wrapped") 188 .build(); 189 // @formatter:on 190 return new MultiSet<>(s, super.keySet()); 191 } 192 193 @Override /* Overridden from SwaggerElement */ 194 public Xml set(String property, Object value) { 195 reqnn("property", property); 196 return switch (property) { 197 case "attribute" -> setAttribute(toBoolean(value)); 198 case "name" -> setName(s(value)); 199 case "namespace" -> setNamespace(s(value)); 200 case "prefix" -> setPrefix(s(value)); 201 case "wrapped" -> setWrapped(toBoolean(value)); 202 default -> { 203 super.set(property, value); 204 yield this; 205 } 206 }; 207 } 208 209 /** 210 * Bean property setter: <property>attribute</property>. 211 * 212 * <p> 213 * Declares whether the property definition translates to an attribute instead of an element. 214 * 215 * @param value 216 * The new value for this property. 217 * <br>Default value is <jk>false</jk>. 218 * <br>Can be <jk>null</jk> to unset the property. 219 * @return This object. 220 */ 221 public Xml setAttribute(Boolean value) { 222 attribute = value; 223 return this; 224 } 225 226 /** 227 * Bean property setter: <property>name</property>. 228 * 229 * <p> 230 * The name of the element/attribute used for the described schema property. 231 * 232 * @param value 233 * The new value for this property. 234 * <br>Can be <jk>null</jk> to unset the property. 235 * @return This object. 236 */ 237 public Xml setName(String value) { 238 name = value; 239 return this; 240 } 241 242 /** 243 * Bean property setter: <property>namespace</property>. 244 * 245 * <p> 246 * The URL of the namespace definition. 247 * 248 * @param value 249 * The new value for this property. 250 * <br>Can be <jk>null</jk> to unset the property. 251 * @return This object. 252 */ 253 public Xml setNamespace(String value) { 254 namespace = value; 255 return this; 256 } 257 258 /** 259 * Bean property setter: <property>prefix</property>. 260 * 261 * <p> 262 * The prefix to be used for the name. 263 * 264 * @param value 265 * The new value for this property. 266 * <br>Can be <jk>null</jk> to unset the property. 267 * @return This object. 268 */ 269 public Xml setPrefix(String value) { 270 prefix = value; 271 return this; 272 } 273 274 /** 275 * Bean property setter: <property>wrapped</property>. 276 * 277 * 278 * <p> 279 * Signifies whether the array is wrapped (for example, 280 * <c><books><book/><book/><books></c>) or unwrapped 281 * (<c><book/><book/></c>). 282 * <br>The definition takes effect only when defined alongside <c>type</c> being <c>array</c> 283 * (outside the <c>items</c>). 284 * 285 * @param value 286 * The new value for this property. 287 * <br>Can be <jk>null</jk> to unset the property. 288 * @return This object. 289 */ 290 public Xml setWrapped(Boolean value) { 291 wrapped = value; 292 return this; 293 } 294 295 /** 296 * Sets strict mode on this bean. 297 * 298 * @return This object. 299 */ 300 @Override 301 public Xml strict() { 302 super.strict(); 303 return this; 304 } 305 306 /** 307 * Sets strict mode on this bean. 308 * 309 * @param value 310 * The new value for this property. 311 * <br>Non-boolean values will be converted to boolean using <code>Boolean.<jsm>valueOf</jsm>(value.toString())</code>. 312 * <br>Can be <jk>null</jk> (interpreted as <jk>false</jk>). 313 * @return This object. 314 */ 315 @Override 316 public Xml strict(Object value) { 317 super.strict(value); 318 return this; 319 } 320}