use of org.collectionspace.chain.csp.schema.Record in project application by collectionspace.
the class WebTermList method termlist.
private void termlist(CSPRequestCache cache, Storage storage, UIRequest request, String path) throws UIException {
try {
// {tenant}/{tenantname}/{recordType}/termList/{termListType}
// needs to be {tenant}/{tenantname}/{recordType}/termList/{fieldname}
// as blanks etc are on a field basis not a vocab basis
String[] bits = path.split("/");
Record vb = this.spec.getRecord("vocab");
Field f = (Field) r.getFieldTopLevel(bits[0]);
if (f == null) {
f = (Field) r.getFieldFullList(bits[0]);
}
// If the field isn't in this record, look for it in subrecords (e.g. contacts).
if (f == null) {
FieldSet[] subRecordFields = r.getAllSubRecords("GET");
for (int i = 0; i < subRecordFields.length; i++) {
FieldSet subRecordField = subRecordFields[i];
Group group = (Group) subRecordField;
if (group.usesRecord()) {
Record subRecord = group.usesRecordId();
f = (Field) subRecord.getFieldTopLevel(bits[0]);
if (f == null) {
f = (Field) subRecord.getFieldFullList(bits[0]);
}
if (f != null) {
break;
}
}
}
}
JSONArray result = new JSONArray();
if (f.getAllAutocompleteInstances() != null && f.getAllAutocompleteInstances()[0] != null) {
for (Instance ins : f.getAllAutocompleteInstances()) {
JSONArray getallnames = ctl.get(storage, ins.getTitleRef(), vb);
for (int i = 0; i < getallnames.length(); i++) {
result.put(getallnames.get(i));
}
}
} else {
String msg = String.format("Dynamic term list(s) (aka, \"autocomplete\" list) for the field '%s' of record '%s' does not exist. Check that it is defined in the Application layer configuration.", f.toString(), r.whoamI);
log.error(msg);
}
JSONObject out = generateENUMField(storage, f, result, false);
request.sendJSONResponse(out);
int cacheMaxAgeSeconds = spec.getAdminData().getTermListCacheAge();
if (cacheMaxAgeSeconds > 0) {
request.setCacheMaxAgeSeconds(cacheMaxAgeSeconds);
}
} catch (JSONException e) {
throw new UIException("JSONException during autocompletion", e);
}
}
use of org.collectionspace.chain.csp.schema.Record in project application by collectionspace.
the class GenericStorage method updateJSON.
/**
* update the item
* @param root
* @param creds
* @param cache
* @param filePath
* @param jsonObject
* @param thisr
* @param serviceurl
* @throws ExistException
* @throws UnimplementedException
* @throws UnderlyingStorageException
*/
public void updateJSON(ContextualisedStorage root, CSPRequestCredentials creds, CSPRequestCache cache, String filePath, JSONObject jsonObject, JSONObject restrictions, Record thisr, String serviceurl) throws ExistException, UnimplementedException, UnderlyingStorageException {
try {
Map<String, Document> parts = new HashMap<String, Document>();
Document doc = null;
for (String section : thisr.getServicesRecordPathKeys()) {
String path = thisr.getServicesRecordPath(section);
String[] record_path = path.split(":", 2);
doc = XmlJsonConversion.convertToXml(thisr, jsonObject, section, "PUT");
if (doc != null) {
parts.put(record_path[0], doc);
// log.info(doc.asXML());
}
}
// This checks for hierarchy support, and does nothing if not appropriate.
handleHierarchyPayloadSend(thisr, parts, jsonObject, filePath);
int status = 0;
if (thisr.isMultipart()) {
String restrictedPath = getRestrictedPath(serviceurl, filePath, restrictions, null);
ReturnedMultipartDocument docm = conn.getMultipartXMLDocument(RequestMethod.PUT, restrictedPath, parts, creds, cache);
status = docm.getStatus();
} else {
ReturnedDocument docm = conn.getXMLDocument(RequestMethod.PUT, serviceurl + filePath, doc, creds, cache);
status = docm.getStatus();
}
// XXX Completely untested subrecord update
for (FieldSet fs : thisr.getAllSubRecords("PUT")) {
Record sr = fs.usesRecordId();
if (sr.isRealRecord()) {
// only deal with ones which are separate Records in the services
// get list of existing subrecords
JSONObject toDeleteList = new JSONObject();
JSONObject toUpdateList = new JSONObject();
JSONArray toCreateList = new JSONArray();
String getPath = serviceurl + filePath + "/" + sr.getServicesURL();
Integer subcount = 0;
String firstfile = "";
String[] filepaths = null;
while (!getPath.equals("")) {
JSONObject data = getListView(creds, cache, getPath, sr.getServicesListPath(), "csid", false, sr);
filepaths = (String[]) data.get("listItems");
subcount += filepaths.length;
if (firstfile.equals("") && subcount != 0) {
firstfile = filepaths[0];
}
// need to paginate // if(sr.getID().equals("termlistitem"))
for (String uri : filepaths) {
String path = uri;
if (path != null && path.startsWith("/")) {
path = path.substring(1);
}
toDeleteList.put(path, "original");
}
if (data.has("pagination")) {
Integer ps = Integer.valueOf(data.getJSONObject("pagination").getString("pageSize"));
Integer pn = Integer.valueOf(data.getJSONObject("pagination").getString("pageNum"));
Integer ti = Integer.valueOf(data.getJSONObject("pagination").getString("totalItems"));
if (ti > (ps * (pn + 1))) {
JSONObject pgRestrictions = new JSONObject();
pgRestrictions.put("pageSize", Integer.toString(ps));
pgRestrictions.put("pageNum", Integer.toString(pn + 1));
getPath = getRestrictedPath(getPath, pgRestrictions, sr.getServicesSearchKeyword(), "", false, "");
// need more values
} else {
getPath = "";
}
}
}
// how does that compare to what we need
if (sr.isType("authority")) {
// XXX need to use configuredVocabStorage
} else {
if (fs instanceof Field) {
JSONObject subdata = new JSONObject();
// loop thr jsonObject and find the fields I need
for (FieldSet subfs : sr.getAllFieldTopLevel("PUT")) {
String key = subfs.getID();
if (jsonObject.has(key)) {
subdata.put(key, jsonObject.get(key));
}
}
if (subcount == 0) {
// create
toCreateList.put(subdata);
} else {
// update - there should only be one
String firstcsid = firstfile;
toUpdateList.put(firstcsid, subdata);
toDeleteList.remove(firstcsid);
}
} else if (fs instanceof Group) {
// subrecorddata.put(value);
if (jsonObject.has(fs.getID())) {
Object subdata = jsonObject.get(fs.getID());
if (subdata instanceof JSONObject) {
if (((JSONObject) subdata).has("_subrecordcsid")) {
String thiscsid = ((JSONObject) subdata).getString("_subrecordcsid");
// update
if (toDeleteList.has(thiscsid)) {
toUpdateList.put(thiscsid, (JSONObject) subdata);
toDeleteList.remove(thiscsid);
} else {
// something has gone wrong... best just create it from scratch
toCreateList.put(subdata);
}
} else {
// create
toCreateList.put(subdata);
}
}
}
} else {
// need to find if we have csid's for each one
if (jsonObject.has(fs.getID())) {
Object subdata = jsonObject.get(fs.getID());
if (subdata instanceof JSONArray) {
JSONArray subarray = (JSONArray) subdata;
for (int i = 0; i < subarray.length(); i++) {
JSONObject subrecord = subarray.getJSONObject(i);
if (subrecord.has("_subrecordcsid") == true) {
String thiscsid = subrecord.getString("_subrecordcsid");
// update
if (toDeleteList.has(thiscsid)) {
toUpdateList.put(thiscsid, subrecord);
toDeleteList.remove(thiscsid);
} else {
// something has gone wrong... no existing records match the CSID being passed in, so
// we will try to create a new record. Could fail if a record with the same short ID already exists
toCreateList.put(subrecord);
}
} else if (subrecord.has("shortIdentifier") == true) {
String thisShortID = subrecord.getString("shortIdentifier");
// update
// See if we can find a matching short ID in the current list of items
String thiscsid = lookupCsid(cache, filepaths, serviceurl, thisShortID);
if (thiscsid != null) {
toUpdateList.put(thiscsid, subrecord);
toDeleteList.remove(thiscsid);
} else {
//
// Since we couldn't find an existing record with that short ID, we need to create it.
//
toCreateList.put(subrecord);
}
} else {
// create since we couldn't look for existing records via CSID or Short ID
toCreateList.put(subrecord);
}
}
}
}
}
String savePath = serviceurl + filePath + "/" + sr.getServicesURL() + "/";
// do delete JSONObject existingcsid = new JSONObject();
Iterator<String> rit = toDeleteList.keys();
while (rit.hasNext()) {
String key = rit.next();
// will fail if this record is a term having active references -i.e., one or more non-deleted records reference it.
deleteJSON(root, creds, cache, key, savePath, sr);
}
// do update JSONObject updatecsid = new JSONObject();
Iterator<String> keys = toUpdateList.keys();
while (keys.hasNext()) {
String key = keys.next();
JSONObject value = toUpdateList.getJSONObject(key);
JSONObject subrRestrictions = new JSONObject();
updateJSON(root, creds, cache, key, value, subrRestrictions, sr, savePath);
}
// do create JSONArray createcsid = new JSONArray();
for (int i = 0; i < toCreateList.length(); i++) {
JSONObject value = toCreateList.getJSONObject(i);
subautocreateJSON(root, creds, cache, sr, value, savePath);
}
}
}
}
// throw new ExistException("Not found: "+serviceurl+filePath);
if (status > 299 || status < 200)
throw new UnderlyingStorageException("Bad response ", status, serviceurl + filePath);
} catch (ConnectionException e) {
throw new UnderlyingStorageException("Service layer exception" + e.getLocalizedMessage(), e.getStatus(), e.getUrl(), e);
} catch (JSONException e) {
throw new UnimplementedException("JSONException", e);
} catch (UnsupportedEncodingException e) {
throw new UnimplementedException("UnsupportedEncodingException", e);
}
}
use of org.collectionspace.chain.csp.schema.Record in project application by collectionspace.
the class GenericStorage method createRelationship.
// NOTE that this is building XML Doc, and not JSON as is typical!
protected static Element createRelationship(Relationship rel, Object data, String csid, String subjtype, String metaType, Boolean reverseIt, Spec spec) throws ExistException, UnderlyingStorageException, JSONException {
Document doc = DocumentFactory.getInstance().createDocument();
Element subroot = doc.addElement("relation-list-item");
Element predicate = subroot.addElement("predicate");
predicate.addText(rel.getPredicate());
Element relMetaType = subroot.addElement("relationshipMetaType");
relMetaType.addText(metaType);
String subjectName = "subject";
String objectName = "object";
if (reverseIt) {
subjectName = "object";
objectName = "subject";
}
Element subject = subroot.addElement(subjectName);
Element subjcsid = subject.addElement("csid");
if (csid != null) {
subjcsid.addText(csid);
} else {
subjcsid.addText("${itemCSID}");
}
// find out record type from urn
String refName = (String) data;
Element object = subroot.addElement(objectName);
// We may or may not be dealing with a sub-resource like AuthItems.
// TODO - this may all be unneccessary, as the services should fill in
// doc types, etc. now automatically.
// OTOH, not a bad idea to validate the refName...
RefName.AuthorityItem itemParsed = RefName.AuthorityItem.parse(refName);
if (itemParsed != null) {
String serviceurl = itemParsed.inAuthority.resource;
Record myr = spec.getRecordByServicesUrl(serviceurl);
if (myr.isType("authority")) {
Element objRefName = object.addElement("refName");
objRefName.addText(refName);
} else {
throw new JSONException("Relation object refName is for sub-resources other than authority item - NYI!");
}
} else {
RefName.Authority resourceParsed = RefName.Authority.parse(refName);
if (resourceParsed != null) {
Element objRefName = object.addElement("refName");
objRefName.addText(refName);
} else {
throw new JSONException("Relation object refName does not appear to be valid!");
}
}
// log.info(subroot.asXML());
return subroot;
}
use of org.collectionspace.chain.csp.schema.Record in project application by collectionspace.
the class ServiceBindingsGeneration method doServiceProperties.
private boolean doServiceProperties(Record record, Element props, Namespace types, boolean isAuthority) {
boolean result = false;
Record r = record;
//
if (isAuthority == true) {
Spec spec = r.getSpec();
r = spec.getRecord(BASE_AUTHORITY_RECORD);
}
FieldSet objNameProp = r.getMiniSummary();
if (objNameProp != null) {
String serviceFieldAlias = objNameProp.getServiceFieldAlias();
if (serviceFieldAlias != null) {
objNameProp = r.getField(serviceFieldAlias);
}
this.addServiceProperty(props, objNameProp, OBJECT_NAME_PROPERTY, types, isAuthority);
result = true;
}
FieldSet objNumberProp = r.getMiniNumber();
if (objNumberProp != null) {
this.addServiceProperty(props, objNumberProp, OBJECT_NUMBER_PROPERTY, types, isAuthority);
result = true;
}
return result;
}
use of org.collectionspace.chain.csp.schema.Record in project application by collectionspace.
the class ServiceBindingsGeneration method createInitFieldList.
/*
* Returns true if we end up creating service binding entries for field initialization.
*/
private boolean createInitFieldList(Element paramsElement, Namespace namespace, Record record, Boolean isAuthority) {
boolean result = false;
// Loop through each field to see if we need to create a service binding entry
for (FieldSet f : record.getAllFieldFullList("")) {
boolean createdEntry = false;
if (f.isASelfRenderer() == true) {
//
// Self rendered fields are essentially sub-records
//
String fieldSetServicesType = f.getServicesType(NOT_NAMESPACED);
Spec spec = f.getRecord().getSpec();
// find a record that corresponds to the fieldset's service type
Record subRecord = spec.getRecord(fieldSetServicesType);
// make a recursive call with the subrecord
createdEntry = createInitFieldList(paramsElement, namespace, subRecord, isAuthority);
} else {
// Create a service binding for the field
createdEntry = createInitFieldEntry(paramsElement, namespace, record, f, isAuthority);
}
//
if (createdEntry == true) {
result = true;
}
}
return result;
}
Aggregations