REST

From BaseX Documentation
Revision as of 14:55, 12 September 2011 by CG (talk | contribs) (→‎GET Requests)
Jump to navigation Jump to search

BaseX offers a RESTful API for accessing distributed XML resources. REST (REpresentational State Transfer) facilitates a simple and fast access to databases through HTTP. The HTTP methods GET, PUT, DELETE, and POST can be applied to interact with the database. The REST implementation has formerly been based on JAX-RX, an interface layer to provide unified access to XML databases and resources. With the release of Version 6.8 of BaseX, it will be reimplemented to allow for a much closer integration with the XQuery processor of BaseX, WebDAV, and many other database features.

Start BaseX server and client

First of all, please launch a HTTP Server instance of BaseX: double click on the BaseX HTTP icon, or run the basexhttp script. Follow this link for some more information (or check out the additional command-line options).

Some browsers, such as Opera, can be used to directly display the results of REST requests. Some more alternatives how to use REST are listed in the Usage Examples Paragraph.

URL Architecture

The root URL lists all available databases. The following examples assume that you have created a database instance from the factbook.xml document:

http://admin:admin@localhost:8984/rest
 
<rest:databases resources="1" xmlns:rest="http://www.basex.org/rest">
  <rest:database resources="1" size="1813599">factbook</rest:database>
</rest:databases>

The resources of a database can be listed by specifying the database, and potential sub directories, in the URL. In the given example, a single document is stored in the factbook database:

http://admin:admin@localhost:8984/rest/factbook
 
<rest:database name="factbook" resources="1" xmlns:rest="http://www.basex.org/rest">
  <rest:resource type="xml" size="77192">factbook.xml</rest:resource>
</rest:database>

The contents of a database can be accessed by adding the query parameter to the path:

http://admin:admin@localhost:8984/rest/factbook?query

If a resource is not found, an HTTP response will be generated with 404 as status code.

Query Parameters

GET and POST requests can be extended with a number of parameters. Only one of the following operations can be specified:

  • query
Evaluates an XPath/XQuery expression.
If a database or database path is specified in the URL, it is used as query context.
  • run
Runs a query file located on the server.
The query directory is defined by the HTTPPATH option.
  • command
Executes a database command.

The following parameters can be applied to the query and run operations:

  • wrap
Wraps the results in XML elements (default: no).
  • Variables: all query parameters prefixed with a dollar sign ($) will be treated as external variables. The parameter name and value will be bound to the query before it is evaluated.
  • Serialization: all serialization parameters known to BaseX can be specified as query parameters. Parameters that are specified within a query will be interpreted by the REST server before the output is generated.

Request Methods

GET Requests

Using GET, all query parameters can be directly specified within the URL. The following example prints the first five city names from the factbook database:

http://admin:admin@localhost:8984/rest/factbook?query=(//city/name)[position()<=5]

The next request chooses US-ASCII as output encoding and opens the database within the XQuery expression:

http://admin:admin@localhost:8984/rest?query=distinct-values(db:open('factbook')//religions)&encoding=US-ASCII

The next URL turns on XML wrapping and lists all database users registered in BaseX:

http://admin:admin@localhost:8984/rest?command=show+users

POST Requests

The POST method offers two different operations:

Add New Resources

By default, the HTTP request body will be added as new XML document to the specified database. For example, if a document is sent as body of the POST request to the URL localhost:8984/rest/DB, the document will be added to the DB database, and the 201 (Created) status code will be returned to confirm that everything went alright.

Execute Queries & Commands

If application/query+xml is chosen as content type, the HTTP request body is interpreted as query. The body must conform to this XML Schema.

The output of the following query equals the above GET request:

<query xmlns="http://www.basex.org/rest">
  <text><![CDATA[ (//city/name)[position() <= 5] ]]></text>
</query>

The following POST request prints the registered database users in the specified ISO-8859-1 encoding:

<command xmlns="http://www.basex.org/rest">
  <text>show users</text>
  <parameter name='encoding' value='ISO-8859-1'/>
</command>

PUT Requests

The PUT method can be used to create or update a database resource.

Usage
Use PUT to send the URL and upload the input XML document.
Example
A new database with the name XMark is created if the URL localhost:8984/rest/XMark is sent via PUT, followed by the input XML file in the HTTP body. The document will have the same name as the database.

If the process was successful, a HTTP response with status code 201 (CREATED) is sent back. Otherwise, 404 will be sent.

DELETE Requests

The DELETE method can be applied to delete single resources.

Usage
Use DELETE to send the URL pointing to the database or resource to be deleted.
Example
The factbook database is deleted via the DELETE method and the URL localhost:8984/rest/factbook.

If deletion was successful, the HTTP status code 200 (OK) will be sent. If not, 404 is returned.

Assigning Variables

GET Requests

Query parameters prefixed with a dollar sign ($) will be handled as external variables:

Query:

declare variable $x as xs:integer external;
declare variable $y as xs:integer external;
$x * $y

Variables: Set the values of the variables with: &$x=21&$y=2

Complete request (compact notation, omitting the explicit variable declarations):

http://admin:admin@localhost:8984/rest?query=$x*$y&$x=21&$y=2

POST Requests

Using POST, the <variable/>> element is used to bind external variables to a query:

<query xmlns="http://www.basex.org/rest">
  <text>
    declare variable $x as xs:integer external;
    declare variable $y as xs:integer external;
    $x * $y
  </text>
  <variable name="x" value="21"/>
  <variable name="y" value="2"/>
</query>

Response Media Type

The media type of a REST response is chosen in several steps (to be revised for Version 6.8):

  1. The value of the wrap parameter determines the initial media type (default: yes):
    • yesapplication/xml
    • notext/plain
  2. If a valid value for "method" has been specified via the output parameter, the media type is overwritten:
    • xmlapplication/xml
    • xhtmlapplication/xhtml+xml
    • htmltext/html
    • texttext/plain
  3. Last, the type is overwritten if a valid value for "media-type" has been specified via the output parameter.

To give two examples, the following URLs will all choose text/plain as response media type:

http://admin:admin@localhost:8984/rest?query=1&wrap=yes
http://admin:admin@localhost:8984/rest?query=1&method=xml
http://admin:admin@localhost:8984/rest?query=1&media-type=application/xml

Usage Examples

Java

Most programming languages offer libraries to communicate with HTTP servers. The following example demonstrates how easy it is to perform a DELETE request with Java:

// The java URL connection to the resource. 
URL url = new URL("http://admin:admin@localhost:8984/rest/factbook"); 
 
// Establish the connection to the URL. 
HttpURLConnection conn = (HttpURLConnection) url.openConnection(); 
// Set as DELETE request. 
conn.setRequestMethod("DELETE"); 
 
// Print the HTTP response code. 
System.out.println("\n* HTTP response: " + conn.getResponseCode()); 
 
// Close connection. 
conn.disconnect(); 

Find Java examples for all methods here: GET, POST (Add), POST (Query), PUT, DELETE.

Command Line

Next, tools such as the Linux command cURL exist to perform HTTP requests (try copy & paste):

GET
curl -i "admin:admin@localhost:8984/rest/factbook?query=//city/name&count=5"
POST (Add)
curl -i -H "Content-Type: text/xml" -d "<HelloWorld/>" "admin:admin@localhost:8984/rest/collection"
POST (Query)
curl -i -X POST -H "Content-Type: application/query+xml" -d
"<query xmlns='http://www.basex.org/rest'><text>//city/name</text><parameter name='count' value='5'/></query>"
"admin:admin@localhost:8984/rest/factbook"
curl -i -X POST -H "Content-Type: application/query+xml" -T query.xml "admin:admin@localhost:8984/rest/factbook"
PUT
curl -i -X PUT -T "etc/xml/factbook.xml" "admin:admin@localhost:8984/rest/factbook"
DELETE
curl -i -X DELETE "admin:admin@localhost:8984/rest/factbook"

User Management

By default, the HTTP server starts with no pre-defined user. Users and passwords can be sent via HTTP basic access authentication with each HTTP request. As an alternative, users and passwords can also be specified as command-line arguments or via the "user.basex.user" and "user.basex.password" system properties before the HTTP server is started.

With some browsers and with cURL, you can send specify the user name and password with each HTTP request within the request string as plain text, using the format USER:PASSWORD@URL. An example:

GET
curl -i "bob:alice@localhost:8984/rest/factbook"

Java Example

Basic access authentication can be activated in Java by adding an authorization header to your HttpURLConnection instance. The header contains the word Basic, which specifies the authentication method, followed by the base64-encoded USER:PASSWORD pair. The BaseX internal org.basex.util.Base64 can be used for encoding strings to the Base64 format:

// The java URL connection to the resource. 
URL url = new URL("http://localhost:8984/rest/factbook"); 
 
// Establish the connection to the URL. 
HttpURLConnection conn = (HttpURLConnection) url.openConnection(); 
// Set as GET request. 
conn.setRequestMethod("GET"); 
// User and password.
String user = "bob";
String pw ="alice";
// Encode user name and password pair with a base64 implementation.
String encoded = Base64.encode(user + ":" + pw);
// Basic access authentication header to connection request.
conn.setRequestProperty("Authorization", "Basic "+encoded);
// Print the HTTP response code. 
System.out.println("\n* HTTP response: " + conn.getResponseCode()); 
// Close connection. 
conn.disconnect();