Note
This documentation is for OMERO 5.2. This version is now in maintenance mode and will only be updated in the event of critical bugs or security concerns. OMERO 5.3 is expected in the first quarter of 2017.
All interaction with the OMERO server takes place via several API services available from a ServiceFactory. A service factory is obtained from the client connection e.g. Python:
client = omero.client("localhost")
session = client.createSession("username", "password") # this is the service factory
adminService = session.getAdminService() # now we can get/create services
The ome.api package in the common component defines the central “verbs” of the OMERO system. All external interactions with the system should happen with these verbs, or services. Each OMERO service belongs to a particular service level with each level calling only on services from lower levels.
A complete list of service APIs can be found here and some examples of API use in Python are provided. Java or C++ code can use the same API in a very similar manner.
IQuery and IUpdate are the basic building blocks for the rest of the (non-binary) API. IQuery is based on QuerySources and QueryParemeters which are explained under Using server queries internally. The goal of this design is to make wildly separate definitions of queries (templates, db-stored, Java code, C# code, …) runnable on the server.
IUpdate takes any graph composed of IObject objects and checks them for dirtiness. All changes to the graph are stored in the database if the user calling IUpdate has the proper permissions, otherwise an exception is thrown.
Dirty checks follow the Three Commandments:
The IAdmin interface defines all the actions necessary to administer the Server security and firewalls . It is explained further on the OMERO admin interface page.
Certain operations, like those dealing with data management and viewing, happen more frequently than others (like defining microscopes). Those have been collected in the IContainer interface. IContainer simplifies a few very common queries, and there is a related package (“omero.gateway.model.*”) for working with the returned graphs. OMERO.insight works almost exclusively with the IContainer interface for its non-binary needs.
// Saving a simple change
Dataset d = iQuery.get( Dataset.class,1L );
d.setName( "test" );
iUpdate.saveObject( d );
// Creating a new object
Dataset d = new Dataset();
d.setName( "test" ); // not-null fields must be filled in
iUpdate.saveObject( d );
// Retrieving a graph
Set<Dataset> ds = iQuery.findAllByQuery( "from Dataset d left outer join d.images where d.name = 'test'",null );
A stateless service has no client-noticeable lifecycle and all instances can be treated equally. A new stateful service, on the other hand, will be created for each client-side proxy (see the ServiceFactory.create\* methods). Once obtained, a stateful service proxy can only be used by a single user. After task completion, the service should be closed (proxy.close()) to free up server resources.
A tutorial is available at How To create a service. In general, if a properly annotated service is placed in any JAR of the OMERO EAR file (see Build System for more) then the service will be deployed to the server. In the case of OMERO.blitz, the service must be properly defined under components/blitz/resources.
The server-side implementation of these interfaces makes use of ((JDK5)) Structured annotations and an AOP interceptor to validate all method parameters. Calls to pojos.findContainerHierarches are first caught by a method interceptor, which checks for annotations on the parameters and, if available, performs the necessary checks. The interceptor also makes proactive checks. For a range of parameter types (such as Java Collections) it requires that annotations exist and will refuse to proceed if not implemented.
An API call of the form:
pojos.findContainerHierarches(Class,Set,Map)
is implemented as
pojos.findContainerHierarchies(@NotNull Class, @NotNull @Validate(Integer.class) Set, Map)