ewg118/numishare

How to get collection items displayed in a conceptual numishare instance

Closed this issue · 7 comments

I have setup a conceptual numishare instance for a medieval coins of a certain mint.
I have setup a collection numishare instance for a collection which uses above instance for the references. So it displays the data from the conceptual instance in the collection instance.

But what needs to be done to display the coin from the collection if I browse in the conceptual instance for a specific coin?
So I want to have it similar to OCRE, like:

http://numismatics.org/ocre/id/ric.1(2).aug.230

which displays the specimen of the collection of the ANS.
Do I need to setup my own nomisma instance?

You don't need to set up Nomisma locally to do it, but you do need to set up a SPARQL endpoint. Apache Fuseki is the easiest thing to get up and running, in my opinion. In the Numishare configuration for your conceptual instance, you would need to update the sparql_endpoint with the URL of your endpoint, which can be running at localhost, e.g., http://localhost:8080/fuseki/nomisma/query

In order for the link between coin and type to work correctly, you'll need to upload the RDF export (and VoID dataset metadata RDF) from your collection Numishare instance, your conceptual Numishare instance, and also probably the nightly RDF dump from Nomisma.org into the SPARQL endpoint. Fuseki has an HTML UI that will allow you to upload these files into your endpoint, so you don't need to prop up the Nomisma framework as a piece of middleware.

See instructions at https://jena.apache.org/documentation/fuseki2/fuseki-webapp.html about running Fuseki as a service or web application in Tomcat.

Again, a very fast response. That sounds promising and easy.
I setup fuseki (http://fuseki:3030) and created a dataset "myfuseki".
I updated SPARQL Endpoint for the conceptual instance to: "http://fuseki:3030/myfuseki"
I created two rdf files, one from the collection, one from the concept instance.
I uploaded both files into the dataset.
I can see rdf data by:
http://fuseki:3030/myfuseki

It looks like:
`@prefix rdfs: http://www.w3.org/2000/01/rdf-schema# .
@Prefix edm: http://www.europeana.eu/schemas/edm/ .
@Prefix geo: http://www.w3.org/2003/01/geo/wgs84_pos# .
@Prefix nmo: http://nomisma.org/ontology# .
@Prefix oa: http://www.w3.org/ns/oa# .
@Prefix rdf: http://www.w3.org/1999/02/22-rdf-syntax-ns# .
@Prefix doap: http://usefulinc.com/ns/doap# .
@Prefix dcterms: http://purl.org/dc/terms/ .
@Prefix pelagios: http://pelagios.github.io/vocab/terms# .
@Prefix relations: http://pelagios.github.io/vocab/relations# .
@Prefix foaf: http://xmlns.com/foaf/0.1/ .
@Prefix nm: http://nomisma.org/id/ .

http://localhost:8081/orbeon/numishare/koeln/
a void:Dataset ;
dcterms:description "A short description of the collection." ;
dcterms:license http://opendatacommons.org/licenses/odbl/ ;
dcterms:publisher "koeln" ;
dcterms:rights http://rightsstatements.org/vocab/InC/1.0/ ;
dcterms:title "Die Münzen und Medaillen von Köln" ;
void:dataDump http://localhost:8081/orbeon/numishare/koeln/nomisma.rdf ;
void:documents "" ;
void:uriSpace "http://localhost:8081/orbeon/numishare/koeln/id/" .

...
http://localhost:8081/orbeon/numishare/srm/id/srm.20081212-026
a nmo:NumismaticObject ;
nmo:hasAxis 12 ;
nmo:hasDiameter 2.73 ;
nmo:hasObverse http://localhost:8081/orbeon/numishare/srm/id/srm.20081212-026#obverse ;
nmo:hasReverse http://localhost:8081/orbeon/numishare/srm/id/srm.20081212-026#reverse ;
nmo:hasTypeSeriesItem http://localhost:8081/orbeon/numishare/koeln/id/koeln.2.eb_koeln.0061 ;
nmo:hasWeight 3.937 ;
dcterms:identifier "srm.20081212-026" ;
dcterms:title "SRM-026"@en ;
void:inDataset http://localhost:8081/orbeon/numishare/srm/ .

http://localhost:8081/orbeon/numishare/srm/id/srm.20081212-026#obverse
foaf:depiction http://localhost:10206/srm/jpg/srm.20081212-026.1.jpg/full/350,/0/default.jpg ;
foaf:thumbnail http://localhost:10206/srm/jpg/srm.20081212-026.1.jpg/full/175,/0/default.jpg .

http://localhost:10206/srm/jpg/srm.20081212-026.1.jpg/full/350,/0/default.jpg
a edm:WebResource ;
dcterms:isReferencedBy http://localhost:10206/srm/jpg/srm.20081212-026.1.jpg/info.json ;
svcs:has_service http://localhost:10206/srm/jpg/srm.20081212-026.1.jpg .

http://localhost:8081/orbeon/numishare/srm/id/srm.20081212-026#reverse
foaf:depiction http://localhost:10206/srm/jpg/srm.20081212-026.2.jpg/full/350,/0/default.jpg ;
foaf:thumbnail http://localhost:10206/srm/jpg/srm.20081212-026.2.jpg/full/175,/0/default.jpg .

http://localhost:10206/srm/jpg/srm.20081212-026.2.jpg/full/350,/0/default.jpg
a edm:WebResource ;
dcterms:isReferencedBy http://localhost:10206/srm/jpg/srm.20081212-026.2.jpg/info.json ;
svcs:has_service http://localhost:10206/srm/jpg/srm.20081212-026.2.jpg .

http://localhost:10206/srm/jpg/srm.20081212-026.1.jpg
a svcs:Service ;
dcterms:conformsTo http://iiif.io/api/image ;
doap:implements http://iiif.io/api/image/2/level1.json .

http://localhost:10206/srm/jpg/srm.20081212-026.2.jpg
a svcs:Service ;
dcterms:conformsTo http://iiif.io/api/image ;
doap:implements http://iiif.io/api/image/2/level1.json .

...
`

Once I browser to:
http://localhost:8081/orbeon/numishare/koeln/id/koeln.2.eb_koeln.0061
I do see the regular conceptual page with the info for the coin. There are two new links at the top:

Examples of this type | Quantitative Analysis

At the bottom, below the regular info, I do see:

===
Quantitative Analysis

Average measurements for this coin type:

Diameter
1.97

Measurement Analysis
Analysis Type
Average
Standard Deviation
Select Measurement

Select the measurement type below for visualization. Measurement queries are executed across all coins harvested in Nomisma.org, regardless connection to coin type URIs.
Compare to other Queries (optional)

You can compare multiple queries to generate a more complex chart. Note that the value for each category for comparison is refined by previous selections in that group. For example, if the first category in a Group is "Denomination: Denarius", and Mint is select as the second category, the drop-down menu will include only those mints that produced denarii. Add Query

So, one step ahead. But where are the thumbnails and the basic info for the speciman?
The console of fuseki doesn't show an error. But the orbeon shows an error:

`2021-12-20 20:06:11,149 INFO lifecycle - event: {"request": "90", "session": "CB831A6906FD0F6A51F1D37545E86954", "source": "service", "message": "start: handle", "path": "/numishare/koeln/apis/getMetrical", "method": "GET"}
2021-12-20 20:06:11,149 INFO ProcessorService - /numishare/koeln/apis/getMetrical - Received request
2021-12-20 20:06:11,170 INFO ProcessorService - /numishare/koeln/apis/getMetrical - Timing: 21
2021-12-20 20:06:11,171 INFO lifecycle - event: {"request": "90", "session": "CB831A6906FD0F6A51F1D37545E86954", "source": "service", "message": "end: handle", "time": "22 ms"}
2021-12-20 20:06:11,176 ERROR PageFlowControllerProcessor - error caught {controller: "oxf:/apps/numishare/page-flow.xml", method: "GET", path: "/numishare/koeln/id/koeln.2.eb_koeln.0061"}
2021-12-20 20:06:11,178 ERROR PageFlowControllerProcessor -
+----------------------------------------------------------------------------------------------------------------------+

An Error has Occurred
There is no
----------------------------------------------------------------------------------------------------------------------
Application Call Stack
----------------------------------------------------------------------------------------------------------------------
oxf:/apps/numishare/page-flow.xml
······················································································································
element=<page path="/numishare/[^\/]+/id/(.*)$" model="xpl/models/object/get-id.xpl" view="xpl/controllers/conneg-id.x
view =xpl/controllers/conneg-id.xpl
----------------------------------------------------------------------------------------------------------------------
oxf:/apps/numishare/xpl/controllers/conneg-id.xpl
······················································································································
element=<p:output name="data" ref="data"/>
name =data
ref =data
----------------------------------------------------------------------------------------------------------------------
oxf:/apps/numishare/xpl/views/serializations/object/html.xpl
······················································································································
element=<p:output name="data" ref="data"/>
name =data
ref =data
----------------------------------------------------------------------------------------------------------------------
oxf:/apps/numishare/xpl/views/serializations/object/html.xpl
······················································································································
element=<p:output name="data" ref="data"/>
name =data
ref =data
----------------------------------------------------------------------------------------------------------------------
----------------------------------------------------------------------------------------------------------------------
Exception: org.orbeon.oxf.common.ValidationException
----------------------------------------------------------------------------------------------------------------------
g.orbeon.oxf.processor.pipeline.PipelineProcessor$1
g.orbeon.oxf.processor.pipeline.PipelineProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
org.orbeon.oxf.processor.impl.ProcessorOutputImpl
org.orbeon.oxf.processor.ProcessorImpl
orbeon.oxf.processor.pipeline.PipelineProcessor$1$1
org.orbeon.oxf.processor.pipeline.PipelineProcessor
org.orbeon.oxf.processor.pipeline.PipelineProcessor
g.orbeon.oxf.processor.pipeline.PipelineProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
org.orbeon.oxf.processor.impl.ProcessorOutputImpl
processor.pipeline.choose.ConcreteChooseProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
org.orbeon.oxf.processor.impl.ProcessorOutputImpl
org.orbeon.oxf.processor.ProcessorImpl
orbeon.oxf.processor.pipeline.PipelineProcessor$1$1
org.orbeon.oxf.processor.pipeline.PipelineProcessor
org.orbeon.oxf.processor.pipeline.PipelineProcessor
g.orbeon.oxf.processor.pipeline.PipelineProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
org.orbeon.oxf.processor.impl.ProcessorOutputImpl
processor.pipeline.choose.ConcreteChooseProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
org.orbeon.oxf.processor.impl.ProcessorOutputImpl
org.orbeon.oxf.processor.ProcessorImpl
orbeon.oxf.processor.pipeline.PipelineProcessor$1$1
org.orbeon.oxf.processor.pipeline.PipelineProcessor
org.orbeon.oxf.processor.pipeline.PipelineProcessor
g.orbeon.oxf.processor.pipeline.PipelineProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
org.orbeon.oxf.processor.impl.ProcessorOutputImpl
org.orbeon.oxf.processor.ProcessorImpl
orbeon.oxf.processor.pipeline.PipelineProcessor$1$1
org.orbeon.oxf.processor.pipeline.PipelineProcessor
org.orbeon.oxf.processor.pipeline.PipelineProcessor
g.orbeon.oxf.processor.pipeline.PipelineProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
org.orbeon.oxf.processor.impl.ProcessorOutputImpl
processor.pipeline.choose.ConcreteChooseProcessor$1
essor.impl.ProcessorOutputImpl$TopLevelOutputFilter
---8<--------8<--------8<--------8<--------8<--------8<--------8<--------8<--------8<--------8<--------8<--------8<---
org.orbeon.oxf.servlet.OrbeonServlet
scala.runtime.java8.JFunction0$mcV$sp
org.orbeon.oxf.util.DynamicVariable
org.orbeon.oxf.webapp.ProcessorService$
org.orbeon.oxf.servlet.OrbeonServlet
javax.servlet.http.HttpServlet
org.apache.catalina.core.ApplicationFilterChain
org.apache.catalina.core.ApplicationFilterChain
org.apache.tomcat.websocket.server.WsFilter
org.apache.catalina.core.ApplicationFilterChain
org.apache.catalina.core.ApplicationFilterChain
org.orbeon.oxf.servlet.FormRunnerAuthFilter
org.apache.catalina.core.ApplicationFilterChain
org.apache.catalina.core.ApplicationFilterChain
org.orbeon.oxf.servlet.LimiterFilter
scala.runtime.java8.JFunction0$mcV$sp
org.orbeon.oxf.logging.LifecycleLogger$
org.orbeon.oxf.servlet.LimiterFilter
org.orbeon.oxf.servlet.LimiterFilter
scala.Option
org.orbeon.oxf.servlet.LimiterFilter
org.apache.catalina.core.ApplicationFilterChain
org.apache.catalina.core.ApplicationFilterChain
org.apache.catalina.core.StandardWrapperValve
org.apache.catalina.core.StandardContextValve
org.apache.catalina.authenticator.AuthenticatorBase
org.apache.catalina.core.StandardHostValve
org.apache.catalina.valves.ErrorReportValve
org.apache.catalina.valves.AbstractAccessLogValve
org.apache.catalina.core.StandardEngineValve
org.apache.catalina.connector.CoyoteAdapter
org.apache.coyote.http11.Http11Processor
org.apache.coyote.AbstractProcessorLight
rg.apache.coyote.AbstractProtocol$ConnectionHandler
.apache.tomcat.util.net.NioEndpoint$SocketProcessor
org.apache.tomcat.util.net.SocketProcessorBase
org.apache.tomcat.util.threads.ThreadPoolExecutor
pache.tomcat.util.threads.ThreadPoolExecutor$Worker
che.tomcat.util.threads.TaskThread$WrappingRunnable
java.lang.Thread
+----------------------------------------------------------------------------------------------------------------------+
2021-12-20 20:06:11,179 ERROR PageFlowControllerProcessor - error caught {controller: "oxf:/page-flow.xml", method: "GET", path: "/numishare/koeln/id/koeln.2.eb_koeln.0061"}
2021-12-20 20:06:11,181 ERROR PageFlowControllerProcessor -`

...

Do you have any idea?

I forgot one thing:

The "Type Series" in the admin interface of the conceptual instance is set to:

"http://localhost:8080/orbeon/numishare/nix/"

which does not really exist. I entered this because it is required and there is no "type series" in nomisma for my purpose. Maybe this is the root cause.

The "Type Series" URI shouldn't affect any of the queries in Numishare.

The SPARQL query that generates the examples section is here: https://github.com/ewg118/numishare/blob/master/ui/sparql/type-examples.sparql

I'm looking at your VoID and your coin example RDF, and it seems fine to me. The "Examples of this Type" heading wouldn't appear on the top of the page if the underlying ASK SPARQL query had resulted in 'false', so there must be something else missing, but I don't see what.

The SPARQL query above requires a dcterms:title for the object and a dcterms:title and dcterms:publisher for the dataset. As long as you uploaded the dataset VoID metadata into the endpoint, the query should result have a result.

You could try the following query in your endpoint:

?object nmo:hasTypeSeriesItem <http://localhost:8081/orbeon/numishare/koeln/id/koeln.2.eb_koeln.0061> ;
dcterms:title ?title .

If that works, then try adding the lines from the above SPARQL query, one by one, starting with OPTIONAL { ?object dcterms:identifier ?identifier} until the query yields no response. Then you'll know what might be missing.

You can ignore the Orbeon error. This is a result of a really non-standard way of using the XML Pipelines to attach an HTTP Link Header for multiple profiles of the same serialization (https://numishare.blogspot.com/2020/08/first-pass-at-mapping-nomismaorg-to.html)

Your described procedure showed the missing piece. It was related to:

?object void:inDataset ?dataset . ?dataset dcterms:publisher ?publisher FILTER (lang(?publisher) = "" || langMatches(lang(?publisher), "en")) . ?dataset dcterms:title ?datasetTitle FILTER (lang(?datasetTitle) = "" || langMatches(lang(?datasetTitle), "en")) .

I uploaded Void from the conceptual instance but not the Void from the collection. After I uploaded the void from the collection all looks fine. Now I do see the thumbnails of the specimen on the pages of the conceptual instance.

Great! Thank you very much.

Ah, yes. In the case that the coin isn't linked to a collection URI, as defined by Nomisma, the query will default to displaying the dataset title. I had to implement this for the Portable Antiquities Scheme dataset, where none of the coins were linked to a collection, but I needed to display some sort of source for the data.