net.quasardb.qdb.ts.Writer Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of jni Show documentation
Show all versions of jni Show documentation
API for the JNI components of the QuasarDB API for Java. Should not be included directly.
package net.quasardb.qdb.ts;
import java.io.IOException;
import java.io.Flushable;
import java.lang.AutoCloseable;
import java.sql.Timestamp;
import java.time.LocalDateTime;
import java.nio.channels.SeekableByteChannel;
import java.util.*;
import net.quasardb.qdb.*;
import net.quasardb.qdb.exception.ExceptionFactory;
import net.quasardb.qdb.exception.InvalidArgumentException;
import net.quasardb.qdb.jni.*;
/**
* High-performance bulk writer for a QuasarDB timeseries table.
*
* Usage of instances of this class is not thread-safe. Use a Writer
* instance per Thread in multi-threaded situations.
*/
public class Writer implements AutoCloseable, Flushable {
boolean async;
Session session;
Long batchTable;
List columns;
/**
* Maintains a cache of table offsets so we can easily look them up
* later.
*/
Map tableOffsets;
/**
* Helper class to represent a table and column pair, which we
* need because we need to lay out all columns as flat array.
*/
public static class TableColumn {
public String table;
public String column;
public TableColumn(String table, String column) {
this.table = table;
this.column = column;
}
public String toString() {
return "TableColumn (table: " + this.table + ", column: " + this.column + ")";
}
}
protected Writer(Session session, Table[] tables) {
this(session, tables, false);
}
protected Writer(Session session, Table[] tables, boolean async) {
this.async = async;
this.session = session;
this.tableOffsets = new HashMap();
this.columns = new ArrayList();
for (Table table : tables) {
this.tableOffsets.put(table.name, this.columns.size());
for (Column column : table.columns) {
this.columns.add(new TableColumn(table.name, column.name));
}
}
TableColumn[] tableColumns = this.columns.toArray(new TableColumn[columns.size()]);
Reference theBatchTable = new Reference();
int err = qdb.ts_batch_table_init(this.session.handle(),
tableColumns,
theBatchTable);
ExceptionFactory.throwIfError(err);
this.batchTable = theBatchTable.value;
}
/**
* After a writer is already initialized, this function allows extra tables to
* be added to the internal state. Blocking function that needs to communicate with
* the QuasarDB daemon to retrieve metadata.
*/
public void extraTables(Table[] tables) {
List columns = new ArrayList();
for (Table table : tables) {
this.tableOffsets.put(table.name, this.columns.size());
for (Column column : table.columns) {
this.columns.add(new TableColumn(table.name, column.name));
columns.add(new TableColumn(table.name, column.name));
}
}
TableColumn[] tableColumns = columns.toArray(new TableColumn[columns.size()]);
int err = qdb.ts_batch_table_extra_columns(this.batchTable,
tableColumns);
ExceptionFactory.throwIfError(err);
}
public void extraTables(Table table) {
extraTables(new Table[] { table });
}
/**
* Utility function that looks up a table's index with the batch being written
* by its name. The first table starts with column 0, but depending upon the amount
* of columns in other tables, it can influence the offset of the table within the batch.
*
* If possible, you are encouraged to cache this value so that recurring writes
* of rows to the same table only do this lookup once.
*/
public int tableIndexByName(String name) {
Integer offset = this.tableOffsets.get(name);
if (offset == null) {
throw new InvalidArgumentException();
}
return offset.intValue();
}
/**
* Cleans up the internal representation of the batch table.
*/
@Override
protected void finalize() throws Throwable {
try {
qdb.ts_batch_table_release(this.session.handle(), this.batchTable);
} finally {
super.finalize();
}
}
/**
* Closes the timeseries table and local cache so that memory can be reclaimed. Flushes
* all remaining output.
*/
public void close() throws IOException {
this.flush();
qdb.ts_batch_table_release(this.session.handle(), this.batchTable);
this.batchTable = null;
}
/**
* Flush current local cache to server.
*/
public void flush() throws IOException {
int err;
if (this.async == true) {
err = qdb.ts_batch_push_async(this.batchTable);
} else {
err = qdb.ts_batch_push(this.batchTable);
}
ExceptionFactory.throwIfError(err);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* @param offset Relative offset of the table inside the batch. Use #tableIndexByName
* to determine the appropriate value.
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(Integer offset, Timespec timestamp, Value[] values) throws IOException {
int err = qdb.ts_batch_table_row_append(this.batchTable, offset, timestamp, values);
ExceptionFactory.throwIfError(err);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This function automatically looks up a table's offset by its name. For performance
* reason, you are encouraged to manually invoke and cache the value of #tableIndexByName
* whenever possible.
*
* @param tableName Name of the table to insert to.
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(String tableName, Timespec timestamp, Value[] values) throws IOException {
this.append(this.tableIndexByName(tableName),
timestamp,
values);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This is a convenience function that assumes only one table is being inserted
* to and should not be used when inserts to multiple tables are being batched.
*
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(Timespec timestamp, Value[] values) throws IOException {
this.append(0, timestamp, values);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* @param offset Relative offset of the table inside the batch. Use #tableIndexByName
* to determine the appropriate value.
* @param row Row being inserted.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(Integer offset, Row row) throws IOException {
this.append(offset,
row.getTimestamp(),
row.getValues());
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This function automatically looks up a table's offset by its name. For performance
* reason, you are encouraged to manually invoke and cache the value of #tableIndexByName
* whenever possible.
*
* @param tableName Name of the table to insert to.
* @param row Row being inserted.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(String tableName, Row row) throws IOException {
this.append(this.tableIndexByName(tableName), row);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This is a convenience function that assumes only one table is being inserted
* to and should not be used when inserts to multiple tables are being batched.
*
* @param row Row being inserted.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(Row row) throws IOException {
this.append(0, row);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* @param offset Relative offset of the table inside the batch. Use #tableIndexByName
* to determine the appropriate value.
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(Integer offset, LocalDateTime timestamp, Value[] values) throws IOException {
this.append(offset, new Timespec(timestamp), values);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This function automatically looks up a table's offset by its name. For performance
* reason, you are encouraged to manually invoke and cache the value of #tableIndexByName
* whenever possible.
*
* @param tableName Name of the table to insert to.
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(String tableName, LocalDateTime timestamp, Value[] values) throws IOException {
this.append(this.tableIndexByName(tableName), timestamp, values);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This is a convenience function that assumes only one table is being inserted
* to and should not be used when inserts to multiple tables are being batched.
*
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(LocalDateTime timestamp, Value[] values) throws IOException {
this.append(0, timestamp, values);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* @param offset Relative offset of the table inside the batch. Use #tableIndexByName
* to determine the appropriate value.
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(Integer offset, Timestamp timestamp, Value[] values) throws IOException {
this.append(offset, new Timespec(timestamp), values);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This function automatically looks up a table's offset by its name. For performance
* reason, you are encouraged to manually invoke and cache the value of #tableIndexByName
* whenever possible.
*
* @param tableName Name of the table to insert to.
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(String tableName, Timestamp timestamp, Value[] values) throws IOException {
this.append(this.tableIndexByName(tableName), timestamp, values);
}
/**
* Append a new row to the local table cache. Should be periodically flushed,
* unless an {@link AutoFlushWriter} is used.
*
* This is a convenience function that assumes only one table is being inserted
* to and should not be used when inserts to multiple tables are being batched.
*
* @param timestamp Timestamp of the row
* @param values Values being inserted, mapped to columns by their relative offset.
*
* @see #tableIndexByName
* @see #flush
* @see Table#autoFlushWriter
*/
public void append(Timestamp timestamp, Value[] values) throws IOException {
this.append(0, timestamp, values);
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy