finally a bnode with a uri

Posts tagged with: forms

Custom auto-generated custom auto-... RDF forms

Still looking for the best approach...
After my last post, I spent some more time on the custom RDF templates, trying to generalize and automate as much of the form generation process as possible.

The first step was to create a re-usable parent-class for custom templates with methods for standard tasks such as the retrieval of property labels and comments, as well as the automatic creation of simple properties.
Additionally, the list of available templates is now created from a little configuration file where each template definition consists of three simple fields: a label, a target class, and an identifying name to later find the custom template class. The target class is used to make sure that the template can be used with resources of a certain type (or inferred sub-type) only.

Upon form creation, the custom template class is instantiated, and a "get_fld_infos" method returns an array of form field parameters that can be used to generate input fields, textareas, checkboxes, and the related labels and property comments. E.g. the following code snippet creates a simple input field:
array(
  "name"=>"dc__publisher",
  "type"=>"str1",
  "label"=>$this->get_prop_label("dc:publisher"),
  "info"=>$this->get_prop_comment("dc:publisher")
)

When a custom form is submitted, the generic template class checks for each form field if the custom class has a "custom creation" method defined, otherwise it will assume that the field is a standard field with either a literal or a URI value. (The script then does ontology look-ups to determine the value type of the property.)

For any non-simple field/property, the custom template has to provide a special method to create the triples "manually". I still had several almost identical methods that did nothing but splitting "one-entry-per-line"-textarea values into single values. So I added an option that allowed me to use textareas for a list of URIs/values, without having to write custom creation methods (by marking a field definition with a simple "is_list"=>true).

So, the only thing that actually remained were blank nodes, i.e. where the template just "asks" for a single value (e.g. a doap:revision identifier), but the script has to create a bnode of a certain type, plus a property with the submitted value (e.g. doap:release -> doap:Version -> doap:revision ->value).

However, that's also a pattern I could generalize, moving the create_bnode_property method in the parent class. I still need the custom methods, but they are rather small now. Only the connecting property, the class, and the properties of the bnode have to be defined.

I've built a custom DOAP-template today, it is generated from a single 7K php class. And the form still looks ok, too. Give it a try and describe your SemWeb project, the template is now available at beta.semanticweb.org in the "Quick-add" section, after creating/selecting a foaf:Project or a doap:Project.

Pimping my RIDE, and shifting down

RDF Instance Data Editing
You all know MTV's Pimp My Ride show where they tune a car until you almost forget its original purpose. While working on my RIDE I sometimes got the impression of maybe also adding too many features to it and losing overall usability.

My main problem was that I had a list of requirements that couldn't be implemented with custom forms in a reasonable amount of time:
  • auto-generating tooltip-like information for each form field
  • separating the RDF editing front-end from the (OWL) model, so that changing the model doesn't force me to adjust the editor
  • offering editing forms for more than 15 different resource types and at the same time making sure that any possibly "fitting" property can be attached to a selected resource
  • being able to define validation and auto-adjust procedures at the model- and not at the forms-level.
  • keeping the editing UI scalable by offering multi-page forms, and filters on namespaces, properties, and property values

However, other requirements were also that
  • people not too familiar with all those RDF characteristics (blank nodes, striping, etc.) and the various different RDF vocabularies should also be able to create and maintain resource descriptions.
  • the UI should not get too big and should not have too many options which rather confuse than help

The latter appeared trickier to implement to me than the more technical requirements, but let's start at the beginning of the list:

auto-generating tooltip-like information

The editor needs an API that allows it to retrieve rdfs:comment annotations for a given property URI. Once such an interface to the OWL model is available (I'm using OWLchestra for this), generating the info texts is easy. Even the creation of a multilingual interface is straight-forward as long as the annotations are available in different languages.

separating the RDF editing front-end from the (OWL) model

The editing forms are created on the fly. This requires the availability of label and comment information for each property. It's also neccessary (for my tool), that each property has a defined domain and range (this can be rdfs:Resource, though). Literal properties should have a datatype set which is needed to auto-generate the different widgets (single-line text fields vs. checkboxes vs. multi-line textareas). I've tweaked my OWL editor so that custom datatypes (with possibly custom widgets) can be created. (I'm still considering a switch to Dan Connolly's new rdfIcal design, which uses timezone datatypes. If I moved to the new design I could create a custom datatype for dtstart/dtend and a widget where users could enter date, time, and timezone.)

offering editing forms for many resource types with different sets of possible properties

As the forms are generated on the fly, there is no need to adjust the editor when new resource types are added to the model. However, I'm using drop-down lists to choose a class or property, so there is a limit for the number of classes and properties the system can support before things get clumsy. The initial model at the SemanticWeb.org Beta site contains about 30 classes and 200 properties (collected on a relaxed term-shopping day ;). I managed to keep the drop-downs somewhat small by defining mappings between the different vocabularies and adjusting domains and ranges where possible, but I don't think I'll be able to add many more. At least not many generic properties with a domain of rdfs:Resource.

defining validation and auto-adjust procedures

Validation functions can be defined in two ways: OWLchestra's datatype editor allows to specify an external validation function for a datatype, and an annotation property can be used to "assign" an auto-adjust function to a property. I'm still not sure if this use of annotation properties is considered a hack, but they are very handy to define little hints whenever needed. And they allow me to standardize form validation, but also to add custom features such as auto-converting an entered email-address to a valid foaf:mbox or foaf:mbox_sha1sum.

keeping the editing UI scalable

In order to keep response times acceptable, I'm using two DHTML-generating PHP classes: A table class and a Tab box class. Using the table class, I don't have to worry too much about sorting and splitting the result sets on multiple views. The tab box class makes it possible to provide a consistent look and feel (I hope) for the lists, filters, details forms, and creation forms. The tabs can also be used to only load/refresh a certain part of the whole form, and to hide functionality that's not needed for the task at hand.

OK, now to the less-technical requirements:

"Easy editing" forms, more compact UI

I was happy when the forms started to work, but there surely is much space for improvements. Making certain fieldsets collapsible helped a little, but having to add properties one by one wasn't really cool. And although this is the only way to manage resources with many properties, and even after having added a "multi-edit" feature for properties, I'd still have preferred the foaf-a-matic over my tool to create an initial resource description, or a one-page form with limited functionality for a small resource description.

So I went back to the drawing-board and redesigned the main "overview tab" you see when you select a resource. It shows now a "quick-edit" form where you can edit up to 20 properties in one form. Properties of the same type are grouped. It's not possible to adjust the language of literals, to change the publication setting, or to update blank nodes. But the form is nice and small and each field still has rdfs:comment information where available.

Next to the "quick-edit" tab is another new tab labeled "quick-add". The quick-add tab enables the creation of semi-hard-coded *-a-matics. Selecting it will let you choose from a list of templates such as "Basic FOAF description", "A list of depictions", "Import PPD", or "Basic DOAP description". These templates are defined at the form level, but can still use labels and tooltip infos from the model. Each template field can be defined as being a "standard" field or a custom field. Standard fields will create simple triples, custom fields can be used to manually create bnodes or more complex triples (e.g. turning a simple IATA code value into a resource property contact:nearestAirport linking to an air:Airport resource with the entered air:iataCode.

So, after building this auto-generate-everything editor, I'm returning to (at least partly) custom forms. Funny. (Well, sooner or later I'm going to need the advanced features, though, the UI scalability argument still holds true.)


The templates are still experimental, some don't even work at all. But I dared uploading the whole stuff to beta.semanticweb.org, and if you like to give it a try and send me some feedback, comments, or bug reports, I'll really appreciate that. I can test the editor with windows browsers only, so I don't know how the app looks or works on other systems. (By the way, it's not possible to browse resource descriptions or site content yet, all you can do is signing-up, playing with the profile and the RDF editor, and generating RDF/XML.) If you don't want to register, you can alternatively use the account alec (with pwd tronnick). Alec is an RDF crash test dummy and will be around during the pre-beta phase.

Handling blank nodes in RDF editing forms

User-friendly RDF editing.
One of the bigger problems when designing editing/creation forms as a front-end to an RDF store is the support for blank nodes. Although it's easy to offer a "don't auto-assign a URI to this resource" checkbox when a new resource is created (i.e. allow blank subjects), things get more complicated with blank objects.

Let's assume someone is creating a FOAF description of himself. As mentioned above, it's straight-forward to offer a simple form with a class drop-down (to select foaf:Person) and a checkbox to mark the new resource as "blank". After adding some basic attributes (name, etc.) the user may now want to add his date of birth. A common way to do this is by linking the person resource via the bio:event property to a blank bio:Birth resource. The date of birth is then assigned to the birth resource (see example below).
<foaf:Person>
  <foaf:name>Benjamin Nowack</foaf:name>
  <bio:event>
    <bio:Birth>
      <bio:date>1973-08-14</bio:date>
    </bio:Birth>
  </bio:event>
</foaf:Person>
Another example is the description of foaf:knows relations:
<foaf:Person>
  <foaf:name>Benjamin Nowack</foaf:name>
  <foaf:knows>
    <foaf:Person>
      <foaf:name>Andreas Harth</foaf:name>
      <foaf:homepage rdf:resource="http://www.harth.org/andreas/"/>
    </foaf:Person>
  </foaf:knows>
</foaf:Person>

The first approach that comes to mind is to simply let users create additional blank nodes (a bio:Birth or foaf:Person in this case), and then to offer them a way to link the base resource to the newly created ones. However, this solution has two UI issues:

First, we can't use simple html drop-down lists to pick a resource as the RDF store may contain hundreds or thousands of possibly fitting resources. We could restrict the resources to choose from to those created by the current user, i.e. the user can only relate his/her "own" resources to each other. But this can still lead to scalability problems (imagine Marc Canter going to enter his foaf:knows relations ;), and furthermore, we end up with lots of redundant information in the RDF store.

The second problem is that for simple cases like the birthday one, the user has to do a lot of clicking and typing.

But how can we implement these use cases in a generic way without putting the burden too much on the user?
I've spent several weeks now on building an editing front-end for OWLchestra's RDF store. Unfortunately, I didn't manage to come up with a solution which would be as easy to use as e.g. Leigh Dodds' foaf-a-matic but would also allow to create forms completely from an OWL model, and would also scale. However, here is my approach for the editing front-end of the new semanticweb.org portal (I'm finally almost there):

The editing form for relations (i.e. owl:ObjectProperties) allows users to create blank nodes by simply not providing a URI for the related resource. Additionally, it's possible to reference a resource by description. (This is a common pattern in FOAF where you say that you know someone who is a person with a homepage foo. FOAF offers a bunch of uniquely identifying properties which enable identification of blank resources afterwards.) So it is at least possible now to create the types of relations mentioned above in a single step (see screenshot below).
screenshot: add relation
After selecting the relation, the list of available properties for the related blank node is created from the underlying OWL model. Also, the "Object type" is pre-selected, but can be modified (in the screenshot above, it could be set to bio:Birth). In order to avoid that people start using the "reference by description" forms to fully describe resources (I'm still trying to keep redundancy low), the number of possibe properties for the linked resource is limited to 4.

I've added some javascript remote scripting stuff to reduce the response times, so when you are editing a relation, only the form is refreshed, not the whole page. It is also possible to edit only certain types of relations (by pre-setting a namespace or a property), and there are both single- and multi-edit modes for updating relations (e.g. "the first 10 foaf:knows relations sorted by modification time").

Although I was quite happy so far, entering all the identifying information of resources which are already described by lots of other people was not as usable as I'd have liked it to be. Why do I have to type in a person's email, weblog, name, etc., if the information is perhaps already in the RDF store and could be re-used?

I don't know if I had eaten too many chocolate bars today, but somehow I found myself working on a find-as-you-type feature to automate filling in the required fields of the form. Yay, I can imagine the funny conversation I'm going to have with the DERI guys:
them: Benjamin, are you MAD? That's going to kill any RDF store!
me: No worries, it worked fine on my test machine.
them: But how many triples are in your test store, dude?
me: More than 900, almost 1000! It scales just fine!
them:""
me: Hey, where are you going? What's wrong? Hello..?
But if we forget the back-end for a second, the utility of such an inline-popup to select from is really great. I've added a delay to the execution which reduces the server hammering, and even if you'd have to wait 10 seconds for the result, that's still faster than typing the information by hand. Here is how it works:

The user selects the type of the related resource. He then starts typing in the "Find object" field. As soon as he pauses, a javascript function is invoked which sends the selected class id and the letters to the server. The server script uses this information to query the RDF store for resoures of the given type and object values matching these letters. In a second step, the RDF store is queried again to retrieve the labels, uniquely identifying properties, and seeAlso links for the resources found in step one.

In order to not kill the server, the result list is limited to 5 entries. Furthermore, the bits which require inferencing or model operations (finding possible label properties for a given class, getting a list of available inverse functional properties, including subclasses) are stored in the user's session object, so they slow down the machine only during the first request.

After retrieving the information from the store, a javascript-friendly result is generated and sent back to the browser, where another script updates the list of matching resources.

screenshot: find as you type
In the ideal case, the server sends sufficient information to help the user choose the right resource. Clicking on one of the entries auto-completes the form:

screenshot: auto-fill

That's as usable as I could get it, but still far away from what we are used to from "normal" HTML forms. Maybe it's just that RDF is too generic (subject-predicate-object) to be stripped down to simple forms (if we don't want them to look like a direct view on the triple store), I don't know.

Well, there is still the possibility to create custom forms and to do the RDF mapping in a separate step. But that's a different story and for now, I'll stick to the generic approach. User feedback may well change this, though ;)

Still alive and clicking

RDF editing forms
Clicking what? Crazy RDF editing forms.

screenshot thumbnail

It wasn't me, they grew on their own! (And the RDF model doesn't really make it easy to hide complexity without losing functionality.)

I'm just hoping that this stuff is going to work in your browsers as well...

Archives/Search

YYYY or YYYY/MM
No Posts found

Feeds