001package com.box.sdk; 002 003import java.net.URL; 004import java.util.ArrayList; 005import java.util.List; 006 007import com.eclipsesource.json.JsonObject; 008import com.eclipsesource.json.JsonValue; 009 010/** 011 * The MetadataTemplate class represents the Box metadata template object. 012 * Templates allow the metadata service to provide a multitude of services, 013 * such as pre-defining sets of key:value pairs or schema enforcement on specific fields. 014 * 015 * @see <a href="https://docs.box.com/reference#metadata-templates">Box metadata templates</a> 016 */ 017public class MetadataTemplate extends BoxJSONObject { 018 019 /** 020 * @see #getMetadataTemplate(BoxAPIConnection) 021 */ 022 private static final URLTemplate METADATA_TEMPLATE_URL_TEMPLATE 023 = new URLTemplate("metadata_templates/%s/%s/schema"); 024 025 /** 026 * @see #getEnterpriseMetadataTemplates(String, int, BoxAPIConnection, String...) 027 */ 028 private static final URLTemplate ENTERPRISE_METADATA_URL_TEMPLATE = new URLTemplate("metadata_templates/%s"); 029 030 /** 031 * Default metadata type to be used in query. 032 */ 033 private static final String DEFAULT_METADATA_TYPE = "properties"; 034 035 /** 036 * Global metadata scope. Used by default if the metadata type is "properties". 037 */ 038 private static final String GLOBAL_METADATA_SCOPE = "global"; 039 040 /** 041 * Enterprise metadata scope. Used by default if the metadata type is not "properties". 042 */ 043 private static final String ENTERPRISE_METADATA_SCOPE = "enterprise"; 044 045 /** 046 * Default number of entries per page. 047 */ 048 private static final int DEFAULT_ENTRIES_LIMIT = 100; 049 050 /** 051 * @see #getTemplateKey() 052 */ 053 private String templateKey; 054 055 /** 056 * @see #getScope() 057 */ 058 private String scope; 059 060 /** 061 * @see #getDisplayName() 062 */ 063 private String displayName; 064 065 /** 066 * @see #getIsHidden() 067 */ 068 private Boolean isHidden; 069 070 /** 071 * @see #getFields() 072 */ 073 private List<Field> fields; 074 075 /** 076 * Constructs an empty metadata template. 077 */ 078 public MetadataTemplate() { 079 super(); 080 } 081 082 /** 083 * Constructs a metadata template from a JSON string. 084 * @param json the json encoded metadate template. 085 */ 086 public MetadataTemplate(String json) { 087 super(json); 088 } 089 090 /** 091 * Constructs a metadate template from a JSON object. 092 * @param jsonObject the json encoded metadate template. 093 */ 094 MetadataTemplate(JsonObject jsonObject) { 095 super(jsonObject); 096 } 097 098 /** 099 * Gets the unique template key to identify the metadata template. 100 * @return the unique template key to identify the metadata template. 101 */ 102 public String getTemplateKey() { 103 return this.templateKey; 104 } 105 106 /** 107 * Gets the metadata template scope. 108 * @return the metadata template scope. 109 */ 110 public String getScope() { 111 return this.scope; 112 } 113 114 /** 115 * Gets the displayed metadata template name. 116 * @return the displayed metadata template name. 117 */ 118 public String getDisplayName() { 119 return this.displayName; 120 } 121 122 /** 123 * Gets is the metadata template hidden. 124 * @return is the metadata template hidden. 125 */ 126 public Boolean getIsHidden() { 127 return this.isHidden; 128 } 129 130 /** 131 * Gets the iterable with all fields the metadata template contains. 132 * @return the iterable with all fields the metadata template contains. 133 */ 134 public List<Field> getFields() { 135 return this.fields; 136 } 137 138 /** 139 * {@inheritDoc} 140 */ 141 @Override 142 void parseJSONMember(JsonObject.Member member) { 143 JsonValue value = member.getValue(); 144 String memberName = member.getName(); 145 if (memberName.equals("templateKey")) { 146 this.templateKey = value.asString(); 147 } else if (memberName.equals("scope")) { 148 this.scope = value.asString(); 149 } else if (memberName.equals("displayName")) { 150 this.displayName = value.asString(); 151 } else if (memberName.equals("hidden")) { 152 this.isHidden = value.asBoolean(); 153 } else if (memberName.equals("fields")) { 154 this.fields = new ArrayList<Field>(); 155 for (JsonValue field: value.asArray()) { 156 this.fields.add(new Field(field.asObject())); 157 } 158 } 159 } 160 161 /** 162 * Gets the metadata template of properties. 163 * @param api the API connection to be used. 164 * @return the metadata template returned from the server. 165 */ 166 public static MetadataTemplate getMetadataTemplate(BoxAPIConnection api) { 167 return getMetadataTemplate(api, DEFAULT_METADATA_TYPE); 168 } 169 170 /** 171 * Gets the metadata template of specified template type. 172 * @param api the API connection to be used. 173 * @param templateName the metadata template type name. 174 * @return the metadata template returned from the server. 175 */ 176 public static MetadataTemplate getMetadataTemplate(BoxAPIConnection api, String templateName) { 177 String scope = scopeBasedOnType(templateName); 178 return getMetadataTemplate(api, templateName, scope); 179 } 180 181 /** 182 * Gets the metadata template of specified template type. 183 * @param api the API connection to be used. 184 * @param templateName the metadata template type name. 185 * @param scope the metadata template scope (global or enterprise). 186 * @param fields the fields to retrieve. 187 * @return the metadata template returned from the server. 188 */ 189 public static MetadataTemplate getMetadataTemplate( 190 BoxAPIConnection api, String templateName, String scope, String ... fields) { 191 QueryStringBuilder builder = new QueryStringBuilder(); 192 if (fields.length > 0) { 193 builder.appendParam("fields", fields); 194 } 195 URL url = METADATA_TEMPLATE_URL_TEMPLATE.buildWithQuery( 196 api.getBaseURL(), builder.toString(), scope, templateName); 197 BoxAPIRequest request = new BoxAPIRequest(api, url, "GET"); 198 BoxJSONResponse response = (BoxJSONResponse) request.send(); 199 return new MetadataTemplate(response.getJSON()); 200 } 201 202 /** 203 * Returns all metadata templates within a user's enterprise. 204 * @param api the API connection to be used. 205 * @param fields the fields to retrieve. 206 * @return the metadata template returned from the server. 207 */ 208 public static Iterable<MetadataTemplate> getEnterpriseMetadataTemplates(BoxAPIConnection api, String ... fields) { 209 return getEnterpriseMetadataTemplates(ENTERPRISE_METADATA_SCOPE, api, fields); 210 } 211 212 /** 213 * Returns all metadata templates within a user's scope. Currently only the enterprise scope is supported. 214 * @param scope the scope of the metadata templates. 215 * @param api the API connection to be used. 216 * @param fields the fields to retrieve. 217 * @return the metadata template returned from the server. 218 */ 219 public static Iterable<MetadataTemplate> getEnterpriseMetadataTemplates( 220 String scope, BoxAPIConnection api, String ... fields) { 221 return getEnterpriseMetadataTemplates(ENTERPRISE_METADATA_SCOPE, DEFAULT_ENTRIES_LIMIT, api, fields); 222 } 223 224 /** 225 * Returns all metadata templates within a user's scope. Currently only the enterprise scope is supported. 226 * @param scope the scope of the metadata templates. 227 * @param limit maximum number of entries per response. 228 * @param api the API connection to be used. 229 * @param fields the fields to retrieve. 230 * @return the metadata template returned from the server. 231 */ 232 public static Iterable<MetadataTemplate> getEnterpriseMetadataTemplates( 233 String scope, int limit, BoxAPIConnection api, String ... fields) { 234 QueryStringBuilder builder = new QueryStringBuilder(); 235 if (fields.length > 0) { 236 builder.appendParam("fields", fields); 237 } 238 return new BoxResourceIterable<MetadataTemplate>( 239 api, ENTERPRISE_METADATA_URL_TEMPLATE.buildWithQuery( 240 api.getBaseURL(), builder.toString(), scope), limit) { 241 242 @Override 243 protected MetadataTemplate factory(JsonObject jsonObject) { 244 return new MetadataTemplate(jsonObject); 245 } 246 }; 247 } 248 249 /** 250 * Determines the metadata scope based on type. 251 * @param typeName type of the metadata. 252 * @return scope of the metadata. 253 */ 254 private static String scopeBasedOnType(String typeName) { 255 return typeName.equals(DEFAULT_METADATA_TYPE) ? GLOBAL_METADATA_SCOPE : ENTERPRISE_METADATA_SCOPE; 256 } 257 258 /** 259 * Class contains information about the metadata template field. 260 */ 261 public class Field extends BoxJSONObject { 262 263 /** 264 * @see #getType() 265 */ 266 private String type; 267 268 /** 269 * @see #getKey() 270 */ 271 private String key; 272 273 /** 274 * @see #getDisplayName() 275 */ 276 private String displayName; 277 278 /** 279 * @see #getIsHidden() 280 */ 281 private Boolean isHidden; 282 283 /** 284 * @see #getDescription() 285 */ 286 private String description; 287 288 /** 289 * @see #getOptions() 290 */ 291 private List<String> options; 292 293 /** 294 * Constructs an empty metadata template. 295 */ 296 public Field() { 297 super(); 298 } 299 300 /** 301 * Constructs a metadate template field from a JSON string. 302 * @param json the json encoded metadate template field. 303 */ 304 public Field(String json) { 305 super(json); 306 } 307 308 /** 309 * Constructs a metadate template field from a JSON object. 310 * @param jsonObject the json encoded metadate template field. 311 */ 312 Field(JsonObject jsonObject) { 313 super(jsonObject); 314 } 315 316 /** 317 * Gets the data type of the field's value. 318 * @return the data type of the field's value. 319 */ 320 public String getType() { 321 return this.type; 322 } 323 324 /** 325 * Gets the key of the field. 326 * @return the key of the field. 327 */ 328 public String getKey() { 329 return this.key; 330 } 331 332 /** 333 * Gets the display name of the field. 334 * @return the display name of the field. 335 */ 336 public String getDisplayName() { 337 return this.displayName; 338 } 339 340 /** 341 * Gets is metadata template field hidden. 342 * @return is metadata template field hidden. 343 */ 344 public Boolean getIsHidden() { 345 return this.isHidden; 346 } 347 348 /** 349 * Gets the description of the field. 350 * @return the description of the field. 351 */ 352 public String getDescription() { 353 return this.description; 354 } 355 356 /** 357 * Gets list of possible options for enum type of the field. 358 * @return list of possible options for enum type of the field. 359 */ 360 public List<String> getOptions() { 361 return this.options; 362 } 363 364 /** 365 * {@inheritDoc} 366 */ 367 @Override 368 void parseJSONMember(JsonObject.Member member) { 369 JsonValue value = member.getValue(); 370 String memberName = member.getName(); 371 if (memberName.equals("type")) { 372 this.type = value.asString(); 373 } else if (memberName.equals("key")) { 374 this.key = value.asString(); 375 } else if (memberName.equals("displayName")) { 376 this.displayName = value.asString(); 377 } else if (memberName.equals("hidden")) { 378 this.isHidden = value.asBoolean(); 379 } else if (memberName.equals("description")) { 380 this.description = value.asString(); 381 } else if (memberName.equals("options")) { 382 this.options = new ArrayList<String>(); 383 for (JsonValue key: value.asArray()) { 384 this.options.add(key.asObject().get("key").asString()); 385 } 386 } 387 } 388 } 389 390}