Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Multiple Geolocating Assertions #140

Closed
thehabes opened this issue Mar 5, 2020 · 3 comments
Closed

Multiple Geolocating Assertions #140

thehabes opened this issue Mar 5, 2020 · 3 comments
Assignees

Comments

@thehabes
Copy link
Contributor

thehabes commented Mar 5, 2020

Multiple Geocoding Assertions

(Provide link to index.md of the issue, if available. To be filled in after issue is created - you need the issue number!)

Use case

SLU is using geographic Annotations to describe JSON-LD resources. We use mapping tools like Leaflet to render these Annotations into meaningful interfaces. The general use case is I know the JSON-LD URI of some data resource. I may own the database in which it presides, I may own the resources, or it may be entirely third party. The resource might not be IIIF, but for our purposes here say that it is. I have geographic information, which may include some metadata beyond geographic coordinates, that applies to this resource. In this case, I have a multitude of geographic data to describe this resource (its origin, its demise, etc.). I would like to make multiple geographic assertions about this single resource in a IIIF compliant manner.

Further Information

This is originating from the IIIF + Maps conference, the original issue can be found at IIIF/iiif-stories#119.

This recipe is an extension of #139.

@thehabes thehabes self-assigned this Mar 5, 2020
@thehabes thehabes changed the title Multiple Geocoding Annotations Multiple Geocoding Assertions Mar 5, 2020
@thehabes
Copy link
Contributor Author

thehabes commented Mar 5, 2020

There are multiple ways to do this depending on your situation. If you own the resource, you can either add a service block containing the geocoding information to the resource directly, or you can choose to annotate the resource.

If you choose to annotate, here is what that looks like in Presentation API 3

{
   "id":"https://example.com/annotation/12345",
   "type":"Annotation",
   "@context":"http://iiif.io/api/presentation/3/context.json",
   "motivation":"geocode",
   "body":{
      "id":"https://example.org/geojson/id/123",
      "@context":"http://geojson.org/geojson-ld/geojson-context.jsonld",
      "type":"Feature",
      "properties":{
         "label":"String this geometry node should use as a label.",
         "description":"Some description to go along with node."
      },
      "geometry":{
         "type":"Point",
         "coordinates":[
            7,
            7
         ]
      }
   },
   "target":"https://iiif.example.org/canvas/123"
}

You can target the same resource with many of these Annotations that represent separate geographic assertions. You can also create an AnnotationPage that contains all the annotations and include that directly on the resource.

{
   "id":"https://iiif.example.org/canvas/123",
   "type":"Canvas",
   "@context":"http://iiif.io/api/presentation/3/context.json",
   "label":{
      "none":[
         "pg. 2"
      ]
   },
   "height":1000,
   "width":750,
   "items":[

   ],
   "annotations":[
      {
         "@context":"http://iiif.io/api/presentation/3/context.json",
         "id":"https://example.org/iiif/annopage/123",
         "type":"AnnotationPage",
         "items":[
            {
               "id":"https://example.com/annotation/12345",
               "type":"Annotation",
               "@context":"http://iiif.io/api/presentation/3/context.json",
               "motivation":"geocode",
               "body":{
                  "id":"https://example.org/geojson/id/123",
                  "@context":"http://geojson.org/geojson-ld/geojson-context.jsonld",
                  "type":"Feature",
                  "properties":{
                     "label":"String this geometry node should use as a label.",
                     "description":"Some description to go along with node."
                  },
                  "geometry":{
                     "type":"Point",
                     "coordinates":[
                        7,
                        7
                     ]
                  }
               },
               "target":"https://iiif.example.org/canvas/123"
            },
            .
            .
            .
         ]
      }
   ]
}

It is a little trickier with presentation 2, since the atomic annotation is not as supported. You would have to make an AnnotationList containing the information and place it into the otherContent field of the resource.

{
   "@context":"http://iiif.io/api/presentation/2/context.json",
   "@id":"http://example.org/iiif/book1/canvas/p1",
   "@type":"sc:Canvas",
   "label":"p. 1",
   "height":1000,
   "width":750,
   "images":[

   ],
   "otherContent":[
      {
         "@id":"http://example.org/annolist/123",
         "@context":"http://iiif.io/api/presentation/2/context.json",
         "@type":"sc:AnnotationList",
         "resources":[
            {
               "@type":"oa:Annotation",
               "motivation":"geocode",
               "resource":{
                  "@id":"https://example.org/geojson/id/123",
                  "@context":"http://geojson.org/geojson-ld/geojson-context.jsonld",
                  "@type":"Feature",
                  "properties":{
                     "label":"String this geometry node should use as a label.",
                     "description":"Some description to go along with node."
                  },
                  "geometry":{
                     "type":"Point",
                     "coordinates":[
                        7,
                        7
                     ]
                  }
               },
               "on":"https://iiif.example.org/canvas/123"
            },
             .
             .
             .
         ]
      }
   ]
}

If you choose to implement using a service, here is what that looks like in Presentation 3

{
   "id":"https://example.org/iiif/book1/canvas/p2",
   "type":"Canvas",
   "@context":"http://iiif.io/api/presentation/3/context.json",
   "label":{
      "none":[
         "pg. 2"
      ]
   },
   "height":1000,
   "width":750,
   "items":[

   ],
   "service":[
      {
         "id":"https://example.org/geo/service/point(7,7)&format=geojson",
         "type":"GeoJSON_Serivce",
         "profile":"http://geojson.org/geojson-spec.html",
         "@context":"http://geojson.org/geojson-ld/geojson-context.jsonld",
         "properties":{
            "type":"Feature",
            "label":"String this geometry node should use as a label.",
            "description":"Some description to go along with node.",
            "motivation":"geocode"
         },
        "geometry":{
               "type":"Point",
               "coordinates":[
                  7,
                  7
               ]
            }
      },
      .
      .
      .
   ]
}

This has a small issue with how type clashes, but we can handle that within properties. However, that means FeatureCollections could not be used here, since FeatureCollections must not have properties. There would be no way to reconcile the type conflict. It is recommended the service return an array of Features here instead of a FeatureCollection.

This is what that service block looks like in Presentation 2. It is a bit different since service is not an array. That means your service will need to return a single FeatureCollection containing all the geographic data Features.

{
   "@context":"http://iiif.io/api/presentation/2/context.json",
   "@id":"http://example.org/iiif/book1/canvas/p1",
   "@type":"sc:Canvas",
   "label":"p. 1",
   "height":1000,
   "width":750,
   "images":[

   ],
   "otherContent":[

   ],
   "service":{
      "@id":"https://example.org/geo/service/point-collection()&format=geojson",
      "@context":"http://geojson.org/geojson-ld/geojson-context.jsonld",
      "profile":"http://geojson.org/geojson-spec.html",
      "@type":"FeatureCollection",
      "features":[
         {
            "@type":"Feature",
            "properties":{
               "label":"String this geometry node should use as a label.",
               "description":"Some description to go along with node.",
               "motivation":"geocode"
            },
            "geometry":{
               "type":"Point",
               "coordinates":[
                  7,
                  7
               ]
            }
         }
      ]
   }
}

You will also notice I have chosen the geocode motivation. Proper extensions to motivation are still being discussed within the IIIF-Maps community.

Note that geometry can be more than just a Point.

Note that properties is a very generic field. This community should seek to put some rails on what goes into that field. If, for example, the targeted resource has a label and the properties field contains a label, the consuming interface must make a choice on which to preference for UI/UX purposes. This could be a way to inject, override or extend resource properties.

Note that target values can include hash or SVG selectors. This would allow someone to annotate a portion/slice/frame/fragment of a resource.

@thehabes
Copy link
Contributor Author

Going to focus this recipe as a solution for IIIF/iiif-stories#116 using IIIF Annotation Page(s).

@thehabes thehabes changed the title Multiple Geocoding Assertions Multiple Geolocating Assertions Jun 2, 2020
@thehabes
Copy link
Contributor Author

This variation is too similar to #139 and will not be implemented.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant