Copyright © 2015 W3C ® ( MIT , ERCIM , Keio , Beihang ). W3C liability , trademark and document use rules apply.
This document defines the procedures and rules to be applied when converting tabular data into JSON. Tabular data may be complemented with metadata annotations that describe its structure, the meaning of its content and how it may form part of a collection of interrelated tabular data. This document specifies the effect of this metadata on the resulting JSON.
This section describes the status of this document at the time of its publication. Other documents may supersede this document. A list of current W3C publications and the latest revision of this technical report can be found in the W3C technical reports index at http://www.w3.org/TR/.
The CSV on the Web Working Group was chartered to produce Recommendations for "Access methods for CSV Metadata", "Metadata vocabulary for CSV data" and "Mapping mechanism to transforming CSV into various Formats (e.g., RDF, JSON, or XML)". This document aims to satisfy the JSON variant of the mapping Recommendation.
This
document
was
published
by
the
CSV
on
the
Web
Working
Group
as
a
Working
Draft.
Candidate
Recommendation.
This
document
is
intended
to
become
a
W3C
Recommendation.
If
you
wish
to
make
comments
regarding
this
document,
please
send
them
to
public-csv-wg@w3.org
(
subscribe
,
archives
).
W3C
publishes
a
Candidate
Recommendation
to
indicate
that
the
document
is
believed
to
be
stable
and
to
encourage
implementation
by
the
developer
community.
This
Candidate
Recommendation
is
expected
to
advance
to
Proposed
Recommendation
no
earlier
than
30
October
2015.
All
comments
are
welcome.
Please see the Working Group's implementation report .
Publication
as
a
Working
Draft
Candidate
Recommendation
does
not
imply
endorsement
by
the
W3C
Membership.
This
is
a
draft
document
and
may
be
updated,
replaced
or
obsoleted
by
other
documents
at
any
time.
It
is
inappropriate
to
cite
this
document
as
other
than
work
in
progress.
This document was produced by a group operating under the 5 February 2004 W3C Patent Policy . W3C maintains a public list of any patent disclosures made in connection with the deliverables of the group; that page also includes instructions for disclosing a patent. An individual who has actual knowledge of a patent which the individual believes contains Essential Claim(s) must disclose the information in accordance with section 6 of the W3C Patent Policy .
This document is governed by the 1 August 2014 W3C Process Document .
This document describes the processing of tabular data to create a set of nested objects that MUST be serialized as JSON [ RFC7159 ].
The conversion of CSV content to JSON is intended for web developers who need not care about the complexities of RDF [ rdf11-concepts ]. Where the formality of RDF is required, [ csv2rdf ] provides the procedures for mapping from CSV content to RDF which may be serialized to [ json-ld ].
The [ tabular-data-model ] defines an annotated tabular data model consisting of tables , columns , rows , and cells , enriched with annotations that describe the structure of the tabular data and the meaning of its content. A group of tables is a collection of tables published as a single atomic unit.
The conversion procedure described in this specification operates on the annotated tabular data model . This specification does not specify the processes needed to convert CSV-encoded data into tabular data form. Please refer to [ tabular-data-model ] for details of parsing tabular data .
Conversion applications MUST provide at least two modes of operation: standard and minimal .
Standard mode conversion frames the information gleaned from the cells of the tabular data with details of the rows , tables , and a group of tables within which that information is provided.
Minimal mode conversion includes only the information gleaned from the cells of the tabular data within the output.
Standard and minimal conversion are described normatively below .
Conversion applications MAY offer additional implementation specific conversion modes.
Transformation definitions , as defined in [ tabular-metadata ] MAY be used to specify how tabular data can be transformed into another format using a script or template. Such transformation definitions MAY use the JSON output described in this specification as input.
As well as sections marked as non-normative, all authoring guidelines, diagrams, examples, and notes in this specification are non-normative. Everything else in this specification is normative.
The key words MAY and MUST are to be interpreted as described in [ RFC2119 ].
Tabular data MUST conform to the description from [ tabular-data-model ]. In particular note that each row MUST contain the same number of cells (although some of these cells may be empty).
Not all CSV-encoded data can be parsed into a tabular data model. An algorithm for parsing CSV-based files is described in [ tabular-data-model ].
The following typographic conventions are used in this specification:
markup
markup
definition
reference
markup
external
definition
reference
Notes are in light green boxes with a green left border and with a "Note" header in green. Notes are normative or informative depending on the whether they are in a normative or informative section, respectively.
Examples are in light khaki boxes, with khaki left border, and with a numbered "Example" header in khaki. Examples are always informative. The content of the example is in monospace font and may be syntax colored.
The procedures for converting tabular data into JSON are described below for both standard and minimal modes.
null
or
a
sequence
of
values.
notes
property.
This
may
be
an
empty
list.
null
.
A conformant JSON conversion application MUST produce output conforming to this algorithm according to the chosen mode of conversion: standard or minimal .
Where an annotated table is defined in isolation (e.g. in the absence of a group of tables ), a default group of tables is provided with a single tables annotation that refers to the given table .
The [ tabular-data-model ] specifies that string values within tabular data (such as column titles or cell string values ) MUST contain only Unicode characters. No Unicode normalization (as specified in [ UAX15 ]) is applied to these string values during the conversion to JSON.
The steps in the algorithm defined here apply to minimal mode.
Insert an empty array A into the JSON output. The objects containing the name-value pairs associated with the cell values will be subsequently inserted into this array .
Each
table
is
processed
sequentially
in
the
order
they
are
referenced
in
the
group
of
tables
.
For
each
table
where
the
suppress
output
annotation
is
false
:
Each row within the table is processed sequentially in order. For each row in the current table :
Generate a sequence of objects , S 1 to S n , each of which corresponds to a subject described by the current row , as described in 4.3 Generating Objects .
As described in 4.4 Generating Nested Objects , process the sequence of objects , S 1 to S n , to produce a new sequence of root objects , S R 1 to S R m , that MAY include nested objects .
The steps in the algorithm defined here apply to standard mode.
Insert an empty object G into the JSON output which is associated with the group of tables .
If the group of tables has an identifier I G ; insert the following name-value pair into object G :
@id
Insert any notes and non-core annotations specified for the group of tables into object G according to the rules provided in 5. JSON-LD to JSON .
Insert the following name-value pair into object G :
table
tables
where A T is an array into which the objects describing the annotated tables will be subsequently inserted.
Each table is processed sequentially in the order they are referenced in the group of tables .
For
each
table
where
the
suppress
output
annotation
is
false
:
Insert an empty object T into the array A T to represent the table .
If the table has an identifier I T ; insert the following name-value pair into object T :
@id
Specify the source tabular data file URL for the current table based on the url annotation; insert the following name-value pair into object T :
url
Insert any notes and non-core annotations specified for the table into object T according to the rules provided in 5. JSON-LD to JSON .
All other core annotations for the table are ignored during the conversion; including information about table schemas and columns specified therein, foreign keys , table direction , transformations etc.
Insert the following name-value pair into object T :
row
where A R is an array into which the objects describing the rows will be subsequently inserted.
Each row within the table is processed sequentially in order. For each row in the current table :
Insert an empty object R into the array A R to represent the row .
Specify the row number n for the row ; insert the following name-value pair into object R :
rownum
Specify
the
row
source
number
n
source
for
the
row
within
the
source
tabular
data
file
URL
using
a
fragment-identifier
as
specified
in
[
RFC7111
];
if
row
source
number
is
not
null
,
insert
the
following
name-value
pair
into
object
R
:
url
#row=
n
source
Specify
any
titles
for
the
row
;
if
row
titles
is
not
null
,
insert
the
following
name-value
pair
into
object
R
:
titles
where t is the single value or array of values provided by the row titles annotation.
JSON has no native support for expressing language information; therefore any such information associated with the row titles is ignored.
Insert any non-core annotations specified for the row into object R according to the rules provided in 5. JSON-LD to JSON .
Insert the following name-value pair into object R :
describes
where A is an array . The objects containing the name-value pairs associated with the cell values will be subsequently inserted into this array .
Generate a sequence of objects , S 1 to S n , each of which corresponds to a subject described by the current row , as described in 4.3 Generating Objects .
As described in 4.4 Generating Nested Objects , process the sequence of objects , S 1 to S n , to produce a new sequence of root objects , S R 1 to S R m , that MAY include nested objects .
The steps in the algorithm defined here apply to both standard and minimal modes.
This algorithm generates a sequence of objects , S 1 to S n , each of which corresponds to a subject described by the current row . The algorithm inserts name-value pairs into S i depending on the cell values as outlined in the following steps.
Determine the unique subjects for the current row . The subject(s) described by each row are determined according to the about URL annotation for each cell in the current row . A default subject for the row is used for any cells where about URL is undefined.
For
each
subject
that
the
current
row
describes
where
at
least
one
of
the
cells
that
refers
to
that
subject
has
a
value
or
value
URL
that
is
not
null
,
and
is
associated
with
a
column
where
suppress
output
annotation
is
false
:
Create an empty object S i to represent the subject i .
( i is the index number with values from 1 to n , where n is the number of subjects for the row )
Subject
i
is
identified
according
to
the
about
URL
annotation
of
its
associated
cells
:
I
S
.
For
a
default
subject
where
about
URL
is
not
specified
by
its
cells
,
I
S
is
null
.
If
the
identifier
for
subject
i
,
I
S
,
is
not
null
,
then
insert
the
following
name-value
pair
into
object
S
i
:
@id
Each cell referring to subject i is then processed sequentially according to the order of the columns .
For
each
cell
referring
to
subject
i
,
where
the
suppress
output
annotation
for
the
column
associated
with
that
cell
is
false
,
insert
a
name-value
pair
into
object
S
i
as
described
below:
If
the
value
of
property
URL
for
the
cell
is
not
null
,
then
name
N
takes
the
value
of
property
URL
compacted
according
to
the
rules
as
defined
in
URL
Compaction
in
[
tabular-metadata
].
Else, name N takes the URI decoded value of the name annotation for the column associated with the cell . (URI decoding is necessary as name may have been encoded if it was taken from a supplied title.)
If
the
value
URL
for
the
current
cell
is
not
null
,
then
insert
the
following
name-value
pair
into
object
S
i
:
where
V
url
is
the
value
of
value
URL
annotation
for
the
current
cell
expressed
as
a
string
in
the
JSON
output.
If
N
is
@type
,
compact
V
url
according
to
the
rules
as
defined
in
URL
Compaction
in
[
tabular-metadata
].
Else, if the cell value is a list that is not empty, then the cell value provides a sequence of values for inclusion within the JSON output; insert an array A v containing each value V of the sequence into object S i :
Each of the values V derived from the sequence MUST be expressed in the JSON output according to the datatype of V as defined below in section 4.5 Interpreting datatypes .
Else,
if
the
cell
value
is
not
null
,
then
the
cell
value
provides
a
single
value
V
for
inclusion
within
the
JSON
output;
insert
the
following
name-value
pair
into
object
S
i
:
Value V derived from the cell values MUST be expressed in the JSON output according to the datatype of the value as defined in section 4.5 Interpreting datatypes .
If name N occurs more than once within object S i , the name-value pairs from each occurrence of name N MUST be compacted to form a single name-value pair with name N and whose value is an array containing all values from each of those name-value pairs.
The steps in the algorithm defined herein apply to both standard and minimal modes.
Where the current row describes multiple subjects , it MAY be possible to organise the objects associated with those subjects such that some objects are nested within others; e.g. where the value URL annotation for one cell matches the about URL annotation for another cell in the same row . This algorithm considers a sequence of objects generated according to 4.3 Generating Objects , S 1 to S n , each of which corresponds to a subject described by the current row . It generates a new sequence of root objects , S R 1 to S R m , that MAY include nested objects .
Where the current row describes only a single subject , this algorithm may be bypassed as no nesting is possible. In such a case, the root object S R 1 is identical to the original object S 1 .
This nesting algorithm is based on the interrelationships between subjects described within a given row that are specified using the value URL annotation. Cell values expressing the identity of a subject in the current row (i.e., as a simple literal) will be ignored by this algorithm.
The algorithm uses the following terms:
The nesting algorithm is defined as follows:
For all cells in the current row , determine the value URLs , V url , that occur only once . The list of these uniquely occurring value URLs is referred to as the URL-list .
Create an empty forest F . Vertices in the trees of this forest represent the subjects described by the current row .
For each object S i in the sequence S 1 to S n :
Determine
the
identity
of
object
S
i
:
I
S
.
If
present
in
object
S
i
,
the
name-value
pair
with
name
@id
provides
the
value
of
I
S
.
Else,
object
S
i
is
not
explicitly
identified
and
I
S
is
null
.
Check whether there is a vertex N in forest F that represents object S i . If none of the existing vertices in forest F represent object S i , then insert a new tree into forest F whose root is a vertex N that represents object S i and has identity I S .
For all cells associated with the current object S i (e.g. whose about URL annotation matches I S ):
If the value URL annotation of the current cell is defined and its value, V url , appears in the URL-list , then check each of the other objects in the sequence S 1 to S n to determine if V url identifies one of those objects .
For
object
S
j
,
if
the
name-value
pair
with
name
@id
is
present
and
its
value
matches
V
url
,
then:
If the root of the tree containing vertex N is a vertex that represents object S j , then object S i is already a descendant of object S j ; no further action should be taken for this instance of V url .
This clause in the algorithm prevents circular loops being created.
Furthermore, because the URL-list contains value URLs that occur only once for the current row , object S i cannot be a descendant of an intermediate vertices in the tree .
Else, if there is a root vertex M in forest F that represents object S j , then set vertex M as a child of vertex N and remove vertex M from the list of roots in forest F (i.e., the tree rooted by M becomes a sub-tree of N ).
Else, create a new vertex M that represents object S j as a child of vertex N .
Each vertex in forest F represents an object in the original sequence of objects S 1 to S n and is associated with a subject described by the current row . Rearrange objects S 1 to S n such that they mirror the structure of the trees in forest F as follows: If vertex M , representing object S i , is a child of vertex N , representing object S j , then the name-value pair in object S j associated with the edge relating M and N MUST be modifed such that the (literal) value, V url , from that name-value pair is replaced by object S i thus creating a nested object .
An implementation may be able to optimize the algorithm by skipping branches (e.g. if URL-list is empty) or by other means.
Cell values are expressed in the JSON output according to the cell value's datatype . The relationship between the base annotation value of the cell value's datatype and the primitive types supported by JSON (as specified in [ RFC7159 ]) is provided in the table below.
Only the base annotation value is used to determine the primitive type used wihtin the JSON output. Additional restrictions to the cell value's datatype , such as the id annotation, are ignored for the purposes of conversion to JSON.
A datatype's format is irrelevant to the conversion procedure defined in this specification; the cell value has already been parsed from the contents the cell according to the format annotation.
Where the contents of the cell cannot be parsed, or other validation errors occur, cell errors will be provided. It is an implementation decision to determine how conversion applications should proceed in the event that cell errors are encountered.
datatype
|
JSON primitive type |
---|---|
anyAtomicType
|
string |
anyURI
|
string |
base64Binary
|
string |
boolean
|
boolean |
date
|
string |
dateTime
|
string |
dateTimeStamp
|
string |
decimal
|
number |
integer
|
number |
long
|
number |
int
|
number |
short
|
number |
byte
|
number |
nonNegativeInteger
|
number |
positiveInteger
|
number |
unsignedLong
|
number |
unsignedInt
|
number |
unsignedShort
|
number |
unsignedByte
|
number |
nonPositiveInteger
|
number |
negativeInteger
|
number |
double
|
number |
duration
|
string |
dayTimeDuration
|
string |
yearMonthDuration
|
string |
float
|
number |
gDay
|
string |
gMonth
|
string |
gMonthDay
|
string |
gYear
|
string |
gYearMonth
|
string |
hexBinary
|
string |
QName
|
string |
string
|
string |
normalizedString
|
string |
token
|
string |
language
|
string |
Name
|
string |
NMTOKEN
|
string |
xml
|
string |
html
|
string |
json
|
string |
time
|
string |
This section defines a mechanism for transforming the [ json-ld ] dialect used for non-core annotations and notes originating from the processing of metadata (as defined in [ tabular-metadata ]) into JSON.
Conversion applications may have other means to create annotated tables , e.g., through some application specific API-s. In such cases the exact format for non-core annotations or notes may be different. Specifications for such annotation processes should specify how these annotations should be converted into RDF.
Name-value pairs from notes and non-core annotations annotations are generally copied verbatim from the metadata description subject to the exceptions below:
Name-value
pairs
whose
value
is
an
object
using
the
[
json-ld
]
keyword
@value
,
for
example:
{
"@value":
"
V
"
}
are transformed to:
Name-value
pairs
occurring
within
the
value
object
that
use
[
json-ld
]
keywords
@language
and
@type
are
ignored.
Name-value
pairs
whose
value
is
an
object
using
the
[
json-ld
]
keyword
@id
to
coerce
a
string-value
to
be
interpreted
as
an
IRI,
for
example:
{
"@id":
"
V
url
"
}
are transformed to:
In
addition
to
compacting
values
of
property
URLs
,
URLs
which
ware
the
value
of
@type
used
within
the
notes
and
non-core
annotations
are
compacted
according
to
the
rules
as
defined
in
URL
Compaction
in
[
tabular-metadata
].
This section is non-normative.
Each of the examples expresses more complex conversions - it is recommended that readers of this specification work through the examples in sequential order.
This
example
comprises
a
single
annotated
table
containing
information
attributes
about
countries;
country
code,
position
(latitude,
longitude)
and
name.
Whilst
the
input
tabular
data
file,
published
at
http://example.org/countries.csv
,
includes
a
header
line
,
no
further
metadata
annotations
are
given.
The
tabular
data
file
is
provided
below:
countryCode,latitude,longitude,nameAD,42.546245,1.601554,Andorra AE,23.424076,53.847818,"United Arab Emirates" AF,33.93911,67.709953,AfghanistanAD,42.5,1.6,Andorra AE,23.4,53.8,"United Arab Emirates" AF,33.9,67.7,Afghanistan
The annotated table generated from parsing the tabular data file is shown below and provides the basis for the conversion to JSON.
Annotations for the resulting table T , with 4 columns and 3 rows, are shown below:
id | core annotations | ||
---|---|---|---|
url | columns | rows | |
T |
http://example.org/countries.csv
|
C1 , C2 , C3 , C4 | R1 , R2 , R3 |
Annotations for the columns , rows and cells in table T are shown in the tables below.
Column annotations:
id | core annotations | |||||
---|---|---|---|---|---|---|
table | number | source number | cells | name | titles | |
C1 | T | 1 | 1 | C1.1 , C2.1 , C3.1 |
countryCode
|
countryCode
|
C2 | T | 2 | 2 | C1.2 , C2.2 , C3.2 |
latitude
|
latitude
|
C3 | T | 3 | 3 | C1.3 , C2.3 , C3.3 |
longitude
|
longitude
|
C4 | T | 4 | 4 | C1.4 , C2.4 , C3.4 |
name
|
name
|
Row annotations:
id | core annotations | |||
---|---|---|---|---|
table | number | source number | cells | |
R1 | T | 1 | 2 | C1.1 , C1.2 , C1.3 , C1.4 |
R2 | T | 2 | 3 | C2.1 , C2.2 , C2.3 , C2.4 |
R3 | T | 3 | 4 | C3.1 , C3.2 , C3.3 , C3.4 |
Cell annotations:
id | core annotations | |||||
---|---|---|---|---|---|---|
table | column | row | string value | value | property URL | |
C1.1 | T | C1 | R1 |
"AD"
|
"AD"
|
null
|
C1.2 | T | C2 | R1 |
|
|
null
|
C1.3 | T | C3 | R1 |
|
|
null
|
C1.4 | T | C4 | R1 |
"Andorra"
|
"Andorra"
|
null
|
C2.1 | T | C1 | R2 |
"AE"
|
"AE"
|
null
|
C2.2 | T | C2 | R2 |
|
|
null
|
C2.3 | T | C3 | R2 |
|
|
null
|
C2.4 | T | C4 | R2 |
"United
Arab
Emirates"
|
"United
Arab
Emirates"
|
null
|
C3.1 | T | C1 | R3 |
"AF"
|
"AF"
|
null
|
C3.2 | T | C2 | R3 |
|
|
null
|
C3.3 | T | C3 | R3 |
|
|
null
|
C3.4 | T | C4 | R3 |
"Afghanistan"
|
"Afghanistan"
|
null
|
Minimal mode output for this example is provided below:
[{ "countryCode": "AD","latitude": "42.5", "longitude": "1.6", "name": "Andorra" }, { "countryCode": "AE","latitude": "23.4", "longitude": "53.8", "name": "United Arab Emirates" }, { "countryCode": "AF","latitude": "33.9", "longitude": "67.7", "name": "Afghanistan" }]
The
about
URL
annotation
has
not
been
set
for
cells
in
table
T
(
{
"url":
"http://example.org/countries.csv"}
);
cells
in
a
given
row
where
about
URL
has
not
been
specified
are
assumed
to
refer
to
the
same
subject
and
so
the
name-value
pairs
associated
with
the
cell
values
of
that
row
occur
within
the
same
object
.
Given
that
the
property
URL
is
null
for
cells
in
table
T
(
{
"url":
"http://example.org/countries.csv"}
),
the
simplified
name
is
used
in
the
name-value
pairs;
e.g.
countryCode
rather
than
http://example.org/countries.csv#countryCode
Standard mode output for this example is provided below:
{ "tables": [{ "url": "http://example.org/countries.csv", "row": [{ "url": "http://example.org/countries.csv#row=2", "rownum": 1, "describes": [{ "countryCode": "AD","latitude": "42.5", "longitude": "1.6", "name": "Andorra" }] }, { "url": "http://example.org/countries.csv#row=3", "rownum": 2, "describes": [{ "countryCode": "AE","latitude": "23.4", "longitude": "53.8", "name": "United Arab Emirates" }] }, { "url": "http://example.org/countries.csv#row=4", "rownum": 3, "describes": [{ "countryCode": "AF","latitude": "33.9", "longitude": "67.7", "name": "Afghanistan" }] }] }] }
Even though the table was defined in isolation, the annotated table is wrapped in a group of tables .
The
name-value
pair
with
name
url
provides
reference
to
the
original
tabular
data
file
and
to
specific
rows
therein.
The
row
number
is
provided
for
each
row
using
name-value
pair
with
name
rownum
.
The
object
containing
the
name-values
pairs
associated
with
the
cell
values
of
a
row
are
related
to
the
object
for
that
row
using
the
name-value
pair
with
name
describes
.
This
example
is
based
on
Use
Case
#11
-
City
of
Palo
Alto
Tree
Data
and
comprises
a
single
annotated
table
describing
an
inventory
of
tree
maintenance
operations.
The
input
tabular
data
file,
published
at
http://example.org/tree-ops-ext.csv
,
and
the
associated
metadata
description
http://example.org/tree-ops-ext.csv-metadata.json
are
provided
below:
GID,On Street,Species,Trim Cycle,Diameter at Breast Ht,Inventory Date,Comments,Protected,KML 1,ADDISON AV,Celtis australis,Large Tree Routine Prune,11,10/18/2010,,,"<Point><coordinates>-122.156485,37.440963</coordinates></Point>" 2,EMERSON ST,Liquidambar styraciflua,Large Tree Routine Prune,11,6/2/2010,,,"<Point><coordinates>-122.156749,37.440958</coordinates></Point>" 6,ADDISON AV,Robinia pseudoacacia,Large Tree Routine Prune,29,6/1/2010,cavity or decay; trunk decay; codominant leaders; included bark; large leader or limb decay; previous failure root damage; root decay; beware of BEES,YES,"<Point><coordinates>-122.156299,37.441151</coordinates></Point>"
{ "@context": ["http://www.w3.org/ns/csvw", {"@language": "en"}], "@id": "http://example.org/tree-ops-ext", "url": "tree-ops-ext.csv", "dc:title": "Tree Operations", "dcat:keyword": ["tree", "street", "maintenance"], "dc:publisher": [{ "schema:name": "Example Municipality", "schema:url": {"@id": "http://example.org"} }], "dc:license": {"@id": "http://opendefinition.org/licenses/cc-by/"}, "dc:modified": {"@value": "2010-12-31", "@type": "xsd:date"}, "notes": [{ "@type": "oa:Annotation", "oa:hasTarget": {"@id": "http://example.org/tree-ops-ext"}, "oa:hasBody": { "@type": "oa:EmbeddedContent", "rdf:value": "This is a very interesting comment about the table; it's a table!", "dc:format": {"@value": "text/plain"} } }], "dialect": {"trim": true}, "tableSchema": { "columns": [{ "name": "GID", "titles": [ "GID", "Generic Identifier" ], "dc:description": "An identifier for the operation on a tree.", "datatype": "string", "required": true, "suppressOutput": true }, { "name": "on_street", "titles": "On Street", "dc:description": "The street that the tree is on.", "datatype": "string" }, { "name": "species", "titles": "Species", "dc:description": "The species of the tree.", "datatype": "string" }, { "name": "trim_cycle", "titles": "Trim Cycle", "dc:description": "The operation performed on the tree.", "datatype": "string", "lang": "en" }, { "name": "dbh", "titles": "Diameter at Breast Ht", "dc:description": "Diameter at Breast Height (DBH) of the tree (in feet), measured 4.5ft above ground.", "datatype": "integer" }, { "name": "inventory_date", "titles": "Inventory Date", "dc:description": "The date of the operation that was performed.", "datatype": {"base": "date", "format": "M/d/yyyy"} }, { "name": "comments", "titles": "Comments", "dc:description": "Supplementary comments relating to the operation or tree.", "datatype": "string", "separator": ";" }, { "name": "protected", "titles": "Protected", "dc:description": "Indication (YES / NO) whether the tree is subject to a protection order.", "datatype": {"base": "boolean", "format": "YES|NO"}, "default": "NO" }, { "name": "kml", "titles": "KML", "dc:description": "KML-encoded description of tree location.", "datatype": "xml" }], "primaryKey": "GID", "aboutUrl": "http://example.org/tree-ops-ext#gid-{GID}" } }
The notes annotation in the metadata description uses the Open Annotation data model currently under development within the Web Annotations Working Group . This is purely illustrative; no constraints are placed on the value of the notes annotation.
The annotated table generated from parsing the tabular data file and associated metadata is shown below and provides the basis for the conversion to JSON.
Core annotations for the resulting table T , with 9 columns and 3 rows , are shown below:
id | core annotations | ||||
---|---|---|---|---|---|
id | url | columns | rows | notes | |
T | <http://example.org/tree-ops-ext> |
http://example.org/tree-ops-ext.csv
|
C1 , C2 , C3 , C4 , C5 , C6 , C7 , C8 , C9 | R1 , R2 , R3 |
[{
"@type":
"oa:Annotation",
...
}]
|
Non-core annotations for the table T are:
dc:title
"Tree
Operations"
dcat:keyword
["tree",
"street",
"maintenance"]
dc:publisher
[{
"schema:name":
"Example
Municipality",
"schema:url":
{
"@id":
"http://example.org"
}
}]
dc:license
{
"@id":
"http://opendefinition.org/licenses/cc-by/"
}
dc:modified
"2010-12-31"
The value of the notes annotation has been shortened for clarity in the table above.
Annotations for the columns , rows and cells in table T are shown in the tables below.
Column annotations:
id | core annotations | annotations | |||||||
---|---|---|---|---|---|---|---|---|---|
table | number | source number | cells | name | titles | required | suppress output |
dc:description
|
|
C1 | T | 1 | 1 | C1.1 , C2.1 , C3.1 |
GID
|
GID
,
Generic
Identifier
|
true
|
true
|
An
identifier
for
the
operation
on
a
tree.
|
C2 | T | 2 | 2 | C1.2 , C2.2 , C3.2 |
on_street
|
On
Street
|
The
street
that
the
tree
is
on.
|
||
C3 | T | 3 | 3 | C1.3 , C2.3 , C3.3 |
species
|
Species
|
The
species
of
the
tree.
|
||
C4 | T | 4 | 4 | C1.4 , C2.4 , C3.4 |
trim_cycle
|
Trim
Cycle
|
The
operation
performed
on
the
tree.
|
||
C5 | T | 5 | 5 | C1.5 , C2.5 , C3.5 |
dbh
|
Diameter
at
Breast
Ht
|
Diameter
at
Breast
Height
(DBH)
of
the
tree
(in
feet),
measured
4.5ft
above
ground.
|
||
C6 | T | 6 | 6 | C1.6 , C2.6 , C3.6 |
inventory_date
|
Inventory
Date
|
The
date
of
the
operation
that
was
performed.
|
||
C7 | T | 7 | 7 | C1.7 , C2.7 , C3.7 |
comments
|
Comments
|
Supplementary
comments
relating
to
the
operation
or
tree.
|
||
C8 | T | 8 | 8 | C1.8 , C2.8 , C3.8 |
protected
|
Protected
|
Indication
(YES
/
NO)
whether
the
tree
is
subject
to
a
protection
order.
|
||
C9 | T | 9 | 9 | C1.9 , C2.9 , C3.9 |
kml
|
KML
|
KML-encoded
description
of
tree
location.
|
In
this
example,
output
for
column
C1
(
GID
)
is
not
required;
note
the
suppress
output
annotation
on
this
column
.
Row annotations:
id | core annotations | ||||
---|---|---|---|---|---|
table | number | source number | cells | primary key | |
R1 | T | 1 | 2 | C1.1 , C1.2 , C1.3 , C1.4 , C1.5 , C1.6 , C1.7 , C1.8 , C1.9 | C1.1 |
R2 | T | 2 | 3 | C2.1 , C2.2 , C2.3 , C2.4 , C2.5 , C2.6 , C2.7 , C2.8 , C2.9 | C2.1 |
R3 | T | 3 | 4 | C3.1 , C3.2 , C3.3 , C3.4 , C3.5 , C3.6 , C3.7 , C3.8 , C3.9 | C3.1 |
Cell annotations:
id | core annotations | |||||
---|---|---|---|---|---|---|
table | column | row | string value | value | about URL | |
C1.1 | T | C1 | R1 |
"1"
|
"1"
|
http://example.org/tree-ops-ext#gid-1
|
C1.2 | T | C2 | R1 |
"ADDISON
AV"
|
"ADDISON
AV"
|
<http://example.org/tree-ops-ext#gid-1>
|
C1.3 | T | C3 | R1 |
"Celtis
australis"
|
"Celtis
australis"
|
<http://example.org/tree-ops-ext#gid-1>
|
C1.4 | T | C4 | R1 |
"Large
Tree
Routine
Prune"
|
"Large
Tree
Routine
Prune"
(English)
|
<http://example.org/tree-ops-ext#gid-1>
|
C1.5 | T | C5 | R1 |
"11"
|
11
|
<http://example.org/tree-ops-ext#gid-1>
|
C1.6 | T | C6 | R1 |
"10/18/2010"
|
2010-10-18
|
<http://example.org/tree-ops-ext#gid-1>
|
C1.7 | T | C7 | R1 |
""
|
null
|
<http://example.org/tree-ops-ext#gid-1>
|
C1.8 | T | C8 | R1 |
""
|
false
|
<http://example.org/tree-ops-ext#gid-1>
|
C1.9 | T | C9 | R1 |
"<Point><coordinates>-122.156485,37.440963</coordinates></Point>"
|
"<Point><coordinates>-122.156485,37.440963</coordinates></Point>"
(XML)
|
<http://example.org/tree-ops-ext#gid-1>
|
C2.1 | T | C1 | R2 |
"2"
|
"2"
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.2 | T | C2 | R2 |
"EMERSON
ST"
|
"EMERSON
ST"
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.3 | T | C3 | R2 |
"Liquidambar
styraciflua"
|
"Liquidambar
styraciflua"
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.4 | T | C4 | R2 |
"Large
Tree
Routine
Prune"
|
"Large
Tree
Routine
Prune"
(English)
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.5 | T | C5 | R2 |
"11"
|
11
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.6 | T | C6 | R2 |
"6/2/2010"
|
2010-06-02
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.7 | T | C7 | R2 |
""
|
null
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.8 | T | C8 | R2 |
""
|
false
|
<http://example.org/tree-ops-ext#gid-2>
|
C2.9 | T | C9 | R2 |
"<Point><coordinates>-122.156749,37.440958</coordinates></Point>"
|
"<Point><coordinates>-122.156749,37.440958</coordinates></Point>"
(XML)
|
<http://example.org/tree-ops-ext#gid-2>
|
C3.1 | T | C1 | R3 |
"6"
|
"6"
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.2 | T | C2 | R3 |
"ADDISON
AV"
|
"ADDISON
AV"
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.3 | T | C3 | R3 |
"Robinia
pseudoacacia"
|
"Robinia
pseudoacacia"
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.4 | T | C4 | R3 |
"Large
Tree
Routine
Prune"
|
"Large
Tree
Routine
Prune"
(English)
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.5 | T | C5 | R3 |
"29"
|
29
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.6 | T | C6 | R3 |
"6/1/2010"
|
2010-06-01
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.7 | T | C7 | R3 |
"cavity
or
decay;
trunk
decay;
codominant
leaders;
included
bark;
large
leader
or
limb
decay;
previous
failure
root
damage;
root
decay;
beware
of
BEES"
|
"cavity
or
decay"
,
"trunk
decay"
,
"codominant
leaders"
,
"included
bark"
,
"large
leader
or
limb
decay"
,
"previous
failure
root
damage"
,
"root
decay"
,
"beware
of
BEES"
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.8 | T | C8 | R3 |
"YES"
|
true
|
<http://example.org/tree-ops-ext#gid-6>
|
C3.9 | T | C9 | R3 |
"<Point><coordinates>-122.156299,37.441151</coordinates></Point>"
|
"<Point><coordinates>-122.156299,37.441151</coordinates></Point>"
(XML)
|
<http://example.org/tree-ops-ext#gid-6>
|
Minimal mode output for this example is provided below:
[{ "@id": "http://example.org/tree-ops-ext#gid-1", "on_street": "ADDISON AV", "species": "Celtis australis", "trim_cycle": "Large Tree Routine Prune", "dbh": 11, "inventory_date": "2010-10-18", "protected": false, "kml": "<Point><coordinates>-122.156485,37.440963</coordinates></Point>" }, { "@id": "http://example.org/tree-ops-ext#gid-2", "on_street": "EMERSON ST", "species": "Liquidambar styraciflua", "trim_cycle": "Large Tree Routine Prune", "dbh": 11, "inventory_date": "2010-06-02", "protected": false, "kml": "<Point><coordinates>-122.156749,37.440958</coordinates></Point>" }, { "@id": "http://example.org/tree-ops-ext#gid-6", "on_street": "ADDISON AV", "species": "Robinia pseudoacacia", "trim_cycle": "Large Tree Routine Prune", "dbh": 29, "inventory_date": "2010-06-01", "comments": [ "cavity or decay", "trunk decay", "codominant leaders", "included bark", "large leader or limb decay", "previous failure root damage", "root decay", "beware of BEES" ], "protected": true, "kml": "<Point><coordinates>-122.156299,37.441151</coordinates></Point>" }]
The
subject
described
by
each
row
is
explicitly
defined
using
the
about
URL
annotation;
e.g.
the
subject
of
row
R1
is
http://example.org/tree-ops-ext#gid-1
.
Output
for
column
C1
(
{
"name":
"GID"
}
)
is
not
included
as
column
suppress
output
annotation
is
true
.
Cells
C1.7
and
C2.7
(
rows
R1
and
R2
;
column
,
{
"name":
"comments"
}
)
have
null
values
-
no
output
is
included
for
these
cells
.
Cell
C3.7
(
row
R3
;
column
,
{
"name":
"comments"
}
)
contains
a
sequence
of
values;
the
set
of
values
are
included
in
an
array
.
Standard mode output for this example is provided below:
{ "tables": [{ "@id": "http://example.org/tree-ops-ext", "url": "http://example.org/tree-ops-ext.csv", "dc:title": "Tree Operations", "dcat:keyword": [ "tree", "street", "maintenance" ], "dc:publisher": [{ "schema:name": "Example Municipality", "schema:url": "http://example.org" }], "dc:license": "http://opendefinition.org/licenses/cc-by/", "dc:modified": "2010-12-31", "notes": [{ "@type": "oa:Annotation", "oa:hasTarget": "http://example.org/tree-ops-ext", "oa:hasBody": { "@type": "oa:EmbeddedContent", "rdf:value": "This is a very interesting comment about the table; it's a table!", "dc:format": "text/plain" } }], "row": [{ "url": "http://example.org/tree-ops-ext.csv#row=2", "rownum": 1, "describes": [{ "@id": "http://example.org/tree-ops-ext#gid-1", "on_street": "ADDISON AV", "species": "Celtis australis", "trim_cycle": "Large Tree Routine Prune", "dbh": 11, "inventory_date": "2010-10-18", "protected": false, "kml": "<Point><coordinates>-122.156485,37.440963</coordinates></Point>" }] }, { "url": "http://example.org/tree-ops-ext.csv#row=3", "rownum": 2, "describes": [{ "@id": "http://example.org/tree-ops-ext#gid-2", "on_street": "EMERSON ST", "species": "Liquidambar styraciflua", "trim_cycle": "Large Tree Routine Prune", "dbh": 11, "inventory_date": "2010-06-02", "protected": false, "kml": "<Point><coordinates>-122.156749,37.440958</coordinates></Point>" }] }, { "url": "http://example.org/tree-ops-ext.csv#row=4", "rownum": 3, "describes": [{ "@id": "http://example.org/tree-ops-ext#gid-6", "on_street": "ADDISON AV", "species": "Robinia pseudoacacia", "trim_cycle": "Large Tree Routine Prune", "dbh": 29, "inventory_date": "2010-06-01", "comments": [ "cavity or decay", "trunk decay", "codominant leaders", "included bark", "large leader or limb decay", "previous failure root damage", "root decay", "beware of BEES" ], "protected": true, "kml": "<Point><coordinates>-122.156299,37.441151</coordinates></Point>" }] }] }] }
Table
T
(
{
"url":
"http://example.org/tree-ops-ext.csv"}
)
has
been
explicitly
identified:
{
"@id":
"<http://exmple.org/tree-ops-ext>"}
.
Non-core
annotations
and
notes
specified
for
table
T
(
{
"url":
"http://example.org/tree-ops-ext.csv"}
)
are
included
in
the
output.
This example uses a single annotated table describing a listing of music events. Each row from the tabular data file corresponds to three resources; the music event itself, the location where that event occurs and the offer to sell tickets for that event. The goal is to convert the CSV content into schema.org markup that a search engine such as Google can use to index music events. Details of how Google expects this information to be structured can be found here .
The
input
tabular
data
file,
published
at
http://example.org/events-listing.csv
,
and
the
associated
metadata
description
http://example.org/events-listing.csv-metadata.json
are
provided
below:
Name, Start Date, Location Name, Location Address, Ticket Url B.B. King,2014-04-12T19:30,"Lupo’s Heartbreak Hotel","79 Washington St., Providence, RI",https://www.etix.com/ticket/1771656 B.B. King,2014-04-13T20:00,"Lynn Auditorium","Lynn, MA, 01901",http://frontgatetickets.com/venue.php?id=11766
{ "@context": ["http://www.w3.org/ns/csvw", {"@language": "en"}], "url": "events-listing.csv", "dialect": {"trim": true}, "tableSchema": { "columns": [{ "name": "name", "titles": "Name", "aboutUrl": "#event-{_row}", "propertyUrl": "schema:name" }, { "name": "start_date", "titles": "Start Date", "datatype": { "base": "datetime", "format": "yyyy-MM-ddTHH:mm" }, "aboutUrl": "#event-{_row}", "propertyUrl": "schema:startDate" }, { "name": "location_name", "titles": "Location Name", "aboutUrl": "#place-{_row}", "propertyUrl": "schema:name" }, { "name": "location_address", "titles": "Location Address", "aboutUrl": "#place-{_row}", "propertyUrl": "schema:address" }, { "name": "ticket_url", "titles": "Ticket Url", "datatype": "anyURI", "aboutUrl": "#offer-{_row}", "propertyUrl": "schema:url" }, { "name": "type_event", "virtual": true, "aboutUrl": "#event-{_row}", "propertyUrl": "rdf:type", "valueUrl": "schema:MusicEvent" }, { "name": "type_place", "virtual": true, "aboutUrl": "#place-{_row}", "propertyUrl": "rdf:type", "valueUrl": "schema:Place" }, { "name": "type_offer", "virtual": true, "aboutUrl": "#offer-{_row}", "propertyUrl": "rdf:type", "valueUrl": "schema:Offer" }, { "name": "location", "virtual": true, "aboutUrl": "#event-{_row}", "propertyUrl": "schema:location", "valueUrl": "#place-{_row}" }, { "name": "offers", "virtual": true, "aboutUrl": "#event-{_row}", "propertyUrl": "schema:offers", "valueUrl": "#offer-{_row}" }] } }
The
CSV
to
JSON
translation
is
limited
to
providing
one
statement,
or
triple,
per
column
in
the
table
.
The
target
schema.org
markup
requires
10
statements
to
describe
each
event.
As
the
base
tabular
data
file
contains
5
columns,
an
additional
5
virtual
columns
have
been
added
in
order
to
provide
for
the
full
complement
of
statements—including
the
relationships
between
the
3
resources
(event,
location,
and
offer)
described
by
each
row
of
the
table
.
Note
that
the
virtual
annotation
is
true
for
these
virtual
columns
.
Furthermore, note that no attempt is made to reconcile between locations or offers that may be associated with more than one event; every row in the table will create both a new location resource and offer resource in addition to the event resource. If considered necessary, applications such as OpenRefine may be used to identify and reconcile duplicate location resources once the JSON output has been generated.
The annotated table generated from parsing the tabular data file and associated metadata is shown below and provides the basis for the conversion to JSON.
Annotations for the resulting table T , with 10 columns and 2 rows , are shown below:
id | core annotations | ||
---|---|---|---|
url | columns | rows | |
T |
http://example.org/events-listing.csv
|
C1 , C2 , C3 , C4 , C5 , C6 , C7 , C8 , C9 , C10 | R1 , R2 |
Annotations for the columns , rows and cells in table T are shown in the tables below.
Column annotations:
id | core annotations | ||||||
---|---|---|---|---|---|---|---|
table | number | source number | cells | name | titles | virtual | |
C1 | T | 1 | 1 | C1.1 , C2.1 |
name
|
Name
|
|
C2 | T | 2 | 2 | C1.2 , C2.2 |
start_date
|
Start
Date
|
|
C3 | T | 3 | 3 | C1.3 , C2.3 |
location_name
|
Location
Name
|
|
C4 | T | 4 | 4 | C1.4 , C2.4 |
location_address
|
Location
Address
|
|
C5 | T | 5 | 5 | C1.5 , C2.5 |
ticket_url
|
Ticket
Url
|
|
C6 | T | 6 | 6 | C1.6 , C2.6 |
type_event
|
true
|
|
C7 | T | 7 | 7 | C1.7 , C2.7 |
type_place
|
true
|
|
C8 | T | 8 | 8 | C1.8 , C2.8 |
type_offer
|
true
|
|
C9 | T | 9 | 9 | C1.9 , C2.9 |
location
|
true
|
|
C10 | T | 10 | 10 | C1.10 , C2.10 |
offers
|
true
|
Row annotations:
id | core annotations | |||
---|---|---|---|---|
table | number | source number | cells | |
R1 | T | 1 | 2 | C1.1 , C1.2 , C1.3 , C1.4 , C1.5 , C1.6 , C1.7 , C1.8 , C1.9 , C1.10 |
R2 | T | 2 | 3 | C2.1 , C2.2 , C2.3 , C2.4 , C2.5 , C2.6 , C2.7 , C2.8 , C2.9 , C2.10 |
Cell annotations:
id | core annotations | |||||||
---|---|---|---|---|---|---|---|---|
table | column | row | string value | value | about URL | property URL | value URL | |
C1.1 | T | C1 | R1 |
"B.B.
King"
|
"B.B.
King"
|
<http://example.org/events-listing.csv#event-1>
|
schema:name
|
|
C1.2 | T | C2 | R1 |
"2014-04-12T19:30"
|
2014-04-12T19:30:00
|
<http://example.org/events-listing.csv#event-1>
|
schema:startDate
|
|
C1.3 | T | C3 | R1 |
"Lupo’s
Heartbreak
Hotel"
|
"Lupo’s
Heartbreak
Hotel"
|
<http://example.org/events-listing.csv#place-1>
|
schema:name
|
|
C1.4 | T | C4 | R1 |
"79
Washington
St.,
Providence,
RI"
|
"79
Washington
St.,
Providence,
RI"
|
<http://example.org/events-listing.csv#place-1>
|
schema:address
|
|
C1.5 | T | C5 | R1 |
"https://www.etix.com/ticket/1771656"
|
<https://www.etix.com/ticket/1771656>
|
<http://example.org/events-listing.csv#offer-1>
|
schema:url
|
|
C1.6 | T | C6 | R1 |
""
|
null
|
<http://example.org/events-listing.csv#event-1>
|
rdf:type
|
schema:MusicEvent
|
C1.7 | T | C7 | R1 |
""
|
null
|
<http://example.org/events-listing.csv#place-1>
|
rdf:type
|
schema:Place
|
C1.8 | T | C8 | R1 |
""
|
null
|
<http://example.org/events-listing.csv#offer-1>
|
rdf:type
|
schema:Offer
|
C1.9 | T | C9 | R1 |
""
|
null
|
<http://example.org/events-listing.csv#event-1>
|
schema:location
|
<http://example.org/events-listing.csv#place-1>
|
C1.10 | T | C10 | R1 |
""
|
null
|
<http://example.org/events-listing.csv#event-1>
|
schema:offers
|
<http://example.org/events-listing.csv#offer-1>
|
C2.1 | T | C1 | R2 |
"B.B.
King"
|
"B.B.
King"
|
<http://example.org/events-listing.csv#event-2>
|
schema:name
|
|
C2.2 | T | C2 | R2 |
"2014-04-13T20:00"
|
2014-04-13T20:00:00
|
<http://example.org/events-listing.csv#event-2>
|
schema:startDate
|
|
C2.3 | T | C3 | R2 |
"Lynn
Auditorium"
|
"Lynn
Auditorium"
|
<http://example.org/events-listing.csv#place-2>
|
schema:name
|
|
C2.4 | T | C4 | R2 |
"Lynn,
MA,
01901"
|
"Lynn,
MA,
01901"
|
<http://example.org/events-listing.csv#place-2>
|
schema:address
|
|
C2.5 | T | C5 | R2 |
"http://frontgatetickets.com/venue.php?id=11766"
|
<http://frontgatetickets.com/venue.php?id=11766>
|
<http://example.org/events-listing.csv#offer-2>
|
schema:url
|
|
C2.6 | T | C6 | R2 |
""
|
null
|
<http://example.org/events-listing.csv#event-2>
|
rdf:type
|
schema:MusicEvent
|
C2.7 | T | C7 | R2 |
""
|
null
|
<http://example.org/events-listing.csv#place-2>
|
rdf:type
|
schema:Place
|
C2.8 | T | C8 | R2 |
""
|
null
|
<http://example.org/events-listing.csv#offer-2>
|
rdf:type
|
schema:Offer
|
C2.9 | T | C9 | R2 |
""
|
null
|
<http://example.org/events-listing.csv#event-2>
|
schema:location
|
<http://example.org/events-listing.csv#place-2>
|
C2.10 | T | C10 | R2 |
""
|
null
|
<http://example.org/events-listing.csv#event-2>
|
schema:offers
|
<http://example.org/events-listing.csv#offer-2>
|
Minimal mode output for this example is provided below:
[{ "@id": "http://example.org/events-listing.csv#event-1", "@type": "schema:MusicEvent", "schema:name": "B.B. King", "schema:startDate": "2014-04-12T19:30:00", "schema:location": { "@id": "http://example.org/events-listing.csv#place-1", "@type": "schema:Place", "schema:name": "Lupo’s Heartbreak Hotel", "schema:address": "79 Washington St., Providence, RI" }, "schema:offer": { "@id": "http://example.org/events-listing.csv#offer-1", "@type": "schema:Offer", "schema:offer": "https://www.etix.com/ticket/1771656" } }, { "@id": "http://example.org/events-listing.csv#event-2", "@type": "schema:MusicEvent", "schema:name": "B.B. King", "schema:startDate": "2014-04-13T20:00:00", "schema:location": { "@id": "http://example.org/events-listing.csv#place-2", "@type": "schema:Place", "schema:name": "Lynn Auditorium", "schema:address": "Lynn, MA, 01901" }, "schema:offer": { "@id": "http://example.org/events-listing.csv#offer-2", "@type": "schema:Offer", "schema:offer": "http://frontgatetickets.com/venue.php?id=11766" } }]
Three resources are defined for each row within the table; event, location and offer. Therefore three objects are created for each row .
Each
column
description
explicitly
defines
both
aboutUrl
and
propertyUrl
properties
which
are
used
to
create
the
about
URL
and
property
URL
annotations
on
the
column's
cells
.
Columns
C6
,
C7
and
C8
(
{
"name":
"type_event"}
,
{
"name":
"type_place"}
and
{
"name":
"type_offer"}
)
define
the
semantic
types
of
the
resources
described
by
each
row
:
schema:MusicEvent
,
schema:Place
and
schema:Offer
respectively—noting
that
the
use
of
rdf:type
is
converted
to
the
name
@type
(as
used
in
[
json-ld
])
by
this
conversion
application.
Column
C9
(
{
"name":
"location"}
)
uses
the
about
URL
,
property
URL
and
value
URL
to
assert
the
relationship
between
the
event
and
location
resources.
Column
C10
(
{
"name":
"offer"}
)
uses
the
about
URL
,
property
URL
and
value
URL
to
assert
the
relationship
between
the
event
and
offer
resources.
Standard mode output for this example is provided below:
{ "tables": [{ "url": "http://example.org/events-listing.csv", "row": [{ "url": "http://example.org/events-listing.csv#row=2", "rownum": 1, "describes": [{ "@id": "http://example.org/events-listing.csv#event-1", "@type": "schema:MusicEvent", "schema:name": "B.B. King", "schema:startDate": "2014-04-12T19:30:00", "schema:location": { "@id": "http://example.org/events-listing.csv#place-1", "@type": "schema:Place", "schema:name": "Lupo’s Heartbreak Hotel", "schema:address": "79 Washington St., Providence, RI" }, "schema:offers": { "@id": "http://example.org/events-listing.csv#offer-1", "@type": "schema:Offer", "schema:url": "https://www.etix.com/ticket/1771656" } }] }, { "url": "http://example.org/events-listing.csv#row=3", "rownum": 2, "describes": [{ "@id": "http://example.org/events-listing.csv#event-2", "@type": "schema:MusicEvent", "schema:name": "B.B. King", "schema:startDate": "2014-04-13T20:00:00", "schema:location": { "@id": "http://example.org/events-listing.csv#place-2", "@type": "schema:Place", "schema:name": "Lynn Auditorium", "schema:address": "Lynn, MA, 01901" }, "schema:offers": { "@id": "http://example.org/events-listing.csv#offer-2", "@type": "schema:Offer", "schema:url": "http://frontgatetickets.com/venue.php?id=11766" } }] }] }] }
The
resources
described
by
each
row
are
explicitly
defined
using
the
about
URL
annotation—in
this
case
three
resources
per
row
(event,
location,
and
offer).
The
objects
containing
the
name-values
pairs
associated
with
the
cell
values
of
a
row
are
related
to
the
object
for
each
subject
in
that
row
using
the
name-value
pair
with
name
describes
.
This example is based on Use Case #4 - Publication of public sector roles and salaries and uses four annotated tables published as a group of tables . Information about senior roles and junior roles within a government department or organization are published in CSV format by each department. These are validated against a centrally published schema to ensure that all the data published by departments is consistent. Additionally, lists of organizations and professions are also published centrally, providing controlled vocabularies against which departmental submissions are validated.
Information published about junior and senior roles provides summary information for each post within the government department or organization. Whilst the junior role information is anonymous, providing only an indication of the number of full-time-equivalent (FTE) staff occupying a given post, the senior role information specifies the named individual occupying each post. As such, each row from the tabular data file describing senior roles corresponds to two resources; the post and the person occupying that post.
This example is concerned only with converting the information provided each government department or organization not the centrally published information listing organizations and professions.
The input tabular data files and associated metadata descriptions are provided below:
Organization Unique Reference,Organization Name,Department Reference hefce.ac.uk,Higher Education Funding Council for England,bis.gov.uk bis.gov.uk,"Department for Business, Innovation and Skills",xx
Profession Finance Information Technology Operational Delivery Policy
Post Unique Reference,Name,Grade,Job Title,Reports to Senior Post,Profession,Organization Reference 90115,Steve Egan,SCS1A,Deputy Chief Executive,90334,Finance,hefce.ac.uk 90334,Sir Alan Langlands,SCS4,Chief Executive,xx,Policy,hefce.ac.uk
Reporting Senior Post,Grade,Payscale Minimum (£),Payscale Maximum (£),Generic Job Title,Number of Posts (FTE),Profession,Organization Reference 90115,4,17426,20002,Administrator,8.67,Operational Delivery,hefce.ac.uk 90115,5,19546,22478,Administrator,0.5,Operational Delivery,hefce.ac.uk
{ "@type": "TableGroup", "@context": ["http://www.w3.org/ns/csvw", {"@language": "en"}], "tables": [{ "url": "gov.uk/data/organizations.csv","tableSchema": "gov.uk/schema/organizations.json", "suppressOutput": true }, { "url": "gov.uk/data/professions.csv","tableSchema": "gov.uk/schema/professions.json", "suppressOutput": true }, { "url": "senior-roles.csv","tableSchema": "gov.uk/schema/senior-roles.json" }, { "url": "junior-roles.csv","tableSchema": "gov.uk/schema/junior-roles.json" }] }
{ "@id": "http://example.org/gov.uk/schema/organizations.json", "@context": "http://www.w3.org/ns/csvw", "columns": [{ "name": "ref", "titles": "Organization Unique Reference", "datatype": "string", "required": true, "propertyUrl": "dc:identifier" }, { "name": "name", "titles": "Organization Name", "datatype": "string", "propertyUrl": "foaf:name" }, { "name": "department", "titles": "Department Reference", "datatype": "string", "null": "xx", "propertyUrl": "org:subOrganizationOf","valueUrl": "http://example.org/organization/{department}" }], "primaryKey": "ref", "aboutUrl": "http://example.org/organization/{ref}", "foreignKeys": [{ "columnReference": "department", "reference": { "schemaReference": "http://example.org/gov.uk/schema/organizations.json", "columnReference": "ref" } }] }
{ "@id": "http://example.org/gov.uk/schema/professions.json", "@context": "http://www.w3.org/ns/csvw", "columns": [{ "name": "name", "titles": "Profession", "datatype": "string", "required": true }], "primaryKey": "name" }
{ "@id": "http://example.org/gov.uk/schema/senior-roles.json", "@context": "http://www.w3.org/ns/csvw", "columns": [{ "name": "ref", "titles": "Post Unique Reference", "datatype": "string", "required": true, "propertyUrl": "dc:identifier" }, { "name": "name", "titles": "Name", "datatype": "string", "aboutUrl": "http://example.org/organization/{organizationRef}/person/{_row}", "propertyUrl": "foaf:name" }, { "name": "grade", "titles": "Grade", "datatype": "string", "propertyUrl": "http://example.org/gov.uk/def/grade" }, { "name": "job", "titles": "Job Title", "datatype": "string", "propertyUrl": "http://example.org/gov.uk/def/job" }, { "name": "reportsTo", "titles": "Reports to Senior Post", "datatype": "string", "null": "xx", "propertyUrl": "org:reportsTo", "valueUrl": "http://example.org/organization/{organizationRef}/post/{reportsTo}" }, { "name": "profession", "titles": "Profession", "datatype": "string", "propertyUrl": "http://example.org/gov.uk/def/profession" }, { "name": "organizationRef", "titles": "Organization Reference", "datatype": "string", "propertyUrl": "org:postIn", "valueUrl": "http://example.org/organization/{organizationRef}", "required": true }, { "name": "post_holder", "virtual": true, "propertyUrl": "org:heldBy", "valueUrl": "http://example.org/organization/{organizationRef}/person/{_row}" }], "primaryKey": "ref", "aboutUrl": "http://example.org/organization/{organizationRef}/post/{ref}", "foreignKeys": [{ "columnReference": "reportsTo", "reference": { "schemaReference": "http://example.org/gov.uk/schema/senior-roles.json", "columnReference": "ref" } }, { "columnReference": "profession", "reference": { "schemaReference": "http://example.org/gov.uk/schema/professions.json", "columnReference": "name" } }, { "columnReference": "organizationRef", "reference": { "schemaReference": "http://example.org/gov.uk/schema/organizations.json", "columnReference": "ref" } }] }
{ "@id": "http://example.org/gov.uk/schema/junior-roles.json", "@context": "http://www.w3.org/ns/csvw", "columns": [{ "name": "reportsToSenior", "titles": "Reporting Senior Post", "datatype": "string", "propertyUrl": "org:reportsTo", "valueUrl": "http://example.org/organization/{organizationRef}/post/{reportsToSenior}", "required": true }, { "name": "grade", "titles": "Grade", "datatype": "string", "propertyUrl": "http://example.org/gov.uk/def/grade" }, { "name": "min_pay", "titles": "Payscale Minimum (£)", "datatype": "integer", "propertyUrl": "http://example.org/gov.uk/def/min_pay" }, { "name": "max_pay", "titles": "Payscale Maximum (£)", "datatype": "integer", "propertyUrl": "http://example.org/gov.uk/def/max_pay" }, { "name": "job", "titles": "Generic Job Title", "datatype": "string", "propertyUrl": "http://example.org/gov.uk/def/job" }, { "name": "number", "titles": "Number of Posts (FTE)", "datatype": "number", "propertyUrl": "http://example.org/gov.uk/def/number_of_posts" }, { "name": "profession", "titles": "Profession", "datatype": "string", "propertyUrl": "http://example.org/gov.uk/def/profession" }, { "name": "organizationRef", "titles": "Organization Reference", "datatype": "string", "propertyUrl": "org:postIn", "valueUrl": "http://example.org/organization/{organizationRef}", "required": true }], "foreignKeys": [{ "columnReference": "reportsToSenior", "reference": { "schemaReference": "http://example.org/gov.uk/schema/senior-roles.json", "columnReference": "ref" } }, { "columnReference": "profession", "reference": { "schemaReference": "http://example.org/gov.uk/schema/professions.json", "columns": "name" } }, { "columnReference": "organizationRef", "reference": { "schemaReference": "http://example.org/gov.uk/schema/organizations.json", "columns": "ref" } }] }
This
example
makes
extensive
use
of
the
example.org
domain.
As
described
in
[
RFC6761
],
this
domain
is
used
for
illustrative
examples
within
documentation.
In
reality,
the
resources
described
here
with
the
URL
path
/gov.uk
would
be
centrally
published
by
the
UK
Government
at,
say,
the
domain
data.gov.uk
.
Given
that
these
resources
are
centrally
published
with
an
aspiration
for
reuse,
the
schema
descriptions
have
been
factored
out
into
separate
resources.
As
such,
the
top-level
metadata
description
resource
metadata.json
simply
provides
the
list
of
tables
and
binds
each
of
them
to
the
appropriate
schema
that
is
defined
elsewhere.
Finally,
note
that
because
the
centrally
published
metadata
descriptions
are
intended
to
be
reused
across
many
government
departments
and
organizations,
extra
consideration
has
been
given
to
defining
URIs
for
the
person
and
post
resources
defined
in
each
row
of
the
senior
roles
tabular
data
and
subsequently
referenced
from
the
junior
roles
tabular
data.
To
ensure
that
naming
clashes
are
avoided,
the
unique
reference
for
the
organization
to
which
the
person
or
post
belongs
has
been
included
in
a
path
segment
of
the
identifier.
For
example,
the
URI
template
property
aboutUrl
used
to
identify
the
senior
post
is
specified
as
http://example.org/organization/{organizationRef}/post/{ref}
,
thus
yielding
the
URI
http://example.org/organization/hefce.ac.uk/post/90115
for
the
post
described
in
the
first
row
of
the
senior
roles
tabular
data.
The group of tables generated from parsing the tabular data files and associated metadata is shown below and provides the basis for the conversion to JSON.
Annotations for the group of tables G and the four tables Ta , Tb , Tc , and Td are shown below.
Group of Tables annotations:
id | core annotations |
---|---|
tables | |
G | Ta , Tb , Tc , Td |
Table annotations:
id | core annotations | ||||
---|---|---|---|---|---|
url
|
columns | rows | suppress output | foreign keys | |
Ta |
http://example.org/gov.uk/data/organizations.csv
|
Ca1 , Ca2 , Ca3 | Ra1 , Ra2 |
true
|
Fa1 |
Tb |
http://example.org/gov.uk/professions.csv
|
Cb1 | Rb1 , Rb2 , Rb3 , Rb4 |
true
|
|
Tc |
http://example.org/senior-roles.csv
|
Cc1 , Cc2 , Cc3 , Cc4 , Cc5 , Cc6 | Rc1 , Rc2 |
false
|
Fc1 , Fc2 , Fc3 |
Td |
http://example.org/junior-roles.csv
|
Cd1 , Cd2 , Cd3 , Cd4 , Cd5 , Cd6 , Cd7 | Rd1 , Rd2 |
false
|
Fd1 , Fd2 , Fd3 |
In
this
example,
output
for
the
centrally
published
lists
of
organizations
and
professions,
tables
Ta
and
Tb
(
http://example.org/gov.uk/data/organizations.csv
and
http://example.org/gov.uk/data/professions.csv
respectively),
are
not
required;
only
information
from
the
departmental
submissions
is
to
be
translated
to
RDF.
Note
the
suppress
output
annotation
on
this
table
.
The following foreign keys are defined:
id | columns in table | columns in referenced table |
---|---|---|
Fa1 | Ca3 | Ca1 |
Fc1 | Cc5 | Cc1 |
Fc2 | Cc6 | Cb1 |
Fc3 | Cc7 | Ca1 |
Fd1 | Cd1 | Cc1 |
Fd2 | Cd7 | Cb1 |
Fd3 | Cd8 | Ca1 |
Annotations for the columns , rows and cells in table T are shown in the tables below.
Column annotations:
id | core annotations | |||||||
---|---|---|---|---|---|---|---|---|
table | number | source number | cells | name | titles | required | virtual | |
Ca1 | Ta | 1 | 1 | Ca1.1 , Ca2.1 |
ref
|
Organization
Unique
Reference
|
true
|
|
Ca2 | Ta | 1 | 1 | Ca1.2 , Ca2.2 |
name
|
Organization
Name
|
||
Ca3 | Ta | 1 | 1 | Ca1.3 , Ca2.3 |
department
|
Department
Reference
|
||
Cb1 | Tb | 1 | 1 | Cb1.1 , Cb2.1 , Cb3.1 , Cb4.1 |
name
|
Profession
|
true
|
|
Cc1 | Tc | 1 | 1 | Cc1.1 , Cc2.1 |
ref
|
Post
Unique
Reference
|
true
|
|
Cc2 | Tc | 2 | 2 | Cc1.2 , Cc2.2 |
name
|
Name
|
||
Cc3 | Tc | 3 | 3 | Cc1.3 , Cc2.3 |
grade
|
Grade
|
||
Cc4 | Tc | 4 | 4 | Cc1.4 , Cc2.4 |
job
|
Job
Title
|
||
Cc5 | Tc | 5 | 5 | Cc1.5 , Cc2.5 |
reportsTo
|
Reports
to
Senior
Post
|
||
Cc6 | Tc | 6 | 6 | Cc1.6 , Cc2.6 |
profession
|
Profession
|
||
Cc7 | Tc | 7 | 7 | Cc1.7 , Cc2.7 |
organizationRef
|
Organization
Reference
|
true
|
|
Cc8 | Tc | 8 | 8 | Cc1.8 , Cc2.8 |
post_holder
|
true
|
||
Cd1 | Td | 1 | 1 | Cd1.1 , Cd2.1 |
reportsToSenior
|
Reporting
Senior
Post
|
true
|
|
Cd2 | Td | 2 | 2 | Cd1.2 , Cd2.2 |
grade
|
Grade
|
||
Cd3 | Td | 3 | 3 | Cd1.3 , Cd2.3 |
min_pay
|
Payscale
Minimum
(£)
|
||
Cd4 | Td | 4 | 4 | Cd1.4 , Cd2.4 |
max_pay
|
Payscale
Maximum
(£)
|
||
Cd5 | Td | 5 | 5 | Cd1.5 , Cd2.5 |
job
|
Generic
Job
Title
|
||
Cd6 | Td | 6 | 6 | Cd1.6 , Cd2.6 |
number
|
Number
of
Posts
(FTE)
|
||
Cd7 | Td | 7 | 7 | Cd1.7 , Cd2.7 |
profession
|
Profession
|
||
Cd8 | Td | 8 | 8 | Cd1.8 , Cd2.8 |
organizationRef
|
Organization
Reference
|
true
|
Column
Cc8
,
with
the
virtual
annotation
specified
as
true
,
is
used
to
relate
the
person
resource,
whose
name
is
provided
in
column
Cc2
,
to
the
associated
post
resource
within
the
current
row
of
table
Tc
(
{
"url":
"http://example.org/senior-roles.csv"
}
).
Row annotations:
id | core annotations | |||
---|---|---|---|---|
table | number | source number | cells | |
Ra1 | Ta | 1 | 2 | Ca1.1 , Ca1.2 , Ca1.3 |
Ra2 | Ta | 2 | 3 | Ca2.1 , Ca2.2 , Ca2.3 |
Rb1 | Tb | 1 | 2 | Cb1.1 |
Rb2 | Tb | 2 | 3 | Cb2.1 |
Rb3 | Tb | 3 | 4 | Cb3.1 |
Rb4 | Tb | 4 | 5 | Cb4.1 |
Rc1 | Tc | 1 | 2 | Cc1.1 , Cc1.2 , Cc1.3 , Cc1.4 , Cc1.5 , Cc1.6 , Cc1.7 , Cc1.8 |
Rc2 | Tc | 2 | 3 | Cc2.1 , Cc2.2 , Cc2.3 , Cc2.4 , Cc2.5 , Cc2.6 , Cc2.7 , Cc2.8 |
Rd1 | Td | 1 | 2 | Cd1.1 , Cd1.2 , Cd1.3 , Cd1.4 , Cd1.5 , Cd1.6 , Cd1.7 , Cd1.8 |
Rd2 | Td | 2 | 3 | Cd2.1 , Cd2.2 , Cd2.3 , Cd2.4 , Cd2.5 , Cd2.6 , Cd2.7 , Cd2.8 |
Cell annotations:
id | core annotations | |||||||
---|---|---|---|---|---|---|---|---|
table | column | row | string value | value | about URL | property URL | value URL | |
Ca1.1 | Ta | Ca1 | Ra1 |
"hefce.ac.uk"
|
"hefce.ac.uk"
|
<http://example.org/organization/hefce.ac.uk>
|
dc:identifier
|
|
Ca1.2 | Ta | Ca2 | Ra1 |
"Higher
Education
Funding
Council
for
England"
|
"Higher
Education
Funding
Council
for
England"
|
<http://example.org/organization/hefce.ac.uk>
|
foaf:name
|
|
Ca1.3 | Ta | Ca3 | Ra1 |
"bis.gov.uk"
|
"bis.gov.uk"
|
<http://example.org/organization/hefce.ac.uk>
|
org:subOrganizationOf
|
<http://example.org/organization/bis.gov.uk>
|
Ca2.1 | Ta | Ca1 | Ra2 |
"bis.gov.uk"
|
"bis.gov.uk"
|
<http://example.org/organization/bis.gov.uk>
|
dc:identifier
|
|
Ca2.2 | Ta | Ca2 | Ra2 |
"Department
for
Business,
Innovation
and
Skills"
|
"Department
for
Business,
Innovation
and
Skills"
|
<http://example.org/organization/bis.gov.uk>
|
foaf:name
|
|
Ca2.3 | Ta | Ca3 | Ra2 |
"xx"
|
null
|
<http://example.org/organization/bis.gov.uk>
|
org:subOrganizationOf
|
|
Cb1.1 | Tb | Cb1 | Rb1 |
"Finance"
|
"Finance"
|
|||
Cb2.1 | Tb | Cb1 | Rb2 |
"Information
Technology"
|
"Information
Techology"
|
|||
Cb3.1 | Tb | Cb1 | Rb3 |
"Operational
Delivery"
|
"Operational
Delivery"
|
|||
Cb4.1 | Tb | Cb1 | Rb4 |
"Policy"
|
"Policy"
|
|||
Cc1.1 | Tc | Cc1 | Rc1 |
"90115"
|
"90115"
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
dc:identifier
|
|
Cc1.2 | Tc | Cc2 | Rc1 |
"Steve
Egan"
|
"Steve
Egan"
|
<http://example.org/organization/hefce.ac.uk/person/1>
|
foaf:name
|
|
Cc1.3 | Tc | Cc3 | Rc1 |
"SCS1A"
|
"SCS1A"
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
<http://example.org/gov.uk/def/grade>
|
|
Cc1.4 | Tc | Cc4 | Rc1 |
"Deputy
Chief
Executive"
|
"Deputy
Chief
Executive"
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
<http://example.org/gov.uk/def/job>
|
|
Cc1.5 | Tc | Cc5 | Rc1 |
"90334"
|
"90334"
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
org:reportsTo
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
Cc1.6 | Tc | Cc6 | Rc1 |
"Finance"
|
"Finance"
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
<http://example.org/gov.uk/def/profession>
|
|
Cc1.7 | Tc | Cc7 | Rc1 |
"hefce.ac.uk"
|
"hefce.ac.uk"
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
org:postIn
|
<http://example.org/organization/hefce.ac.uk>
|
Cc1.8 | Tc | Cc8 | Rc1 |
""
|
null
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
org:heldBy
|
<http://example.org/organization/hefce.ac.uk/person/1>
|
Cc2.1 | Tc | Cc1 | Rc2 |
"90334"
|
"90334"
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
dc:identifier
|
|
Cc2.2 | Tc | Cc2 | Rc2 |
"Sir
Alan
Langlands"
|
"Sir
Alan
Langlands"
|
<http://example.org/organization/hefce.ac.uk/person/2>
|
foaf:name
|
|
Cc2.3 | Tc | Cc3 | Rc2 |
"SCS4"
|
"SCS4"
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
<http://example.org/gov.uk/def/grade>
|
|
Cc2.4 | Tc | Cc4 | Rc2 |
"Chief
Executive"
|
"Chief
Executive"
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
<http://example.org/gov.uk/def/job>
|
|
Cc2.5 | Tc | Cc5 | Rc2 |
"xx"
|
null
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
org:reportsTo
|
|
Cc2.6 | Tc | Cc6 | Rc2 |
"Policy"
|
"Policy"
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
<http://example.org/gov.uk/def/profession>
|
|
Cc2.7 | Tc | Cc7 | Rc2 |
"hefce.ac.uk"
|
"hefce.ac.uk"
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
org:postIn
|
<http://example.org/organization/hefce.ac.uk>
|
Cc2.8 | Tc | Cc8 | Rc2 |
""
|
null
|
<http://example.org/organization/hefce.ac.uk/post/90334>
|
org:heldBy
|
<http://example.org/organization/hefce.ac.uk/person/2>
|
Cd1.1 | Td | Cd1 | Rd1 |
"90115"
|
"90115"
|
org:reportsTo
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
|
Cd1.2 | Td | Cd2 | Rd1 |
"4"
|
"4"
|
<http://example.org/gov.uk/def/grade>
|
||
Cd1.3 | Td | Cd3 | Rd1 |
"17426"
|
17426
|
<http://example.org/gov.uk/def/min_pay>
|
||
Cd1.4 | Td | Cd4 | Rd1 |
"20002"
|
20002
|
<http://example.org/gov.uk/def/max_pay>
|
||
Cd1.5 | Td | Cd5 | Rd1 |
"Administrator"
|
"Administrator"
|
<http://example.org/gov.uk/def/job>
|
||
Cd1.6 | Td | Cd6 | Rd1 |
"8.67"
|
8.67
|
<http://example.org/gov.uk/def/number_of_posts>
|
||
Cd1.7 | Td | Cd7 | Rd1 |
"Operational
Delivery"
|
"Operational
Delivery"
|
<http://example.org/gov.uk/def/profession>
|
||
Cd1.8 | Td | Cd8 | Rd1 |
"hefce.ac.uk"
|
"hefce.ac.uk"
|
org:postIn
|
<http://example.org/organization/hefce.ac.uk>
|
|
Cd2.1 | Td | Cd1 | Rd2 |
"90115"
|
"90115"
|
org:reportsTo
|
<http://example.org/organization/hefce.ac.uk/post/90115>
|
|
Cd2.2 | Td | Cd2 | Rd2 |
"5"
|
"5"
|
<http://example.org/gov.uk/def/grade>
|
||
Cd2.3 | Td | Cd3 | Rd2 |
"19546"
|
19546
|
<http://example.org/gov.uk/def/min_pay>
|
||
Cd2.4 | Td | Cd4 | Rd2 |
"22478"
|
22478
|
<http://example.org/gov.uk/def/max_pay>
|
||
Cd2.5 | Td | Cd5 | Rd2 |
"Administrator"
|
"Administrator"
|
<http://example.org/gov.uk/def/job>
|
||
Cd2.6 | Td | Cd6 | Rd2 |
"0.5"
|
0.5
|
<http://example.org/gov.uk/def/number_of_posts>
|
||
Cd2.7 | Td | Cd7 | Rd2 |
"Operational
Delivery"
|
"Operational
Delivery"
|
<http://example.org/gov.uk/def/profession>
|
||
Cd2.8 | Td | Cd8 | Rd2 |
"hefce.ac.uk"
|
"hefce.ac.uk"
|
org:postIn
|
<http://example.org/organization/hefce.ac.uk>
|
Notice
that
value
URL
is
not
specified
for
cells
Ca2.3
and
Cc2.5
because
in
each
case
the
cell
value
is
null
and
the
virtual
annotation
of
column
Cb5
is
not
defined.
Minimal mode output for this example is provided below:
[{ "@id": "http://example.org/organization/hefce.ac.uk/post/90115", "dc:identifier": "90115", "org:heldBy": { "@id": "http://example.org/organization/hefce.ac.uk/person/1", "foaf:name": "Steve Egan" }, "http://example.org/gov.uk/def/grade": "SCS1A", "http://example.org/gov.uk/def/job": "Deputy Chief Executive", "org:reportsTo": "http://example.org/organization/hefce.ac.uk/post/90334", "http://example.org/gov.uk/def/profession": "Finance", "org:postIn": "http://example.org/organization/hefce.ac.uk" }, { "@id": "http://example.org/organization/hefce.ac.uk/post/90334", "dc:identifier": "90334", "org:heldBy": { "@id": "http://example.org/organization/hefce.ac.uk/person/2", "foaf:name": "Sir Alan Langlands" }, "http://example.org/gov.uk/def/grade": "SCS4", "http://example.org/gov.uk/def/job": "Chief Executive", "http://example.org/gov.uk/def/profession": "Policy", "org:postIn": "http://example.org/organization/hefce.ac.uk" }, { "org:reportsTo": "http://example.org/organization/hefce.ac.uk/post/90115", "http://example.org/gov.uk/def/grade": "4", "http://example.org/gov.uk/def/min_pay": 17426, "http://example.org/gov.uk/def/max_pay": 20002, "http://example.org/gov.uk/def/job": "Administrator", "http://example.org/gov.uk/def/number_of_posts": 8.67, "http://example.org/gov.uk/def/profession": "Operational Delivery", "org:postIn": "http://example.org/organization/hefce.ac.uk" }, { "org:reportsTo": "http://example.org/organization/hefce.ac.uk/post/90115", "http://example.org/gov.uk/def/grade": "5", "http://example.org/gov.uk/def/min_pay": 19546, "http://example.org/gov.uk/def/max_pay": 22478, "http://example.org/gov.uk/def/job": "Administrator", "http://example.org/gov.uk/def/number_of_posts": 0.5, "http://example.org/gov.uk/def/profession": "Operational Delivery", "org:postIn": "http://example.org/organization/hefce.ac.uk" }]
Prefixes
defined
within
the
RDFa
1.1
Initial
Context
([
rdfa-core
])
are
not
expanded;
e.g.
dc:
for
<http://purl.org/dc/terms/>.
Output
for
tables
Ta
and
Tb
(
{
"url":
"http://example.org/gov.uk/data/organizations.csv"
}
and
{
"url":
"http://example.org/gov.uk/data/professions.csv"
}
)
are
not
included
as
the
suppress
output
annotation
has
the
value
true
for
each
of
the
tables
.
The property URL is specified for all cells in tables Tc and Td .
Columns
Cc5
and
Cd1
(
{
"name":
"reportsTo"
}
and
{
"name":
"reportsToSenior"
}
)
use
the
about
URL
,
property
URL
and
value
URL
annotations
to
assert
the
relationship
between
the
given
post
and
the
senior
post
it
reports
to
for
the
cells
therein.
However,
since
senior
posts
and
junior
posts
are
described
in
different
tables
it
is
not
possible
to
create
nested
objects
for
this
particular
case.
Similarly,
columns
Cc7
and
Cd8
(both
with
{
"name":
"organizationRef"
}
)
use
the
about
URL
,
property
URL
and
value
URL
annotations
to
assert
the
relationship
between
the
given
post
and
the
organization
to
which
it
belongs
for
the
cells
those
columns
.
Finally,
note
that
two
resources
are
created
for
each
row
within
table
Tc
(
{
"url":
"http://example.org/senior-roles.csv"
}
):
the
person
and
the
post
they
occupy.
The
relationship
between
these
resources
is
specified
via
virtual
column
Cc8
(
{
"name":
"post_holder"
}
)
using
the
about
URL
,
property
URL
and
value
URL
annotations.
The
person
object
provides
the
value
of
the
name-value
pair
with
corresponding
name
org:heldBy
,
thus
nesting
the
person
object
within
the
post
object
.
Standard mode output for this example is provided below:
{ "tables": [{ "url": "http://example.org/senior-roles.csv", "row": [{ "url": "http://example.org/senior-roles.csv#row=2", "rownum": 1, "describes": [{ "@id": "http://example.org/organization/hefce.ac.uk/post/90115", "dc:identifier": "90115", "org:heldBy": { "@id": "http://example.org/organization/hefce.ac.uk/person/1", "foaf:name": "Steve Egan" }, "http://example.org/gov.uk/def/grade": "SCS1A", "http://example.org/gov.uk/def/job": "Deputy Chief Executive", "org:reportsTo": "http://example.org/organization/hefce.ac.uk/post/90334", "http://example.org/gov.uk/def/profession": "Finance", "org:postIn": "http://example.org/organization/hefce.ac.uk" }] }, { "url": "http://example.org/senior-roles.csv#row=3", "rownum": 2, "describes": [{ "@id": "http://example.org/organization/hefce.ac.uk/post/90334", "dc:identifier": "90334", "org:heldBy": { "@id": "http://example.org/organization/hefce.ac.uk/person/2", "foaf:name": "Sir Alan Langlands" }, "http://example.org/gov.uk/def/grade": "SCS4", "http://example.org/gov.uk/def/job": "Chief Executive", "http://example.org/gov.uk/def/profession": "Policy", "org:postIn": "http://example.org/organization/hefce.ac.uk" }] }] }, { "url": "http://example.org/junior-roles.csv", "row": [{ "url": "http://example.org/junior-roles.csv#row=2", "rownum": 1, "describes": [{ "org:reportsTo": "http://example.org/organization/hefce.ac.uk/post/90115", "http://example.org/gov.uk/def/grade": "4", "http://example.org/gov.uk/def/min_pay": 17426, "http://example.org/gov.uk/def/max_pay": 20002, "http://example.org/gov.uk/def/job": "Administrator", "http://example.org/gov.uk/def/number_of_posts": 8.67, "http://example.org/gov.uk/def/profession": "Operational Delivery", "org:postIn": "http://example.org/organization/hefce.ac.uk" }] }, { "url": "http://example.org/junior-roles.csv#row=3", "rownum": 2, "describes": [{ "org:reportsTo": "http://example.org/organization/hefce.ac.uk/post/90115", "http://example.org/gov.uk/def/grade": "5", "http://example.org/gov.uk/def/min_pay": 19546, "http://example.org/gov.uk/def/max_pay": 22478, "http://example.org/gov.uk/def/job": "Administrator", "http://example.org/gov.uk/def/number_of_posts": 0.5, "http://example.org/gov.uk/def/profession": "Operational Delivery", "org:postIn": "http://example.org/organization/hefce.ac.uk" }] }] }] }
@id
annotation
in
the
model
is
ignored
for
JSON.
table
and
title
properties
have
been
changed
to
tables
and
titles
,
respectively,
to
be
consistent
in
the
usage
of
plural
forms.
The document has undergone substantial changes since the first public working draft . Below are some of the changes made: