/**
* This Source Code Form is subject to the terms of the Mozilla Public License,
* v. 2.0. If a copy of the MPL was not distributed with this file, You can
* obtain one at http://mozilla.org/MPL/2.0/. OpenMRS is also distributed under
* the terms of the Healthcare Disclaimer located at http://openmrs.org/license.
*
* Copyright (C) OpenMRS Inc. OpenMRS is a registered trademark and the OpenMRS
* graphic logo is a trademark of OpenMRS Inc.
*/
package org.openmrs.customdatatype;
/**
* Represents a custom datatype, which an administrator may use for global properties, attribute types, etc.
* Handles conversion between a typed Java object and a reference string which can be persisted in a database
* varchar column.
* @param <T> the Java class used for typed values
* @since 1.9
*/
public interface CustomDatatype<T> {
/**
* A {@link CustomValueDescriptor} defines both a datatype and its configuration (e.g. a regex for a RegexValidatedString datatype).
* The framework will instantiate datatypes and call this method to set that configuration. Subclasses should define the format
* of this configuration.
*
* @param config
*/
void setConfiguration(String config);
/**
* The OpenMRS service layer calls this method when a custom value of this datatype is saved (created or edited). Implementations
* should persist the typed value, and return a valueReference that can be used to access that value in the future.
* (Simple datatype implementations that don't require external storage may just serialize their typedValue to a String and
* return that.)
*
* Implementations may safely assume that validate was called on typedValue before this method is called.
*
* @param typedValue
* @param existingValueReference If null, the custom value is being saved for the first time. If not null, this custom value has
* been saved before with the given reference. Implementations may choose to return the same value reference if they are overwriting
* the old value on remote storage.
* @return a valueReference that may be used in the future to retrieve typedValue
* @throws InvalidCustomValueException
*/
String save(T typedValue, String existingValueReference) throws InvalidCustomValueException;
/**
* Gets the reference string that would be persisted for the given typed value. (This allows efficient searching for exact attribute
* values.)
*
* @param typedValue
* @return reference string
* @throws UnsupportedOperationException if it is not feasible to calculate this efficiently (e.g. you'd need to go to remote storage)
*/
String getReferenceStringForValue(T typedValue) throws UnsupportedOperationException;
/**
* Converts a reference string to its typed value. This may be expensive, especially if the datatype needs
* to go to remote storage.
*
* @param referenceString
* @return the actual typed value for the given referenceString
* @throws InvalidCustomValueException if the persisted value is illegal (perhaps because datatype configuration
* was changed since this value was persisted)
*/
T fromReferenceString(String referenceString) throws InvalidCustomValueException;
/**
* Converts a reference string to a short (generally < 100 characters) plain-text representation of its value. The return
* value also indicates whether this representation is a complete view of the value, or if there is more to display.
* Implementations of this method must be high-performance, e.g. if the method is called thousands of times for a table
* of objects with custom values.
*
* @param referenceString
* @return a summary representation of the given value
*/
Summary getTextSummary(String referenceString);
/**
* Validates the given value to see if it is a legal value for the given handler. (For example the RegexValidatedText
* type checks against a regular expression.)
* @param typedValue
*/
void validate(T typedValue) throws InvalidCustomValueException;
/**
* A short representation of a custom value, along with an indication of whether this is the complete value,
* or just a summary.
*/
public class Summary {
private String summary;
private boolean complete;
/**
* @param summary
* @param complete
*/
public Summary(String summary, boolean complete) {
this.summary = summary;
this.complete = complete;
}
/**
* @return the short representation of a custom value
*/
public String getSummary() {
return summary;
}
/**
* @param summary the summary to set
*/
public void setSummary(String summary) {
this.summary = summary;
}
/**
* @return if true, then getSummary() returns a complete view of the custom value; otherwise the value is
* in fact a summary
*/
public boolean isComplete() {
return complete;
}
/**
* @param complete the complete to set
*/
public void setComplete(boolean complete) {
this.complete = complete;
}
/**
* @see java.lang.Object#toString()
*/
@Override
public String toString() {
return summary;
}
}
}