Top Description Fields Methods
com.amazon.ion

public Interface IonValue

extends Cloneable
Known Direct Subinterfaces
com.amazon.ion.impl._Private_IonValue, com.amazon.ion.IonBool, com.amazon.ion.IonClob, com.amazon.ion.IonContainer, com.amazon.ion.IonList, com.amazon.ion.IonLob, com.amazon.ion.IonNull, com.amazon.ion.IonNumber, com.amazon.ion.IonSexp, com.amazon.ion.IonText, com.amazon.ion.IonTimestamp
Imports
com.amazon.ion.system.IonTextWriterBuilder, java.util.Collections, java.util.concurrent.CountDownLatch

Base type for all Ion data nodes.

Warning

This interface should not be implemented or extended by code outside of this library.

The IonValue hierarchy presents a "tree view" of Ion data; every node in the tree is an instance of this class. Since the Ion type system is highly orthogonal, most operations use this base type, and applications will need to examine individual instances and "downcast" the value to one of the "real" types (e.g., IonString) in order to access the Ion content.

Besides the real types, there are other generic interfaces that can be useful:

To determine the real type of a generic IonValue, there are three main mechanisms:

Use the most appropriate mechanism for your algorithm, depending upon how much validation you've done on the data.

Single-Parent Restriction

IonValue trees are strictly hierarchical: every node has at most one parent, as exposed through getContainer() (and, implicitly, getFieldName()). You cannot add an IonValue instance into two IonContainers; any attempt to do so will result in a ContainedValueException. You can of course add the same instance to multiple "normal" Collections, since that's stepping outside of the DOM.

The implication of this design is that you need to be careful when performing DOM transformations. You must remove a node from its parent before adding it to another one; removeFromContainer() is handy. Alternatively you can clone() a value, but be aware that cloning is a deep-copy operation (for the very same single-parent reason).

Thread Safety

Mutable IonValues are not safe for use by multiple threads! Your application must perform its own synchronization if you need to access IonValues from multiple threads. This is true even for read-only use cases, since implementations may perform lazy materialization or other state changes internally.

Alternatively, you can invoke makeReadOnly() from a single thread, after which point the value (and all recursively contained values) will be immutable and hence thread-safe.

It is important to note that makeReadOnly() is not guaranteed to implicitly provide a synchronization point between threads. This means it is the responsibility of the application to make sure operations on a thread other than the one that invoked makeReadOnly() causally happen after that invocation observing the rules of the Java Memory Model (JSR-133).

Here is an example of ensuring the correct ordering for multiple threads accessing an IonValue using a CountDownLatch to explicitly create a the temporal relationship:

      // ...
      // Shared Between Threads
      // ...

      IonValue value = ...;
      CountDownLatch latch = new CountDownLatch(1);

      // ...
      // Thread 1
      // ...

      value.makeReadOnly();
      latch.countDown();

      // ...
      // Thread 2
      // ...

      // before this point operations on 'value' are not defined
      latch.await();
      // we can now operate (in a read-only way) on 'value'
      value.isNullValue();
 

In the above, two threads have a reference to value. latch in this example provides a way to synchronize when makeReadOnly() happens in the first thread relative to isNullValue() being invoked on the second thread.

Alternatives

The Ion maintainers recommend using IonElement instead of IonValue whenever possible.

IonElement is a better choice than IonValue as long as you can work within its limitations. IonElement has significantly less memory overhead than IonValue. It is immutable and does not have a single-parent restriction, so it is always threadsafe, and unlike IonValue there is no need to make deep copies of IonElement. The limitations of IonElement are that it does not support symbols with unknown text, it will bring a dependency on the Kotlin Stdlib, and you may need to change some logic in your application if your logic relies on being able to access the parent container of an Ion value.

For more information, see "Why is IonElement needed?"

Field Summary

Modifier and TypeField and Description
public static final IonValue[]
EMPTY_ARRAY

A zero-length immutable IonValue array.

Method Summary

Modifier and TypeMethod and Description
public void
accept(ValueVisitor
will have one of its visit methods called.
visitor
)

Entry point for visitor pattern.

public void
addTypeAnnotation(String
as a string value.
annotation
)

Adds a user type annotation to the annotations attached to this value.

public void
clearTypeAnnotations()

Removes all the user type annotations attached to this value.

public IonValue
clone()

Creates a copy of this value and all of its children.

public boolean

Returns:

A boolean, true if the argument is an IonValue that is semantically identical within the Ion data model, including precision and annotations.
equals
(Object
The value to compare with.
other
)

Compares two Ion values for structural equality, which means that they represent the exact same semantics, including annotations, numeric precision, and so on.

public IonContainer
getContainer()

Gets the container of this value, or null if this is not part of one.

public int

Returns:

the symbol ID of the field name, if this is part of an IonStruct. If this is not a field, or if the symbol ID cannot be determined, this method returns a value less than one.
getFieldId
()
Deprecated Use getFieldNameSymbol() instead.

Gets the symbol ID of the field name attached to this value.

public String
getFieldName()

Gets the field name attached to this value, or null if this is not part of an IonStruct.

public SymbolToken

Returns:

null if this value isn't a struct field.
getFieldNameSymbol
()

Gets the field name attached to this value as an interned symbol (text + ID).

public SymbolTable

Returns:

the symbol table, or null if this value is not currently backed by binary-encoded data.
getSymbolTable
()

Gets the symbol table used to encode this value.

public IonSystem

Returns:

not null.
getSystem
()

Gets the system that constructed this value.

public IonType

Returns:

a non-null enumeration value.
getType
()

Gets an enumeration value identifying the core Ion data type of this object.

public String[]

Returns:

the (ordered) annotations on the current value, or an empty array (not null) if there are none.
getTypeAnnotations
()

Gets this value's user type annotations as text.

public SymbolToken[]

Returns:

the (ordered) annotations on the current value, or an empty array (not null) if there are none.
getTypeAnnotationSymbols
()

Gets this value's user type annotations as interned symbols (text + ID).

public int
hashCode()

Returns a hash code consistent with equals(Object).

public boolean

Returns:

true if this value has the annotation.
hasTypeAnnotation
(String
as a string value.
annotation
)

Determines whether or not the value is annotated with a particular user type annotation.

public boolean

Returns:

true if this value is one of the Ion null values.
isNullValue
()

Determines whether this in an Ion null value, e.g., null or null.string.

public boolean

Returns:

true if this value is read-only and safe for multi-threaded reads.
isReadOnly
()

Determines whether this value is read-only.

public void
makeReadOnly()

Marks this instance and its children to be immutable.

public boolean

Returns:

true if this value was in a container before this method was called.
removeFromContainer
()

Removes this value from its container, if any.

public void
removeTypeAnnotation(String
as a string value. If null or empty, the method has no effect.
annotation
)

Removes a user type annotation from the list of annotations attached to this value.

public void
setTypeAnnotations(String...
the new annotations. If null or empty array, then all annotations are removed. Any duplicates are preserved.
annotations
)

Replaces all type annotations with the given text.

public void
setTypeAnnotationSymbols(SymbolToken...
the new annotations. If null or empty array, then all annotations are removed. Any duplicates are preserved.
annotations
)

Replaces all type annotations with the given symbol tokens.

public IonValue

Returns:

the top level value above this value, never null, and never an IonDatagram.
topLevelValue
()

Finds the top level value above this value.

public String

Returns:

Ion text data equivalent to this value.
toPrettyString
()

Returns a pretty-printed Ion text representation of this value, using the settings of IonTextWriterBuilder#pretty().

public String

Returns:

Ion text data equivalent to this value.
toString
()

Returns a non-canonical Ion-formatted ASCII representation of this value.

public String

Returns:

Ion text data equivalent to this value.
toString
(IonTextWriterBuilder
the configuration that will be used for writing data to a string.
writerBuilder
)

Returns an Ion text representation of this value, using the settings from the given builder.

public void
writeTo(IonWriter writer)

Copies this value to the given IonWriter.

Field Detail

EMPTY_ARRAYback to summary
public static final IonValue[] EMPTY_ARRAY

A zero-length immutable IonValue array.

Method Detail

acceptback to summary
public void accept(ValueVisitor visitor) throws Exception

Entry point for visitor pattern. Implementations of this method by concrete classes will simply call the appropriate visit method on the visitor. For example, instances of IonBool will invoke ValueVisitor#visit(IonBool).

Parameters
visitor:ValueVisitor

will have one of its visit methods called.

Exceptions
Exception:
any exception thrown by the visitor is propagated.
NullPointerException:
if visitor is null.
addTypeAnnotationback to summary
public void addTypeAnnotation(String annotation)

Adds a user type annotation to the annotations attached to this value. If the annotation exists the list does not change.

Parameters
annotation:String

as a string value.

clearTypeAnnotationsback to summary
public void clearTypeAnnotations()

Removes all the user type annotations attached to this value.

cloneback to summary
public IonValue clone() throws UnknownSymbolException

Creates a copy of this value and all of its children. The cloned value may use the same shared symbol tables, but it will have an independent local symbol table if necessary. The cloned value will be modifiable regardless of whether this instance isReadOnly().

The cloned value will be created in the context of the same ValueFactory as this instance; if you want a copy using a different factory, then use ValueFactory#clone(IonValue) instead.

Exceptions
UnknownSymbolException:
if any part of this value has unknown text but known Sid for its field name, annotation or symbol.
equalsback to summary
public boolean equals(Object other)

Compares two Ion values for structural equality, which means that they represent the exact same semantics, including annotations, numeric precision, and so on. This is a "deep" comparison that recursively traverses the hierarchy, and as such it should be considered an expensive operation.

Parameters
other:Object

The value to compare with.

Returns:boolean

A boolean, true if the argument is an IonValue that is semantically identical within the Ion data model, including precision and annotations.

See Also
com.amazon.ion.util.Equivalence
getContainerback to summary
public IonContainer getContainer()

Gets the container of this value, or null if this is not part of one.

getFieldIdback to summary
public int getFieldId()

Deprecated

Use getFieldNameSymbol() instead.

Gets the symbol ID of the field name attached to this value.

Returns:int

the symbol ID of the field name, if this is part of an IonStruct. If this is not a field, or if the symbol ID cannot be determined, this method returns a value less than one.

Annotations
@Deprecated
getFieldNameback to summary
public String getFieldName()

Gets the field name attached to this value, or null if this is not part of an IonStruct.

Exceptions
UnknownSymbolException:
if the field name has unknown text.
getFieldNameSymbolback to summary
public SymbolToken getFieldNameSymbol()

Gets the field name attached to this value as an interned symbol (text + ID).

Returns:SymbolToken

null if this value isn't a struct field.

getSymbolTableback to summary
public SymbolTable getSymbolTable()

Gets the symbol table used to encode this value. The result is either a local or system symbol table (or null).

Returns:SymbolTable

the symbol table, or null if this value is not currently backed by binary-encoded data.

getSystemback to summary
public IonSystem getSystem()

Gets the system that constructed this value.

Returns:IonSystem

not null.

getTypeback to summary
public IonType getType()

Gets an enumeration value identifying the core Ion data type of this object.

Returns:IonType

a non-null enumeration value.

getTypeAnnotationsback to summary
public String[] getTypeAnnotations()

Gets this value's user type annotations as text.

Returns:String[]

the (ordered) annotations on the current value, or an empty array (not null) if there are none.

Exceptions
UnknownSymbolException:
if any annotation has unknown text.
getTypeAnnotationSymbolsback to summary
public SymbolToken[] getTypeAnnotationSymbols()

Gets this value's user type annotations as interned symbols (text + ID).

Returns:SymbolToken[]

the (ordered) annotations on the current value, or an empty array (not null) if there are none.

hashCodeback to summary
public int hashCode()

Returns a hash code consistent with equals(Object).

hasTypeAnnotationback to summary
public boolean hasTypeAnnotation(String annotation)

Determines whether or not the value is annotated with a particular user type annotation.

Parameters
annotation:String

as a string value.

Returns:boolean

true if this value has the annotation.

isNullValueback to summary
public boolean isNullValue()

Determines whether this in an Ion null value, e.g., null or null.string. Note that there are unique null values for each Ion type.

Returns:boolean

true if this value is one of the Ion null values.

isReadOnlyback to summary
public boolean isReadOnly()

Determines whether this value is read-only. Such values are safe for simultaneous read from multiple threads.

Returns:boolean

true if this value is read-only and safe for multi-threaded reads.

See Also
makeReadOnly()
makeReadOnlyback to summary
public void makeReadOnly()

Marks this instance and its children to be immutable. In addition, read-only values are safe for simultaneous use from multiple threads. This may require materializing the Java forms of the values.

After this method completes, any attempt to change the state of this instance, or of any contained value, will trigger a ReadOnlyValueException.

See Also
isReadOnly()
removeFromContainerback to summary
public boolean removeFromContainer()

Removes this value from its container, if any.

Returns:boolean

true if this value was in a container before this method was called.

removeTypeAnnotationback to summary
public void removeTypeAnnotation(String annotation)

Removes a user type annotation from the list of annotations attached to this value. If the annotation appears more than once, only the first occurrance is removed. If the annotation does not exist, the value does not change.

Parameters
annotation:String

as a string value. If null or empty, the method has no effect.

setTypeAnnotationsback to summary
public void setTypeAnnotations(String... annotations)

Replaces all type annotations with the given text.

Parameters
annotations:String[]

the new annotations. If null or empty array, then all annotations are removed. Any duplicates are preserved.

Exceptions
NullPointerException:
if any of the annotations are null
setTypeAnnotationSymbolsback to summary
public void setTypeAnnotationSymbols(SymbolToken... annotations)

Replaces all type annotations with the given symbol tokens. The contents of the annotations array are copied into this writer, so the caller does not need to preserve the array.

This is an "expert method": correct use requires deep understanding of the Ion binary format. You almost certainly don't want to use it.

Parameters
annotations:SymbolToken[]

the new annotations. If null or empty array, then all annotations are removed. Any duplicates are preserved.

topLevelValueback to summary
public IonValue topLevelValue()

Finds the top level value above this value. If this value has no container, or if it's immediate container is a datagram, then this value is returned.

Returns:IonValue

the top level value above this value, never null, and never an IonDatagram.

Exceptions
UnsupportedOperationException:
if this is an IonDatagram.
toPrettyStringback to summary
public String toPrettyString()

Returns a pretty-printed Ion text representation of this value, using the settings of IonTextWriterBuilder#pretty().

The specific configuration may change between releases of this library, so automated processes should not depend on the exact output formatting. In particular, there's currently no promise regarding handling of system data.

Returns:String

Ion text data equivalent to this value.

toStringback to summary
public String toString()

Returns a non-canonical Ion-formatted ASCII representation of this value. All data will be on a single line, with (relatively) minimal whitespace. There is no guarantee that multiple invocations of this method will return identical results, only that they will be equivalent per the Ion data model. For this reason it is erroneous for code to compare two strings returned by this method.

For more configurable rendering, see com.amazon.ion.system.IonTextWriterBuilder.

This is not the correct way to retrieve the content of an IonString or IonSymbol! Use IonText#stringValue() for that purpose.

   ionSystem.newString("Levi's").toString()     =>  "\"Levi's\""
   ionSystem.newString("Levi's").stringValue()  =>  "Levi's"
   ionSystem.newSymbol("Levi's").toString()     =>  "'Levi\\'s'"
   ionSystem.newSymbol("Levi's").stringValue()  =>  "Levi's"
Returns:String

Ion text data equivalent to this value.

See Also
IonText#stringValue(), toString(IonTextWriterBuilder), toPrettyString()
toStringback to summary
public String toString(IonTextWriterBuilder writerBuilder)

Returns an Ion text representation of this value, using the settings from the given builder.

Parameters
writerBuilder:IonTextWriterBuilder

the configuration that will be used for writing data to a string.

Returns:String

Ion text data equivalent to this value.

writeToback to summary
public void writeTo(IonWriter writer)

Copies this value to the given IonWriter.

This method writes annotations and field names (if in a struct), and performs a deep write, including the contents of any containers encountered.