public class Schema<I extends Iced,S extends Schema<I,S>> extends Iced
The purpose of Schemas is to provide a stable, versioned interface to the functionality in H2O, which allows the back end implementation to change rapidly without breaking REST API clients such as the Web UI and R binding. Schemas also allow for functionality which exposes the schema metadata to clients, allowing them to do service discovery and to adapt dynamically to new H2O functionality (e.g., to be able to call any ModelBuilder, even new ones written since the client was built, without knowing any details about the specific algo).
Most schemas have a 1-to-1 mapping to an Iced implementation object. Both the Schema and the Iced object may have children, or (more often) not. Occasionally, e.g. in the case of schemas used only to handle HTTP request parameters, there will not be a backing impl object and the Schema will be parameterized by Iced.
Schemas have a State section (broken into Input, Output and InOut fields) and an Adapter section. The adapter methods fill the State to and from the Iced impl objects and from HTTP request parameters. In the simple case, where the backing object corresponds 1:1 with the Schema and no adapting need be done, the methods here in the Schema class will do all the work based on reflection.
Methods here allow us to convert from Schema to Iced (impl) and back in a flexible way. The default behaviour is to map like-named fields back and forth, often with some default type conversions (e.g., a Keyed object like a Model will be automagically converted back and forth to a Key). Subclasses can override methods such as fillImpl or fillFromImpl to provide special handling when adapting from schema to impl object and back. Usually they will want to call super to get the default behavior, and then modify the results a bit (e.g., to map differently-named fields, or to compute field values).
Schema Fields must have a single API annotation describing their direction of operation and any other properties such as "required". Fields are API.Direction.OUTPUT by default. Transient and static fields are ignored.
for information on the field annotations
Some use cases:
To create a schema object and fill it from an existing impl object (the common case):
{@code
S schema = schema(version);
schema.fillFromImpl(impl);
}
To create an impl object and fill it from an existing schema object (the common case):
{@code
I impl = schema.createImpl(); // create an empty impl object and any empty children
schema.fillImpl(impl); // fill the empty impl object and any children from the Schema and its children
}
or
{@code
I impl = schema.createAndFillImpl(); // helper which does schema.fillImpl(schema.createImpl())
}
To create a schema object filled from the default values of its impl class and then
overridden by HTTP request params:
{@code
S schema = schema(version);
I defaults = schema.createImpl();
schema.fillFromImpl(defaults);
schema.fillFromParms(parms);
}
,
Serialized FormModifier and Type | Class and Description |
---|---|
static class |
Schema.Meta |
Modifier and Type | Field and Description |
---|---|
Schema.Meta |
__meta |
protected java.lang.Class<I> |
_impl_class |
protected static java.util.regex.Pattern |
_version_pattern |
static java.lang.String |
EXCLUDE_FIELDS |
static java.lang.String |
INCLUDE_FIELDS |
Constructor and Description |
---|
Schema() |
Modifier and Type | Method and Description |
---|---|
protected java.lang.String |
acceptsFrame(Frame fr)
Deprecated.
|
I |
createAndFillImpl()
Convenience helper which creates and fill an impl.
|
I |
createImpl()
Create an implementation object and any child objects but DO NOT fill them.
|
static int |
extractVersion(java.lang.String clz_name)
Extract the version number from the schema class name.
|
S |
fillFromImpl(I impl)
Version and Schema-specific filling from the implementation object.
|
S |
fillFromParms(java.util.Properties parms) |
I |
fillImpl(I impl)
Fill an impl object and any children from this schema and its children.
|
static int |
getExperimentalVersion() |
static int |
getHighestSupportedVersion() |
java.lang.Class<I> |
getImplClass() |
static java.lang.Class<? extends Iced> |
getImplClass(java.lang.Class<? extends Schema> clz) |
static int |
getLatestVersion() |
int |
getSchemaVersion() |
java.lang.StringBuffer |
markdown(SchemaMetadata meta,
java.lang.StringBuffer appendToMe) |
java.lang.StringBuffer |
markdown(SchemaMetadata meta,
java.lang.StringBuffer appendToMe,
boolean include_input_fields,
boolean include_output_fields)
Generate Markdown documentation for this Schema, given we already have the metadata constructed.
|
java.lang.StringBuffer |
markdown(java.lang.StringBuffer appendToMe)
Generate Markdown documentation for this Schema.
|
java.lang.StringBuffer |
markdown(java.lang.StringBuffer appendToMe,
boolean include_input_fields,
boolean include_output_fields)
Generate Markdown documentation for this Schema possibly including only the input or output fields.
|
static Schema |
newInstance(java.lang.Class<? extends Schema> clz) |
static void |
register(java.lang.Class<? extends Schema> clz)
Register the given schema class.
|
static void |
registerAllSchemasIfNecessary()
Find all schemas using reflection and register them.
|
static Schema |
schema(java.lang.Class<? extends Schema> clz)
For a given schema class (e.g., water.api.FrameV2) return a new instance (e.g., a water.api.Framev2).
|
static Schema |
schema(int version,
java.lang.Class<? extends Iced> impl_class)
For a given version and Iced class return an appropriate Schema instance, if any.
|
static Schema |
schema(int version,
Iced impl)
For a given version and Iced object return an appropriate Schema instance, if any.
|
static Schema |
schema(int version,
java.lang.String type)
For a given version and type (Iced class simpleName) return an appropriate new Schema
object, if any.
|
static Schema |
schema(java.lang.String schema_name)
For a given schema_name (e.g., "FrameV2") return an appropriate new schema object (e.g., a water.api.Framev2).
|
static java.lang.Class<? extends Schema> |
schemaClass(int version,
java.lang.Class<? extends Iced> impl_class)
For a given version and Iced class return the appropriate Schema class, if any.f
|
static java.lang.Class<? extends Schema> |
schemaClass(int version,
Iced impl)
For a given version and Iced object return the appropriate Schema class, if any.
|
static java.lang.Class<? extends Schema> |
schemaClass(int version,
java.lang.String type)
For a given version and type (Iced class simpleName) return the appropriate Schema
class, if any.
|
static java.lang.Class<? extends Schema> |
schemaClass(java.lang.String schema_name)
For a given schema_name (e.g., "FrameV2") return the schema class (e.g., water.api.Framev2).
|
static java.util.Map<java.lang.String,java.lang.Class<? extends Schema>> |
schemas()
Return an immutable Map of all the schemas: schema_name -> schema Class.
|
clone, frozenType, read_impl, read, readExternal, readJSON_impl, readJSON, toJsonString, write_impl, write, writeExternal, writeHTML_impl, writeHTML, writeJSON_impl, writeJSON
public static final java.lang.String EXCLUDE_FIELDS
public static final java.lang.String INCLUDE_FIELDS
@API(help="Metadata on this schema instance, to make it self-describing.", direction=OUTPUT) public Schema.Meta __meta
protected static java.util.regex.Pattern _version_pattern
public static int extractVersion(java.lang.String clz_name)
public int getSchemaVersion()
public static final int getLatestVersion()
public static final int getHighestSupportedVersion()
public static final int getExperimentalVersion()
public static void register(java.lang.Class<? extends Schema> clz)
public I createImpl()
For objects without children this method does all the required work. For objects with children the subclass will need to override, e.g. by calling super.createImpl() and then calling createImpl() on its children.
Note that impl objects for schemas which override this method don't need to have a default constructor (e.g., a Keyed object constructor can still create and set the Key), but they must not fill any fields which can be filled later from the schema.
TODO: We *could* handle the common case of children with the same field names here by finding all of our fields that are themselves Schemas.
public I fillImpl(I impl)
public final I createAndFillImpl()
public S fillFromImpl(I impl)
public static java.lang.Class<? extends Iced> getImplClass(java.lang.Class<? extends Schema> clz)
public java.lang.Class<I> getImplClass()
@Deprecated protected java.lang.String acceptsFrame(Frame fr)
public S fillFromParms(java.util.Properties parms)
public static void registerAllSchemasIfNecessary()
public static java.util.Map<java.lang.String,java.lang.Class<? extends Schema>> schemas()
public static java.lang.Class<? extends Schema> schemaClass(int version, Iced impl)
schemaClass(int, java.lang.String)
public static java.lang.Class<? extends Schema> schemaClass(int version, java.lang.Class<? extends Iced> impl_class)
schemaClass(int, java.lang.String)
public static java.lang.Class<? extends Schema> schemaClass(int version, java.lang.String type)
If a higher version is asked for than is available (e.g., if the highest version of Frame is FrameV2 and the client asks for the schema for (Frame, 17) then FrameV2 will be returned. This compatibility lookup is cached.
public static java.lang.Class<? extends Schema> schemaClass(java.lang.String schema_name)
public static Schema schema(int version, Iced impl)
schema(int, java.lang.String)
public static Schema schema(int version, java.lang.Class<? extends Iced> impl_class)
schema(int, java.lang.String)
public static Schema schema(int version, java.lang.String type)
If a higher version is asked for than is available (e.g., if the highest version of Frame is FrameV2 and the client asks for the schema for (Frame, 17) then an instance of FrameV2 will be returned. This compatibility lookup is cached.
public static Schema schema(java.lang.String schema_name)
public static Schema schema(java.lang.Class<? extends Schema> clz)
public java.lang.StringBuffer markdown(java.lang.StringBuffer appendToMe)
public java.lang.StringBuffer markdown(java.lang.StringBuffer appendToMe, boolean include_input_fields, boolean include_output_fields)
public java.lang.StringBuffer markdown(SchemaMetadata meta, java.lang.StringBuffer appendToMe)
public java.lang.StringBuffer markdown(SchemaMetadata meta, java.lang.StringBuffer appendToMe, boolean include_input_fields, boolean include_output_fields)