Learning
Community
Open Exchange
Global Masters
InterSystems IRIS Data Platform 2019.3 / Application Development / Using the Native API for Python / Introduction to the Native API
Previous section   Next section

Introduction to the Native API

The Native API for Python is a lightweight interface to the native multidimensional storage data structures that underlie the InterSystems IRIS™ object and SQL interfaces. The Native API allows you to implement your own data structures by providing direct access to global arrays, the tree-based sparse arrays that form the basis of the multidimensional storage model.
This chapter discusses the following topics:

Introduction to Global Arrays

A global array, like all sparse arrays, is a tree structure rather than a sequential list. The basic concept behind global arrays can be illustrated by analogy to a file structure. Each directory in the tree is uniquely identified by a path composed of a root directory identifier followed by a series of subdirectory identifiers, and any directory may or may not contain data.
Global arrays work the same way: each node in the tree is uniquely identified by a node address composed of a global name identifier and a series of subscript identifiers, and a node may or may not contain a value. For example, here is a global array consisting of six nodes, two of which contain values:
   root -->|--> foo --> SubFoo='A'
           |--> bar --> lowbar --> UnderBar=123
Values could be stored in the other possible node addresses (for example, root or root->bar), but no resources are wasted if those node addresses are valueless. In InterSystems ObjectScript globals notation, the two nodes with values would be:
   root('foo','SubFoo')
   root('bar','lowbar','UnderBar')
The global name (root) is followed by a comma-delimited subscript list in parentheses. Together, they specify the entire path to the node.
This global array could be created by two calls to the Native API set() method:
  irisObject.set('A', 'root', 'foo', 'SubFoo')
  irisObject.set(123, 'root', 'bar', 'lowbar', 'UnderBar')

Global array root is created when the first call assigns value 'A' to node root('foo','SubFoo'). Nodes can be created in any order, and with any set of subscripts. The same global array would be created if we reversed the order of these two calls. The valueless nodes are created automatically, and will be deleted automatically when no longer needed. For details, see “Creating, Updating, and Deleting Nodes” in the next chapter.
The Native API code to create this array is demonstrated in the following example. A connection object establishes a connection to the server. The connection will be used by an instance of class iris named iris. Native API methods are used to create a global array, read the resulting persistent values from the database, and then delete the global array.
The NativeDemo Program
# Import the Native API module
import irisnative

# Open a connection to the server
args = {'hostname':'127.0.0.1', 
        'port':51773, 
        'namespace':'USER', 
        'username':'_SYSTEM', 
        'password':'SYS'}
conn = irisnative.createConnection(**args)

# Create an iris object
iris = irisnative.createIris(conn)

# Create a global array in the USER namespace on the server
iris.set('A', 'root', 'foo', 'SubFoo')
iris.set(123, 'root', 'bar', 'lowbar', 'UnderBar')

# Read the values from the database and print them
subfoo = iris.get('root', 'foo', 'SubFoo')
underbar = iris.get('root', 'bar', 'lowbar', 'UnderBar')
print('Created two values: ')
print('   root("foo","SubFoo")=', subfoo)
print('   root("bar","lowbar","UnderBar")=', underbar)

# Delete the global array and terminate
iris.kill('root') # delete global array root
conn.close()
NativeDemo prints the following lines:
  Created two values:
     root('foo','SubFoo')=A
     root('bar','lowbar','UnderBar')=123
In this example, irisnative is the Native API module. Native API methods perform the following actions:
The next chapter provides detailed explanations and examples for all of these methods.

Glossary of Native API Terms

See the previous section for an overview of the concepts listed here. Examples in this glossary will refer to the global array structure listed below. The Legs global array has ten nodes and three node levels. Seven of the ten nodes contain values:
  Legs                       // root node, valueless, 3 child nodes
    fish = 0                 // level 1 node, value=0
    mammal                   // level 1 node, valueless
      human = 2              // level 2 node, value=2
      dog = 4                // level 2 node, value=4
    bug                      // level 1 node, valueless, 3 child nodes
      insect = 6             // level 2 node, value=6
      spider = 8             // level 2 node, value=8
      millipede = Diplopoda  // level 2 node, value="Diplopoda", 1 child node
        centipede = 100      // level 3 node, value=100

Child node
The nodes immediately under a given parent node. The address of a child node is specified by adding exactly one subscript to the end of the parent subscript list. For example, parent node Legs('mammal') has child nodes Legs('mammal','human') and Legs('mammal','dog').
Global name
The identifier for the root node is also the name of the entire global array. For example, root node identifier Legs is the global name of global array Legs.
Node
An element of a global array, uniquely identified by a namespace consisting of a global name and an arbitrary number of subscript identifiers. A node must either contain data, have child nodes, or both.
Node level
The number of subscripts in the node address. A ‘level 2 node’ is just another way of saying ‘a node with two subscripts’. For example, Legs('mammal','dog') is a level 2 node. It is two levels under root node Legs and one level under Legs('mammal').
Node address
The complete namespace of a node, including the global name and all subscripts. For example, node address Legs('fish') consists of root node identifier Legs plus a list containing one subscript, 'fish'. Depending on context, Legs (with no subscript list) can refer to either the root node address or the entire global array.
Root node
The unsubscripted node at the base of the global array tree. The identifier for a root node is its global name with no subscripts.
Subnode
All descendants of a given node are referred to as subnodes of that node. For example, node Legs('bug') has four different subnodes on two levels. All nine subscripted nodes are subnodes of root node Legs.
Subscript / Subscript list
All nodes under the root node are addressed by specifying the global name and a list of one or more subscript identifiers. (The global name plus the subscript list is the node address).
Target address
Many Native API methods require you to specify a valid node address that does not necessarily point to an existing node. For example, the set() method takes a value argument and a target address, and stores the value at that address. If no node exists at the target address, a new node is created.
Value
A node can contain a value of any supported type. A node with no child nodes must contain a value; a node that has child nodes can be valueless.
Valueless node
A node must either contain data, have child nodes, or both. A node that has child nodes but does not contain data is called a valueless node. Valueless nodes only exist as pointers to lower level nodes.

Global Naming Rules

Global names and subscripts obey the following rules:
  • The length of a node address (totaling the length of the global name and all subscripts) can be up to 511 characters. (Some typed characters may count as more than one encoded character for this limit. For more information, see “Maximum Length of a Global Reference” in Using Globals).
  • A global name can include letters, numbers, and periods ('.'), and can have a length of up to 31 significant characters. It must begin with a letter, and must not end with a period.
  • A subscript can be a Unicode string, Integer/Long, Float, or Byte string. String subscripts are case-sensitive, and can include characters of all types. Length is limited only by the 511 character maximum for the total node address.
Previous section   Next section