[
https://issues.apache.org/jira/browse/OODT-613?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=13766627#comment-13766627
]
Ross Laidlaw commented on OODT-613:
-----------------------------------
Hi Rishi,
I've been experimenting with a design for configurable writers. Here's an
explanation of my work so far:
I was thinking it would be great if we could allow users to select from
multiple configurations per mime/content type. In the URLs, we could use a
query parameter (e.g. 'configuration') to select the configuration to use for
each request. The default would be no configuration, i.e. standard output, if
the parameter isn't present. For example:
{noformat}
http://[host]/fmprod/jaxrs/dataset.rss?productTypeId=urn:oodt:GenericFile&configuration=example
http://[host]/fmprod/jaxrs/dataset.rss?productTypeId=urn:oodt:GenericFile&configuration=georss
http://[host]/fmprod/jaxrs/product.json?productId=123&configuration=geojson
{noformat}
We could set this up by using a naming scheme for our context.xml parameters
that point to the configuration files:
{code:xml|title=context.xml|borderStyle=solid}
<Context>
...
<Parameter name="configuration.rss.example"
value="[FMPROD_HOME]/rss-example.xml"/>
<Parameter name="configuration.rss.georss" value="[FMPROD_HOME]/georss.xml"/>
<Parameter name="configuration.json.geojson" value="/tmp/geojson.xml"/>
...
</Context>
{code}
The naming scheme could be as follows: "configuration.<format>.<name>" where
<format> is the content/mime type that the configuration applies to (matching
the extension in the URL, e.g. xml, rss, json) and <name> is the name of that
particular configuration (matching the 'configuration' parameter in the URL).
In our JAX-RS servlet, we can read in all of these parameters, initialize each
configuration object and store the objects in a data structure (e.g.
Map<String, Map<String, Configuration>>, where the key of the parent map is the
content/mime type and the keys of the submaps are the configuration names):
{code:java|title=CasProductJaxrsServlet.java|borderStyle=solid}
public void init(ServletConfig servletConfig) throws ServletException
{
super.init(servletConfig);
ServletContext context = servletConfig.getServletContext();
...
// Create a map to store all of the configuration instances.
// The parent map is keyed by content type (e.g. rdf, rss, json).
// The sub-maps are keyed by configuration name (e.g. 'example', 'georss').
// A specific configuration can therefore be retrieved using the content type
and configuration name.
Map<String, Map<String, Configuration>> configurationMap =
new HashMap<String, Map<String, Configuration>>();
// Iterate over all of the context parameters in context.xml.
Enumeration<String> enumeration = context.getInitParameterNames();
while (enumeration.hasMoreElements())
{
String parameterName = enumeration.nextElement();
// Look for parameter names matching "configuration.<format>.<name>"
if(parameterName.startsWith("configuration"))
{
String[] values = parameterName.split("\\.");
if (values.length == 3)
{
String format = values[1];
String name = values[2];
String fileName = context.getInitParameter(parameterName);
// Create a configuration and import details from the file.
Configuration config = ConfigurationFactory.createInstance(format);
config.initialize(fileName);
// Add the new configuration instance to the map.
if (configurationMap.containsKey(format))
{
configurationMap.get(format).put(name, config);
}
else
{
Map<String, Configuration> map = new HashMap<String, Configuration>();
map.put(name, config);
configurationMap.put(format, map);
}
}
else
{
LOGGER.log(Level.FINE, "Configuration context parameter could not be
parsed.");
}
}
}
// Store the map as a context attribute so that it can be accessed by
services and/or resources.
context.setAttribute("configurations", configurationMap);
...
}
{code}
(This will require some configuration classes (e.g. RdfConfiguration,
RssConfiguration) that implement an interface 'Configuration', plus the
ConfigurationFactory class. The configuration code from the original packages
will be ported to these classes (I've nearly completed working on that).)
Then, in our provider/writer classes we can use context injection to access the
URL for the request and the servlet context. From the URL we can check if the
configuration parameter was supplied. If so, we can access the servlet context
attribute for our configuration objects (i.e. the map) to get the correct
configuration object. For example:
{code:java|borderStyle=solid}
...
@Context
private ServletContext context;
@Context
private UriInfo uriInfo;
...
public void writeTo(Resource resource, Class<?> type,
Type genericType, Annotation[] annotations, MediaType mediaType,
MultivaluedMap<String, Object> httpHeaders, OutputStream entityStream)
throws IOException, WebApplicationException
{
// Check if we received a valid 'configuration' query parameter
String configurationName =
uriInfo.getQueryParameters().getFirst("configuration");
if (configurationName != null && !configurationName.trim().equals(""))
{
// Get the map of configuration objects from the servlet context.
Map<String, Map<String, Configuration>> formatsMap =
(Map<String, Map<String, Configuration>>)
context.getAttribute("configurations");
// Get the the sub-map for this writer/provider.
Map<String, Configuration> namesMap = formatsMap.get("rss");
// Get the configuration object from the map using the supplied parameter.
Configuration configuration = namesMap.get(configurationName);
if (configuration != null)
{
...
}
}
...
}
...
{code}
I have a basic example working quite well for RSS, so I'm hoping to supply a
full patch before Monday's deadline.
Ross
> Make the content writers configurable for the JAX-RS service
> ------------------------------------------------------------
>
> Key: OODT-613
> URL: https://issues.apache.org/jira/browse/OODT-613
> Project: OODT
> Issue Type: Sub-task
> Components: product server
> Affects Versions: 0.6
> Reporter: Ross Laidlaw
> Assignee: Ross Laidlaw
> Labels: gsoc2013
> Fix For: 0.7
>
>
> Allow the content writers implemented in OODT-612, e.g. the RDF and RSS
> writers, to be configured via configuration files (e.g. XML files). This
> feature is available for the RDF and RSS servlets in the original web
> application.
--
This message is automatically generated by JIRA.
If you think it was sent incorrectly, please contact your JIRA administrators
For more information on JIRA, see: http://www.atlassian.com/software/jira