RestorableTsFileIOWriter extends TsFileIOWriter { public static RestorableTsFileIOWriter getWriterForAppendingDataOnCompletedTsFile(File file) throws IOException { long position = file.length(); try (TsFileSequenceReader reader = new TsFileSequenceReader(file.getAbsolutePath(), false)) { if (reader.isComplete()) { reader.loadMetadataSize(); position = reader.getFileMetadataPos(); } } if (position != file.length()) { try (FileChannel channel = FileChannel .open(Paths.get(file.getAbsolutePath()), StandardOpenOption.WRITE)) { channel.truncate(position - 1); } } return new RestorableTsFileIOWriter(file); } RestorableTsFileIOWriter(File file); static RestorableTsFileIOWriter getWriterForAppendingDataOnCompletedTsFile(File file); Map<Path, MeasurementSchema> getKnownSchema(); List<ChunkMetadata> getVisibleMetadataList(String deviceId, String measurementId,
      TSDataType dataType); Map<String, Map<String, List<ChunkMetadata>>> getMetadatasForQuery(); void makeMetadataVisible(); boolean hasCrashed(); void addSchema(Path path, MeasurementSchema schema);  }
@Test public void testAppendDataOnCompletedFile() throws Exception { File file = fsFactory.getFile(FILE_NAME); TsFileWriter writer = new TsFileWriter(file); writer.registerTimeseries(new Path("d1", "s1"), new MeasurementSchema("s1", TSDataType.FLOAT, TSEncoding.RLE)); writer.registerTimeseries(new Path("d1", "s2"), new MeasurementSchema("s2", TSDataType.FLOAT, TSEncoding.RLE)); writer.write(new TSRecord(1, "d1").addTuple(new FloatDataPoint("s1", 5)) .addTuple(new FloatDataPoint("s2", 4))); writer.write(new TSRecord(2, "d1").addTuple(new FloatDataPoint("s1", 5)) .addTuple(new FloatDataPoint("s2", 4))); writer.close(); long size = file.length(); RestorableTsFileIOWriter rWriter = RestorableTsFileIOWriter .getWriterForAppendingDataOnCompletedTsFile(file); TsFileWriter write = new TsFileWriter(rWriter); write.close(); assertEquals(size, file.length()); assertTrue(file.delete()); }