51
http://thewebsemantic.com http://jenabean.googlecode.com Programming with Jena Sources for examples can be found @ http:// jenabean.googlecode.com/svn/jenabean-la b1 http://jenabean.googlecode.com/svn/ jenaclass Taylor Cowan Travelocity 8982

Programming with Jena

  • Upload
    chin

  • View
    49

  • Download
    1

Embed Size (px)

DESCRIPTION

Programming with Jena. Sources for examples can be found @ http:// jenabean.googlecode.com/svn/jenabean-lab1 http:// jenabean.googlecode.com/svn/jenaclass. Taylor Cowan Travelocity 8982. [] a foaf:Person ; foaf:name Taylor Cowan; foaf:weblog ; - PowerPoint PPT Presentation

Citation preview

Page 1: Programming with  Jena

http://thewebsemantic.com http://jenabean.googlecode.com

Programming with Jena

Sources for examples can be found @

http://jenabean.googlecode.com/svn/jenabean-lab1http://jenabean.googlecode.com/svn/jenaclass

Taylor CowanTravelocity8982

Page 2: Programming with  Jena

2

http://thewebsemantic.com http://jenabean.googlecode.com

[] a foaf:Person;

foaf:name Taylor Cowan;foaf:weblog <http://thewebsemantic.com>;foaf:workplaceHomepage <http://www.travelocity.com>;foaf:holdsAccount <http://twitter.com/tcowan>;foaf:currentProject <http://jenabean.googlecode.com>;foaf:currentProject <http://geosparql.googlecode.com>;foaf:currentProject <http://jo4neo.googlecode.com>;

Page 3: Programming with  Jena

3

http://thewebsemantic.com http://jenabean.googlecode.com

Model m = ModelFactory.createDefaultModel();Thing todaysTopic = new Thing("http://jenabean.googlecode.com", m);

new Thing(m).isa(Foaf.Person.class)

.name("Taylor Cowan")

.weblog(URI.create("http://thewebsemantic.com"))

.holdsAccount(URI.create("http://twitter.com/tcowan"))

.currentProject(todaysTopic)

.currentProject(URI.create("http://jo4neo.googlecode.com"));

@see

Card.java in package example.fluentwriter

Page 4: Programming with  Jena

4

http://thewebsemantic.com http://jenabean.googlecode.com

AGENDA

> Semantic Web Introduction> RDF basics> Coding Towards Jena’s Semantic Web Framework API> Java to Model Binding with JenaBean> Java to Model Binding with Fluent Interfaces

Page 5: Programming with  Jena

5

http://thewebsemantic.com http://jenabean.googlecode.com

Why Not Microformats?<xsl:choose><xsl:when test="(false() = not((.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and (local-name() = 'img' or local-name() = 'area')]/@alt) and (string-length(normalize-space(.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and (local-name() = 'img' or local-name() = 'area')]/@alt)) = string-length(translate(normalize-space(.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and (local-name() = 'img' or local-name() = 'area')]/@alt),' ',''))))) or (false() = not((.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and (local-name() = 'abbr')]/@title) and (string-length(normalize-space(.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and (local-name() = 'abbr')]/@title)) = string-length(translate(normalize-space(.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and (local-name() = 'abbr')]/@title),' ',''))))) or (false() = not((.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and not(local-name() = 'abbr' or local-name() = 'img')]) and (string-length(normalize-space(.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and not(local-name() = 'abbr' or local-name() = 'img' or local-name() = 'area')][1])) = string-length(translate(normalize-space(.//*[not(ancestor-or-self::*[local-name() = 'del']) = true() and contains(concat(' ',normalize-space(@class),' '),' fn ') and not(local-name() = 'abbr' or local-name() = 'img')][1]),' ','')))))">

http://suda.co.uk/projects/microformats/hcard/xhtml2vcard.xsl

Page 6: Programming with  Jena

6

http://thewebsemantic.com http://jenabean.googlecode.com

RDF != XML

“The site at http://www.travelocity.com, also known as Travelocity, is an online travel agency competing with expedia.com”

Page 7: Programming with  Jena

7

http://thewebsemantic.com http://jenabean.googlecode.com

Concepts as a Directed Graph

Travelocity.com Travelocity

Online travel agency

Expedia.com

Page 8: Programming with  Jena

8

http://thewebsemantic.com http://jenabean.googlecode.com

Concepts Serialized as N3

:OnlineTravelAgency a owl:Class .

:hasCompetitor a rdf:Property .

<http://www.travelocity.com> a :OnlineTravelAgency ; rdfs:label "Travelocity"@en ; :hasCompetitor <http://www.expedia.com> .

Page 9: Programming with  Jena

9

http://thewebsemantic.com http://jenabean.googlecode.com

Concepts Serialized as RDF/XML

<rdf:RDF …>

  <owl:Class rdf:about="http://foo#OnlineTravelAgency"/>

  <rdf:Property rdf:about="http://foo#hasCompetitor"/>

  <OnlineTravelAgency rdf:about="http://www.travelocity.com">

    <hasCompetitor rdf:resource="http://www.expedia.com"/>

    <rdfs:label xml:lang="en">Travelocity</rdfs:label>

  </OnlineTravelAgency>

</rdf:RDF>

Page 10: Programming with  Jena

10

http://thewebsemantic.com http://jenabean.googlecode.com

As N-Triples (Most Canonical or Normalized)

<hasCompetitor> <rdf:type> <rdf:Property> .

<http://travelocity.com> <hasCompetitor> <http://expedia.com>.

<http://travelocity.com> <rdfslabel> "Travelocity"@en

<http://travelocity.com> <rdf:type> <OnlineTravelAgency> .

<OnlineTravelAgency> <rdf:type> <owl:Class> .

Subject, Verb, Object = a triple

Page 11: Programming with  Jena

11

http://thewebsemantic.com http://jenabean.googlecode.com

As Java Code, using the Jena API

OntModel m = ModelFactory.createOntologyModel();

OntClass ota = m.createClass("OnlineTravelAgency");

Individual tvly =

ota.createIndividual("http://www.travelocity.com");

tvly.setLabel("Travelocity", "en");

OntProperty p = m.createOntProperty("hasCompetitor");

tvly.setPropertyValue(p,

m.createResource("http://www.expedia.com"));

Page 12: Programming with  Jena

12

http://thewebsemantic.com http://jenabean.googlecode.com

Creating a Model1: Model m = ModelFactory.createDefaultModel();

2: m.setNsPrefix("foaf", FOAF.NS);

3: Resource jazoon = m.createResource("http://jazoon.com/");

4: Resource java = m.createResource(

5: "http://dbpedia.org/resource/Java_(software_platform)");

6: jazoon.addProperty(FOAF.primaryTopic, java);

7: m.write(System.out, "N3");

<http://jazoon.com/> foaf:primaryTopic <http://dbpedia.org/resource/Java_(software_platform)> .

Page 13: Programming with  Jena

13

http://thewebsemantic.com http://jenabean.googlecode.com

Assertion

jazoon.com java

foaf:primaryTopic

Page 14: Programming with  Jena

14

http://thewebsemantic.com http://jenabean.googlecode.com

Creating an Inferencing ModelOntModel infModel = ModelFactory.createOntologyModel(

OntModelSpec.OWL_MEM_MICRO_RULE_INF, m);

infModel.read("http://xmlns.com/foaf/spec/index.rdf");

infModel.writeAll(System.out, "N3",null);

<http://dbpedia.org/resource/Java_(software_platform)> foaf:isPrimaryTopicOf <http://jazoon.com/>

In addition to known data, a new triple is inferred…

Page 15: Programming with  Jena

15

http://thewebsemantic.com http://jenabean.googlecode.com

Knowledge after Inference

jazoon.com

java

foaf:primaryTopic

foaf:isPrimaryTopicOf

foaf:DocumentIs a

Page 16: Programming with  Jena

16

http://thewebsemantic.com http://jenabean.googlecode.com

The Semantic Web is Property focused

> Properties have Classes, not vice versa> Don’t read “the domain of foaf:knows is a foaf:Person”, but instead

“anything with foaf:knows relationship is a foaf:Person”> Properties can extend other properties> Properties can be declared as inverse, symmetric, and transitive, all

resulting in new inferences.

Page 17: Programming with  Jena

17

http://thewebsemantic.com http://jenabean.googlecode.com

List All Classes from an OntologyOntModel model = ModelFactory.createOntologyModel();

model.read("http://xmlns.com/foaf/spec/index.rdf");

ExtendedIterator<OntClass> it = model.listClasses();

while(it.hasNext()) {

OntClass cls = it.next();

if (cls.getNameSpace().equals(FOAF.NS))

System.out.println(cls.getURI());

}

Page 18: Programming with  Jena

18

http://thewebsemantic.com http://jenabean.googlecode.com

Models Can be Populated from URL, Either Public or LocalOntModel model = ModelFactory.createOntologyModel();// read from URLmodel.read("http://xmlns.com/foaf/spec/index.rdf");

model.read("file:mydata.n3","N3");

Page 19: Programming with  Jena

19

http://thewebsemantic.com http://jenabean.googlecode.com

Models can be Populated from Other Models

Model modelA = ModelFactory.createDefaultModel();Model modelB = ModelFactory.createDefaultModel();…//Add all statements from modelB to modelAmodelA.add(modelB);

Page 20: Programming with  Jena

20

http://thewebsemantic.com http://jenabean.googlecode.com

Some example foaf:

<http://www.ibm.com/developerworks/xml/library/j-jena/>

a dc:Article ;

dc:creator "Philip McCarthy"^^xsd:string ;

dc:subject "jena, rdf, java, semantic web"^^xsd:string ;

dc:title "Introduction to Jena"^^xsd:string .

Page 21: Programming with  Jena

21

http://thewebsemantic.com http://jenabean.googlecode.com

Equivalent Raw Jena API Client Code

String NS = "http://purl.org/dc/elements/1.1/";OntModel m = ModelFactory.createOntologyModel();OntClass articleCls = m.createClass(NS +"Article");Individual i = articleCls.createIndividual( "http://www.ibm.com/developerworks/xml/library/j-jena/");Property title = m.getProperty(NS + "title");Literal l = m.createTypedLiteral("Introduction to Jena");i.setPropertyValue(title,l);Property creator = m.getProperty(NS + "creator");l = m.createTypedLiteral("Philip McCarthy");i.setPropertyValue(creator,l);Property subject = m.getProperty(NS + "subject");l = m.createTypedLiteral("jena, rdf, java, semantic web");i.setPropertyValue(subject,l);m.write(System.out, "N3");

Page 22: Programming with  Jena

22

http://thewebsemantic.com http://jenabean.googlecode.com

Pain Points of Raw Jena API Programming

> You need to create unique URI’s for every entity.> You must specify the type of each primitive value.> Properties must be created for each bean property.> The impedance mismatch is similar to what we had with RDBMS

Page 23: Programming with  Jena

23

http://thewebsemantic.com http://jenabean.googlecode.com

Creating The Same Assertions with JenaBean

Model m = ModelFactory.createDefaultModel();Bean2RDF writer = new Bean2RDF(m);Article article = new Article( "http://www.ibm.com/developerworks/xml/library/j-jena/");article.setCreator("Philip McCarthy");article.setTitle("Introduction to Jena");article.setSubject("jena, rdf, java, semantic web");writer.save(article);m.write(System.out, "N3");

Page 24: Programming with  Jena

24

http://thewebsemantic.com http://jenabean.googlecode.com

The JenaBean Project

> Hosted at Google code> Bean binding, not code generation> Doesn’t use byte code interweaving> Doesn’t require implementing an interface> http://jenabean.googlecode.com

Page 25: Programming with  Jena

25

http://thewebsemantic.com http://jenabean.googlecode.com

Programming with JenaBean is Simple

> Bean2RDF writes objects> RDF2Bean reads objects> 3 Annotations

– @Id specifies unique field– @Namespace provides a domain– @RdfProperty maps java properties to RDF properties

Page 26: Programming with  Jena

26

http://thewebsemantic.com http://jenabean.googlecode.com

The Simplest Possible Examplepackage examples.model;import thewebsemantic.Id;public class Person { @Id private String email; public String getEmail() { return email;} public void setEmail(String email) { this.email = email;}}

<http://examples.model/Person> a <http://www.w3.org/2000/01/rdf-schema#Class> ; <http://thewebsemantic.com/javaclass> "examples.model.Person" .

<http://examples.model/Person/[email protected]> a <http://examples.model/Person> ; <http://examples.model/email> "[email protected]"^^xsd:string .

Page 27: Programming with  Jena

27

http://thewebsemantic.com http://jenabean.googlecode.com

Saving an Instance of Person

Model m = ModelFactory.createOntologyModel(); Bean2RDF writer = new Bean2RDF(m); Person p = new Person(); p.setEmail("[email protected]"); writer.save(p); m.write(System.out, "N3");

<http://example/Person> a owl:Class ; <http://thewebsemantic.com/javaclass> "example.Person" . <http://example/Person/[email protected]> a <http://example/Person> ; <http://example/email> "[email protected]"^^xsd:string .

Page 28: Programming with  Jena

28

http://thewebsemantic.com http://jenabean.googlecode.com

Overriding the Default Namespacepackage examples.model;

import thewebsemantic.Id;import thewebsemantic.Namespace;

@Namespace("http://mydomain#")public class Person { … }

<http://mydomain#Person> a <http://www.w3.org/2000/01/rdf-schema#Class> ; <http://thewebsemantic.com/javaclass> "examples.model.Person" .

<http://mydomain#Person/[email protected]> a <http://mydomain#Person> ; <http://mydomain#email> "[email protected]"^^xsd:string .

Page 29: Programming with  Jena

29

http://thewebsemantic.com http://jenabean.googlecode.com

Overriding the Default Property Bindings@Namespace(“http://mydomain#”)public class Person { private String email; @RdfProperty(FOAF.NS + "name") private String name;

<http://mydomain#Person> a <http://www.w3.org/2000/01/rdf-schema#Class> ; <http://thewebsemantic.com/javaclass> "examples.model.Person" .

<http://mydomain#Person/[email protected]> a <http://mydomain#Person> ; <http://xmlns.com/foaf/0.1/name> "Taylor Cowan"^^xsd:string .

Page 30: Programming with  Jena

30

http://thewebsemantic.com http://jenabean.googlecode.com

Extending Person to Support Friendship

public Collection<Person> friends = new LinkedList<Person>();

@RdfProperty("http://xmlns.com/foaf/0.1/knows")public Collection<Person> getFriends() { return friends;}

Page 31: Programming with  Jena

31

http://thewebsemantic.com http://jenabean.googlecode.com

Loading Beans from a Model

RDF2Bean reader = new RDF2Bean(m);

Person p = reader.load(Person.class,"[email protected]");

Collection<Person> allPeople = reader.load(Person.class);

Page 32: Programming with  Jena

32

http://thewebsemantic.com http://jenabean.googlecode.com

JenaBean Support for OWL Entailments

public class Location {@Idpublic String id;

public String name;

@RdfProperty(transitive=true)public Collection<Location> within;

@RdfProperty(inverseOf="within")public Collection<Location> contains;

…<http://example.transitive/within>

a rdf:Property , owl:TransitiveProperty .

<http://example.transitive/contains>

a rdf:Property ;

owl:inverseOf <http://example.transitive/within> .

Page 33: Programming with  Jena

33

http://thewebsemantic.com http://jenabean.googlecode.com

Reading Existing RDF/OWL

> Up till this point we were generating the triples> JenaBean + annotations controlled the URI’s> The model knew the provenance of all data (the originating java

class)

Page 34: Programming with  Jena

34

Example Geonames “feature” entry

<Feature rdf:about="http://sws.geonames.org/3333156/">

<name>London Borough of Islington</name>

<alternateName xml:lang="fr">Islington</alternateName>

<inCountry rdf:resource="http://www.geonames.org/countries/#GB"/>

<population>185500</population>

<wgs84_pos:lat>51.5333333</wgs84_pos:lat>

<wgs84_pos:long>-0.1333333</wgs84_pos:long>

</Feature>

Jenabean will bind to existing URI’s

Page 35: Programming with  Jena

35

http://thewebsemantic.com http://jenabean.googlecode.com

Crafting beans for existing RDF requires care

@Namespace("http://www.geonames.org/ontology#")public class Feature {

@Id private URI uri;

@RdfProperty("http://www.w3.org/2003/01/geo/wgs84_pos#lat") public double lat;

12

34

1. Namespace must accurately match2. Your java’s classname must match the Ontology class3. Your @Id must be of type java.net.URI4. All property URI’s must match the Ontology property

Page 36: Programming with  Jena

36

http://thewebsemantic.com http://jenabean.googlecode.com

JenaBean can auto discover JenaBeans, provided it knows the package(s) 1: Model m = ModelFactory.createDefaultModel();2: m.read("http://ws.geonames.org/search?q=london&type=rdf");3: RDF2Bean reader = new RDF2Bean(m);4: reader.bindAll("com.foo", "com.bar");

// type safe binding by classreader.bind(Feature.class);

// or packagereader.bind(Feature.class.getPackage());

Page 37: Programming with  Jena

37

http://thewebsemantic.com http://jenabean.googlecode.com

JenaBean tip: handling lang encoded strings

If your data has something like this:

<alternateName xml:lang="es">Londres</alternateName>

Then use JenaBean‘s special type “LocalizedString“

public Collection<LocalizedString> alternateName;

example.geonames

Page 38: Programming with  Jena

38

http://thewebsemantic.com http://jenabean.googlecode.com

Query Support

// load using a Jena Resourcereader.load(Human.class, jenaResource);

// load any node using it’s URIreader.load(Human.class, "http://any.uri");

> Most most practical purposes there’s no need to utilize anything other than Jena’s ARQ api to query. JenaBean’s reader (RDF2Bean) can transform a node given it’s URI or it’s representation as a jena Resource…

Page 39: Programming with  Jena

39

http://thewebsemantic.com http://jenabean.googlecode.com

thewebsemantic.Sparql UtilString query = "prefix ntn: <http://semanticbible.org/ns/2006/NTNames#>\n" +"SELECT ?s WHERE { ?s a ntn:Woman }";Model m = ModelFactory.createOntologyModel();m.read("file:NTNames.owl");m.read("file:NTN-individuals.owl");

RDF2Bean reader = new RDF2Bean(m);reader.bindAll("example.query");

Collection<Woman> women = Sparql.exec(m, Woman.class, query);

for (Human human : women) System.out.println(human.label + ":" + human.comment);

example.query

Page 40: Programming with  Jena

40

http://thewebsemantic.com http://jenabean.googlecode.com

Summary

@Namespace(“http://yournamespace.goes.here”)Applies to class declaration

@IdApplies to field or getter methodShould be a String or primitive type, or wrapper typetype java.net.URI is special

@RdfProperty(“http://specific.property.uri”)Applies to field or getter method

Remember: by definition, JavaBeans must have a default constructor.

Page 41: Programming with  Jena

41

http://thewebsemantic.com http://jenabean.googlecode.com

Summary

writer.save(mybean)

writer.saveDeep(mybean)Save this and all related objects

reader.load(Class.class, key);

reader.loadDeep(…);take care, could place entire graph into memory.

reader.bindAll(package, package, …);Makes jenabean aware of your beans

Page 42: Programming with  Jena

42

http://thewebsemantic.com http://jenabean.googlecode.com

JenaBean Fluent Programming API

> AKA method chaining, foo.this().that().bar();> A “Fluent Interface” aims to provide more readable code> A significant departure from JavaBeans> Is always connected to the jena graph> Entirely interface (not class) driven> Allows Individuals to morph into their various classes> Allows use of vocabulary terms against any Individual regardless

of classification.

Page 43: Programming with  Jena

43

http://thewebsemantic.com http://jenabean.googlecode.com

Example: wgs84 geo vocabulary

import thewebsemantic.As;import thewebsemantic.Functional;import thewebsemantic.Namespace;

@Namespace("http://www.w3.org/2003/01/geo/wgs84_pos#")public interface Geo extends As {

interface Point extends Geo{}

@Functional Geo lat(float l); Float lat();

@Functional Geo long_(float l); Float long_();

}

Page 44: Programming with  Jena

44

http://thewebsemantic.com http://jenabean.googlecode.com

A fluent api + good IDE makes things fun

Page 45: Programming with  Jena

45

http://thewebsemantic.com http://jenabean.googlecode.com

Create a new anonymous iCal event.

Ical t = new Thing(m).isa(Ical.Vevent.class);

Create a new iCal event with URI

Ical t = new Thing(“http://uri”, m).

isa(Ical.Vevent.class);

Page 46: Programming with  Jena

46

http://thewebsemantic.com http://jenabean.googlecode.com

Full Example: Creating an iCal event for the meetup1: Ical.Vevent t = new Thing(m).isa(Ical.Vevent.class);2: t.uid("[email protected]").3: dtstart("20100124T200000Z").4: dtend("20100124T220000Z").5: summary("Jena Semantic Web…").6: location("Parisoma - …")7: .as(Geo.class).8: lat(37.77f).9: long_(-122.41f);

[] a ical:Vevent ; ical:dtend "20100124T220000Z" ; ical:dtstart "20100124T200000Z" ; ical:location "Parisoma - " ; ical:summary "Jena Semantic Web…" ; ical:uid "[email protected]" ; geo:lat "37.77"^^xsd:float ; geo:long "-122.41"^^xsd:float .

Page 47: Programming with  Jena

47

http://thewebsemantic.com http://jenabean.googlecode.com

JenaBean comes with a few common vocabulary interfaces> thewebsemantic.vocabulary.Foaf> Geo> Ical> DCTerms> Sioc> Skos> Rdfs> ReviewVocab> You may want to copy and modify in some cases.

Page 48: Programming with  Jena

48

http://thewebsemantic.com http://jenabean.googlecode.com

Fluent API summary:> Your interface should extend thewebsemantic.As

> Provides polymorphic “as(Class)” to other vocabs.> Provides easy type declaration with “isa(Class)”

> Use the @Namespace annotation to bind to the vocabulary> Name setters according to vocab, taking either an Object (literal) or

anther Thing (relationship to other Individuals)> Name getters according to vocab, returning the same vocabulary type

and taking no arguments.> If the vocabulary term collides with reserved term (as with long), append

a dash.> Plural properties should return a Collection.

Page 49: Programming with  Jena

49

http://thewebsemantic.com http://jenabean.googlecode.com

Project Ideas

> Create your own foaf document using the fluent interface.

> Integrate Jena/JenaBean with restlets– restlets.org

> Use your favorite framework (struts, stripes, spring mvc) and create a user registration screen.

> Write JenaBeans that bind to jamendo or other music ontology at http://dbtune.org

> Write a foaf crawler beginning with Berners-Lee that traverses his social graph.

cc nickjohnson http://flickr.com/photots/npj/

Page 50: Programming with  Jena

50

http://thewebsemantic.com http://jenabean.googlecode.com

Open Source Tools For Java Devs

> Java Triple Stores– Jena (HP Labs)– Sesame OpenRDF (Aduna)– Mulgara

> Java Binding tools– JenaBean (Jena)– Jastor (Jena)– Owl2Java (Jena)– Elmo (Sesame)– Empire

cc nickjohnson http://flickr.com/photots/npj/

Page 51: Programming with  Jena

http://thewebsemantic.com http://jenabean.googlecode.com

Taylor Cowanhttp://thewebsemantic.com

http://twitter.com/[email protected]