HTTP Client API for ActiveX Version 8.2.2
 —  HTTP Client API for ActiveX  —

Programming the XML API

The following sections describe how to use the various operations that the API provides. All code snippets are written in Visual Basic. To be able to use the predefined constants and receive tool tips, a reference to the ActiveX control must be added to the Visual Basic project. See sampleVBXML for a sample demonstrating the use of the XML ActiveX control.

Methods that take a relative URL will combine the supplied relative URL with the Tamino XML Server base URL to produce an absolute URL that is used to process the programmer's request.

Note that the code snippets that follow make use of the scratch collection ino:etc. It should not be used for real applications.


Initialization

Before using the API, the ActiveX control must be created and initialized. This is done by using the Initialize method and setting the Tamino XML Server base URL.

Example:

...
Dim TamX As TaminoX
...
Set TamX = CreateObject("TaminoX.TaminoX1")
If TamX.Initialize = 0 Then
    Call MsgBox("TaminoX initialize failed!", vbExclamation)
    ' exit app
End If

TamX.csDatabaseURL = "http://localhost/tamino/mydb/ino:etc"
...

The only method that may be used before Initialize is UseServerHTTP. This is used if a different IXMLHTTPRequest MSXML COM interface is needed to perform HTTP requests to the Tamino XML Server. This may be the case if the ActiveX control is being used from within a server environment.

Example:

...
Set TamX = CreateObject("TaminoX.TaminoX1")
Call TamX.UseServerHTTP (XMLHttpMSXML2Server)
If TamX.Initialize = 0 Then
    Call MsgBox("TaminoX initialize failed!", vbExclamation)
    ' exit app
End If
...

Top of page

Error Checking

The programmer should use GetErrorStatus after methods that are expected to return a result to check for errors. The method returns an error number and the corresponding error text. If the error number is zero then no error occurred. If the error number is non-zero then the corresponding error text should provide more information as to the underlying reason for the error.

Example:

...
errNum = TamX.GetErrorStatus(errTxt)
If errNum <> 0 Then
    Call MsgBox(errTxt, vbCritical)
End If
...

"sampleVBXML" includes code such as the above example in the outputError function.

If an invalid database URL is used in the initialization one would receive an error message of the following form:

invalid DB URL error

Another method that may prove useful in determining the underlying reason for an error is GetAllResponseHeaders. This method returns the concatenation of all the received HTTP headers.

Top of page

Insert/Retrieve/Delete

The most direct methods to insert, retrieve and delete documents are PutDocument, GetDocument and DeleteDocument. PutDocument and DeleteDocument do not normally return a response document. GetDocument returns the actual requested document as the response document. This means that the programmer must invariably use GetErrorStatus to check for errors.

Example:

...
' xmldoc: <?xml version="1.0"?><Doc><Tag>some text</Tag></Doc>
doctype = "Doc"     ' document type [root element tag]
docname = "Bob"     ' document name [programmer specified]

relURL  = doctype & "/" & docname
    
Call TamX.PutDocument(relURL, xmldoc.DocumentElement)
If TamX.GetErrorStatus(errTxt) <> 0 Then
    Call MsgBox("PutDocument: " & errTxt)
Else
    Set res = TamX.GetDocument(relURL)
    If TamX.GetErrorStatus(errTxt) <> 0 Then
        Call MsgBox("GetDocument: " & errTxt)
    Else
        Call TamX.DeleteDocument(relURL)
        If TamX.GetErrorStatus(errTxt) <> 0 Then
            Call MsgBox("DeleteDocument: " & errTxt)
        Else
            Call MsgBox("Put/Get/Delete all worked!")
        End If
    End If
End If
...

Top of page

XQL Queries

To perform a legacy XQL query, use the DoQuery method. Use GetResult to obtain just the result element of the response. Use ReturnNodes to obtain the result element's node list.

Example:

...
TamX.lPagesize = 2
Set doc = TamX.DoQuery("Doc/Tag")
If TamX.GetErrorStatus(errtxt) = 0 Then
    Set nodelist = TamX.ReturnNodes(doc)
    MsgBox("NUM NODES: " & nodelist.Length)
    For Each node In nodelist
        MsgBox("NODE: " + node.xml)
    Next
End If
...

Note that the methods IsNext/GetNext and IsPrevious/GetPrev can be used to step through multi-page result sets – see Cursoring for an explanation/example.

Top of page

XQuery Queries

To perform an XQuery query, use the XQuery method. Use XQueryResult to obtain just the result element of the response. Use ChildNodes on the XQueryResult response to obtain the result element's node list.

Example:

...
Set doc = TamX.XQuery("input()/Doc/Tag")
If TamX.GetErrorStatus(errtxt) = 0 Then
    Set nodelist = TamX.XQueryResult(doc).ChildNodes
    MsgBox("NUM NODES: " & nodelist.Length)
    For Each node In nodelist
        MsgBox("NODE: " + node.xml)
    Next
End If
...

Note that if a transactional session is not in progress the pagesize property is ignored and all matching items are returned in a single response document. If a transactional session is in progress, a scrollable cursor may be used along with the pagesize property to split the response documents up into a number of manageable chunks. The methods IsNext/GetNext and IsPrevious/GetPrev can be used to step through multi-page result sets – see Cursoring for an explanation/example.

Top of page

Cursoring

Cursoring permits large query result sets to be split into smaller manageable chunks. Instead of all matching results being sent as a single response document, the results can sent as a number of response documents (pages). Note that cursoring may only be used within a transactional session. The programmer specifies that cursoring is required by using the UseRealCursoring method. The cursor is closed either at the end of the transactional session or by using the CloseCursor method.

...
' use a scrollable cursor 
Call TamX.UseRealCursoring(RealCursorScrollable)
' start a transactional session to use cursoring
Call TamX.StartSession(InoIsolationDefault, InoLockWaitDefault)
' set pagesize for cursor
TamX.lPagesize = 2
' perform XQuery and process results
Set doc = TamX.XQuery("input()/Doc/Tag")
Set nodelist = TamX.XQueryResult(doc).ChildNodes
For Each node in nodelist
    ...
Next
' process subsequent pages
While TamX.IsNext(doc) <> 0
    Set doc = TamX.GetNext(doc)
    Set nodelist = TamX.XQueryResult(doc).ChildNodes
    For Each node In nodelist
        ...
    Next
Wend
' close the cursor
Call TamX.CloseCursor(doc)
' end the transactional session
Call TamX.EndSession
...

Top of page

Local Transactions

The API supports the grouping of commands on the Tamino XML Server within transactions. To be able to use grouping transactions the programmer must start a transactional session. Groups of commands may be performed and either committed or rolled back as a group. The programmer must indicate when the transactional session is finished with in order to prevent resource leakage.

Example:

...
' start a transactional session
Call TamX.StartSession(InoIsolationDefault, InoLockWaitDefault)
' perform some methods
...
' commit all methods
Call TamX.Commit
' perform some methods
...
' roll back ALL methods since last commit
Call TamX.Rollback
' now end the transactional session
Call TamX.EndSession
...

Note that in the "sampleVBXML" error checking is done after each of the above calls. The sample also shows the form of the response documents received by these calls.

Top of page

Lock Management

To ensure consistency, Tamino XML Server provides a sophisticated locking concept. For detailed information regarding the Tamino locking concept, please refer to the Tamino XML Server documentation. Individual commands outside of a transactional session may have a lock specified or all commands within a transactional session may have a lock specified.

The types IsolationTypes, LockWaitTypes and LockModeTypes specify the possible values.

Individual commands outside of a transactional session may have a lock specified by using the following methods:

SetIsolationLevel
SetLockWait
SetLockMode

Example:

...
Call TamX.SetIsolationLevel(requiredIsolation)
Call TamX.SetLockWait(requiredLockwait)
Call TamX.SetLockMode(requiredLockMode)
...
' perform commands using the specified lock values
...

All commands within a transactional session may have a lock specified by specifying the lock values in the StartSession or BeginSession methods.

Example:

...
Call TamX.BeginSession(requiredIsolation, requiredLockwait, requiredLockMode)
...
' do commands using the specified lock values
...
Call TamX.EndSession
...

Top of page

Transaction Timeouts

It is possible to vary the timeouts that the Tamino XML Server will apply to transactions on a connection basis. You can change the timeout values by using the methods SetTransactionTimeout and SetNonActivityTimeout.

SetTransactionTimeout

The timeout specifies the maximum amount of time between commit/rollback calls.

SetNonActivityTimeout

The timeout specifies the maximum amount of time between database operations.

Both timeouts are in seconds. If not specified, the timeouts that the Tamino XML Server will use will be the database specific values. These may be viewed/altered by using the Tamino Manager.

Example:

...
' set suitable timeouts
Call TamX.SetTransactionTimeout(60)
Call TamX.SetNonActivityTimeout(30)
...
' perform transactions using the specified timeout values
...

Top of page

Distributed Transactions

Distributed transactions can be used to group commands associated with different databases. All the commands run within the scope of a distributed transaction.

To participate in a distributed transaction, the Tamino XML Server needs to know the transaction ID. The transaction ID of the currently active distributed transaction can either be determined automatically by the API or it can be explicitly specified by the application. In either case, the transaction ID is communicated to the Tamino XML Server. Also, neither form of transaction may use the API Commit or Rollback methods.

If the transaction ID is to be determined automatically, then the application must be running in the context of a distributed transaction that implements the Microsoft COM+ interface ITipTransaction. This would be satisfied by an application running within the MS/DTC (Microsoft's Distributed Transaction Monitor, which can coordinate commits/rollbacks in different databases) transactional environment with the application specifying that it "Requires Transaction" using the MS/DTC console. Note that the StartSession/BeginSession method must execute within the context of the distributed transaction. The EndSession method may not be used within an automatically determined distributed transaction.

The following sample shows the code needed to use an automatically determined transaction:

Example:

...
' MS/DTC automatically starts distributed transaction for application

' use distributed transactions
Call TamX.UseGlobalTransactions (True)

' automatically pass transaction id to Tamino
Call TamX.BeginSession(InoIsolationDefault,InoLockWaitDefault,LockModeDefault)
If TamX.GetErrorStatus(errtxt) <> 0 Then
    MsgBox("ERROR: " & errtxt)
End If
...
' do work in context of distributed transaction
...
' do not use EndSession

It is possible that the distributed transaction is explicitly under the control of the application. If the application wishes to perform Tamino operations within the context of this distributed transaction, then it must supply the transaction ID to Tamino via the BeginSessionWithGlobalTransaction method. The EndSession method may be used if the distributed transaction has been terminated.

Example:

...
' user starts distributed transaction in some manner

' obtain transaction id as TIP URL
tipUrl = ...

' pass transaction id to Tamino
Call TamX.BeginSessionWithGlobalTransaction(InoIsolationDefault, InoLockWaitDefault, LockModeDefault, tipUrl, TipTransaction)
If TamX.GetErrorStatus(errtxt) <> 0 Then
    MsgBox("ERROR: " & errtxt)
End If
...
' do work in context of distributed transaction
...
' user terminates distributed transaction in some manner

' safe to complete transaction
Call TamX.EndSession
...

Top of page

Legacy NodeLevelUpdate

Please note that this filter is a legacy filter provided for backwards compatibility. The preferred and more powerful way of performing these operations is to use the XQuery Update functionality directly in the Tamino XML Server itself.

For Microsoft's Internet Information Server (IIS) and also for Personal Web Server (PWS) there is a filter available, which you need in case you want to use some special methods of the Tamino DOM APIs.

This filter provides the implementation of the following API methods.

InoAppendChild Appends an additional node below a document's node
InoInsertBefore Inserts an additional node before a document's node
InoReplaceChild Replaces one node by another
InoRemoveChild Deletes a node in a document

Without this special filter you cannot use the above methods. The filter has to be installed in the Internet Information Server. The method calls are intercepted and the filter uses corresponding methods of Microsoft's DOM interface. The filter takes the DOM result objects to communicate then directly to/from the Tamino XML Server (i.e. these methods are not performed directly in the server but within the filter environment on the complete documents).

Top of page

Schema Manipulation

The following methods may be used to manipulate schema within the Tamino XML Server: Define and Undefine. Define is used to define a schema. Undefine is used to undefine a schema or a collection.

Warning:
Undefining a schema or a collection will cause ALL related data to be deleted!

Example:

...
schema.Load("Doc.xsd")
Set doc = TamX.Define(schema)
MsgBox("Define: " & doc.xml)
...
Set doc = TamX.Undefine("Doc")
MsgBox("Undefine: " & doc.xml)
...

Top of page

Diagnosis

The following methods may be used for diagnostic purposes: GetVersion, Ping and Echo.

Example:

...
MsgBox("Version: " & TamX.GetVersion)
...
Set doc = TamX.Ping
MsgBox("Ping: " & doc.xml)
...
Set doc = TamX.Echo
MsgBox("Echo: " & doc.xml)
...

Top of page