Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions doc/files.md
Original file line number Diff line number Diff line change
Expand Up @@ -656,6 +656,9 @@ float floatValue = metadata.getFloat("/price");

// Date metadata fields
Date dateValue = metadata.getDate("/deadline");

// Multiselect metadata fields
List<String> multiSelectValues = metadata.getMultiSelect("/categories");
```

[metadata]: http://opensource.box.com/box-java-sdk/javadoc/com/box/sdk/Metadata.html
Expand Down
50 changes: 49 additions & 1 deletion src/main/java/com/box/sdk/Metadata.java
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,22 @@ public Metadata add(String path, float value) {
return this;
}

/**
* Adds a new metadata value of array type.
* @param path the path to the field.
* @param values the collection of values.
* @return the metadata object for chaining.
*/
public Metadata add(String path, List<String> values) {
JsonArray arr = new JsonArray();
for (String value : values) {
arr.add(value);
}
this.values.add(this.pathToProperty(path), arr);
this.addOp("add", path, arr);
return this;
}

/**
* Replaces an existing metadata value.
* @param path the path that designates the key. Must be prefixed with a "/".
Expand Down Expand Up @@ -194,7 +210,7 @@ public Metadata replace(String path, float value) {
*/
public Metadata remove(String path) {
this.values.remove(this.pathToProperty(path));
this.addOp("remove", path, null);
this.addOp("remove", path, (String) null);
return this;
}

Expand Down Expand Up @@ -265,6 +281,20 @@ public Date getDate(String path) throws ParseException {
return BoxDateFormat.parse(this.getValue(path).asString());
}

/**
* Get a value from a multiselect metadata field.
* @param path the key path in the metadata object. Must be prefixed with a "/".
* @return the list of values set in the field.
*/
public List<String> getMultiSelect(String path) {
List<String> values = new ArrayList<String>();
for (JsonValue val : this.getValue(path).asArray()) {
values.add(val.asString());
}

return values;
}

/**
* Returns a list of metadata property paths.
* @return the list of metdata property paths.
Expand Down Expand Up @@ -360,6 +390,24 @@ private void addOp(String op, String path, float value) {
.add("value", value));
}

/**
* Adds a new patch operation for array values.
* @param op the operation type. Must be add, replace, remove, or test.
* @param path the path that designates the key. Must be prefixed with a "/".
* @param values the array of values to be set.
*/
private void addOp(String op, String path, JsonArray values) {

if (this.operations == null) {
this.operations = new JsonArray();
}

this.operations.add(new JsonObject()
.add("op", op)
.add("path", path)
.add("value", values));
}

static String scopeBasedOnType(String typeName) {
String scope;
if (typeName.equals(DEFAULT_METADATA_TYPE)) {
Expand Down
74 changes: 73 additions & 1 deletion src/main/java/com/box/sdk/MetadataTemplate.java
Original file line number Diff line number Diff line change
Expand Up @@ -382,6 +382,17 @@ private static JsonObject getFieldOperationJsonObject(FieldOperation fieldOperat
if (enumOptionKey != null) {
jsonObject.add("enumOptionKey", enumOptionKey);
}

String multiSelectOptionKey = fieldOperation.getMultiSelectOptionKey();
if (multiSelectOptionKey != null) {
jsonObject.add("multiSelectOptionKey", multiSelectOptionKey);
}

List<String> multiSelectOptionKeys = fieldOperation.getMultiSelectOptionKeys();
if (multiSelectOptionKeys != null) {
jsonObject.add("multiSelectOptionKeys", getJsonArray(multiSelectOptionKeys));
}

return jsonObject;
}

Expand Down Expand Up @@ -727,6 +738,8 @@ public static class FieldOperation extends BoxJSONObject {
private List<String> fieldKeys;
private List<String> enumOptionKeys;
private String enumOptionKey;
private String multiSelectOptionKey;
private List<String> multiSelectOptionKeys;

/**
* Constructs an empty FieldOperation.
Expand Down Expand Up @@ -847,6 +860,38 @@ public void setEnumOptionKey(String enumOptionKey) {
this.enumOptionKey = enumOptionKey;
}

/**
* Gets the multi-select option key.
* @return the key.
*/
public String getMultiSelectOptionKey() {
return this.multiSelectOptionKey;
}

/**
* Sets the multi-select option key.
* @param key the key.
*/
public void setMultiSelectOptionKey(String key) {
this.multiSelectOptionKey = key;
}

/**
* Gets the list of multiselect option keys.
* @return the list of keys.
*/
public List<String> getMultiSelectOptionKeys() {
return this.multiSelectOptionKeys;
}

/**
* Sets the multi-select option keys.
* @param keys the list of keys.
*/
public void setMultiSelectOptionKeys(List<String> keys) {
this.multiSelectOptionKeys = keys;
}

/**
* {@inheritDoc}
*/
Expand Down Expand Up @@ -884,6 +929,13 @@ void parseJSONMember(JsonObject.Member member) {
}
} else if (memberName.equals("enumOptionKey")) {
this.enumOptionKey = value.asString();
} else if (memberName.equals("multiSelectOptionKey")) {
this.multiSelectOptionKey = value.asString();
} else if (memberName.equals("multiSelectOptionKeys")) {
this.multiSelectOptionKeys = new ArrayList<String>();
for (JsonValue key : value.asArray()) {
this.multiSelectOptionKeys.add(key.asString());
}
}
}
}
Expand Down Expand Up @@ -936,6 +988,26 @@ public enum Operation {
/**
* Reorders the field list to match the requested field list.
*/
reorderFields
reorderFields,

/**
* Adds a new option to a multiselect field.
*/
addMultiSelectOption,

/**
* Edits an existing option in a multiselect field.
*/
editMultiSelectOption,

/**
* Removes an option from a multiselect field.
*/
removeMultiSelectOption,

/**
* Changes the display order of options in a multiselect field.
*/
reorderMultiSelectOptions
}
}
151 changes: 151 additions & 0 deletions src/test/java/com/box/sdk/MetadataTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,10 @@
import com.eclipsesource.json.JsonObject;

import java.text.ParseException;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

public class MetadataTest {

Expand Down Expand Up @@ -112,6 +115,154 @@ public void testMissingMetaProperties() {
Assert.assertEquals(null, m.getParentID());
}

@Test
@Category(IntegrationTest.class)
public void testMultiSelectMetadataCRUD() {

BoxAPIConnection api = new BoxAPIConnection(TestConfig.getAccessToken());

long timestamp = Calendar.getInstance().getTimeInMillis();
String templateKey = "multiselect" + timestamp;
String fieldKey = "testMultiSelect";

// Create new template with multiselect field
List<String> fieldOptions = new ArrayList<String>();
fieldOptions.add("foo");
fieldOptions.add("bar");
fieldOptions.add("baz");
fieldOptions.add("quux");

List<MetadataTemplate.Field> fields = new ArrayList<MetadataTemplate.Field>();
MetadataTemplate.Field multiSelectField = new MetadataTemplate.Field();
multiSelectField.setKey(fieldKey);
multiSelectField.setType("multiSelect");
multiSelectField.setDisplayName("MultiSelect Field");
multiSelectField.setOptions(fieldOptions);
fields.add(multiSelectField);

MetadataTemplate template = MetadataTemplate.createMetadataTemplate(api, "enterprise",
templateKey, "MultiSelect " + timestamp, false, fields);

Assert.assertEquals("multiSelect", template.getFields().get(0).getType());
List<String> actualOptions = template.getFields().get(0).getOptions();
Assert.assertEquals("foo", actualOptions.get(0));
Assert.assertEquals("bar", actualOptions.get(1));
Assert.assertEquals("baz", actualOptions.get(2));
Assert.assertEquals("quux", actualOptions.get(3));

// Add template to item
Metadata mdValues = new Metadata();
List<String> values = new ArrayList<String>();
values.add("foo");
values.add("bar");
mdValues.add("/" + fieldKey, values);
BoxFolder.Info folder = BoxFolder.getRootFolder(api).createFolder("Metadata Test " + timestamp);
Metadata actualMD = folder.getResource().createMetadata(templateKey, mdValues);

Assert.assertEquals(templateKey, actualMD.getTemplateName());
List<String> multiSelectValues = actualMD.getMultiSelect("/" + fieldKey);
Assert.assertEquals(2, multiSelectValues.size());
Assert.assertEquals("foo", multiSelectValues.get(0));
Assert.assertEquals("bar", multiSelectValues.get(1));

// Update template with multiselect operations - change existing field and add another multiselect field
List<MetadataTemplate.FieldOperation> updates = new ArrayList<MetadataTemplate.FieldOperation>();

MetadataTemplate.Field newOption = new MetadataTemplate.Field();
newOption.setKey("blargh");
MetadataTemplate.FieldOperation add = new MetadataTemplate.FieldOperation();
add.setOp(MetadataTemplate.Operation.addMultiSelectOption);
add.setFieldKey(fieldKey);
add.setData(newOption);
updates.add(add);

MetadataTemplate.Field updatedField = new MetadataTemplate.Field();
updatedField.setKey("foooooo");
MetadataTemplate.FieldOperation edit = new MetadataTemplate.FieldOperation();
edit.setOp(MetadataTemplate.Operation.editMultiSelectOption);
edit.setFieldKey(fieldKey);
edit.setMultiSelectOptionKey("foo");
edit.setData(updatedField);
updates.add(edit);

MetadataTemplate.FieldOperation remove = new MetadataTemplate.FieldOperation();
remove.setOp(MetadataTemplate.Operation.removeMultiSelectOption);
remove.setFieldKey(fieldKey);
remove.setMultiSelectOptionKey("baz");
updates.add(remove);

MetadataTemplate.FieldOperation reorder = new MetadataTemplate.FieldOperation();
reorder.setOp(MetadataTemplate.Operation.reorderMultiSelectOptions);
reorder.setFieldKey(fieldKey);
List<String> reorderedFields = new ArrayList<String>();
reorderedFields.add("quux");
reorderedFields.add("blargh");
reorderedFields.add("bar");
reorderedFields.add("foooooo");
reorder.setMultiSelectOptionKeys(reorderedFields);
updates.add(reorder);

MetadataTemplate.FieldOperation addField = new MetadataTemplate.FieldOperation();
MetadataTemplate.Field newField = new MetadataTemplate.Field();
List<String> opts = new ArrayList<String>();
opts.add("one");
opts.add("two");
newField.setKey("otherMultiSelect");
newField.setDisplayName("Another MultiSelect");
newField.setType("multiSelect");
newField.setOptions(opts);
addField.setOp(MetadataTemplate.Operation.addField);
addField.setData(newField);
updates.add(addField);

MetadataTemplate updatedTemplate = MetadataTemplate.updateMetadataTemplate(api, "enterprise",
templateKey, updates);

Assert.assertEquals(2, updatedTemplate.getFields().size());
for (MetadataTemplate.Field field : updatedTemplate.getFields()) {

if (field.getKey().equals(fieldKey)) {
Assert.assertEquals("multiSelect", field.getType());
actualOptions = field.getOptions();
Assert.assertEquals("quux", actualOptions.get(0));
Assert.assertEquals("blargh", actualOptions.get(1));
Assert.assertEquals("bar", actualOptions.get(2));
Assert.assertEquals("foooooo", actualOptions.get(3));
} else if (field.getKey().equals("otherMultiSelect")) {
Assert.assertEquals("multiSelect", field.getType());
actualOptions = field.getOptions();
Assert.assertEquals("one", actualOptions.get(0));
Assert.assertEquals("two", actualOptions.get(1));
} else {
Assert.fail("Incorrect field found on metadata template: " + field.getKey());
}
}

// Update instance multiselect field
values = new ArrayList<String>();
values.add("two");
values.add("one");
actualMD.add("/otherMultiSelect", values);
actualMD.test("/" + fieldKey + "/0", "foooooo");
actualMD.test("/" + fieldKey + "/1", "bar");
actualMD.remove("/" + fieldKey + "/0");
actualMD.add("/" + fieldKey + "/-", "blargh");
Metadata updatedMD = folder.getResource().updateMetadata(actualMD);

multiSelectValues = updatedMD.getMultiSelect("/" + fieldKey);
Assert.assertEquals(2, multiSelectValues.size());
Assert.assertEquals("bar", multiSelectValues.get(0));
Assert.assertEquals("blargh", multiSelectValues.get(1));
multiSelectValues = updatedMD.getMultiSelect("/otherMultiSelect");
Assert.assertEquals(2, multiSelectValues.size());
Assert.assertEquals("two", multiSelectValues.get(0));
Assert.assertEquals("one", multiSelectValues.get(1));

// Delete metadata template and folder
MetadataTemplate.deleteMetadataTemplate(api, "enterprise", template.getTemplateKey());
folder.getResource().delete(true);
}

@Test
@Category(UnitTest.class)
public void getValues() {
Expand Down