Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
apache
Iotdb
提交
f80c2894
I
Iotdb
项目概览
apache
/
Iotdb
8 个月 前同步成功
通知
25
Star
3344
Fork
916
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
I
Iotdb
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
前往新版Gitcode,体验更适合开发者的 AI 搜索 >>
未验证
提交
f80c2894
编写于
8月 29, 2023
作者:
S
shuwenwei
提交者:
GitHub
8月 29, 2023
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Fix point priority reader array index out of bound exception (#10919)
上级
f1a40124
变更
5
隐藏空白更改
内联
并排
Showing
5 changed file
with
257 addition
and
7 deletion
+257
-7
iotdb-core/datanode/src/main/java/org/apache/iotdb/db/storageengine/dataregion/compaction/execute/utils/executor/fast/SeriesCompactionExecutor.java
...execute/utils/executor/fast/SeriesCompactionExecutor.java
+7
-4
iotdb-core/datanode/src/main/java/org/apache/iotdb/db/storageengine/dataregion/compaction/execute/utils/executor/fast/element/PointElement.java
...ion/execute/utils/executor/fast/element/PointElement.java
+3
-0
iotdb-core/datanode/src/main/java/org/apache/iotdb/db/storageengine/dataregion/compaction/execute/utils/reader/PointPriorityReader.java
.../compaction/execute/utils/reader/PointPriorityReader.java
+12
-2
iotdb-core/datanode/src/test/java/org/apache/iotdb/db/storageengine/dataregion/compaction/FastCompactionPerformerWithEmptyPageTest.java
.../compaction/FastCompactionPerformerWithEmptyPageTest.java
+137
-0
iotdb-core/datanode/src/test/java/org/apache/iotdb/db/storageengine/dataregion/compaction/utils/CompactionTestFileWriter.java
...dataregion/compaction/utils/CompactionTestFileWriter.java
+98
-1
未找到文件。
iotdb-core/datanode/src/main/java/org/apache/iotdb/db/storageengine/dataregion/compaction/execute/utils/executor/fast/SeriesCompactionExecutor.java
浏览文件 @
f80c2894
...
...
@@ -244,8 +244,9 @@ public abstract class SeriesCompactionExecutor {
||
firstPageElement
.
needForceDecoding
)
{
// has overlap or modified pages, then deserialize it
summary
.
pageOverlapOrModified
+=
1
;
pointPriorityReader
.
addNewPage
(
firstPageElement
);
compactWithOverlapPages
();
if
(
pointPriorityReader
.
addNewPageIfPageNotEmpty
(
firstPageElement
))
{
compactWithOverlapPages
();
}
}
else
{
// has none overlap or modified pages, flush it to chunk writer directly
summary
.
pageNoneOverlap
+=
1
;
...
...
@@ -276,7 +277,9 @@ public abstract class SeriesCompactionExecutor {
}
else
{
// unsealed page is not large enough or page.endTime > file.endTime, then deserialze it
summary
.
pageNoneOverlapButDeserialize
+=
1
;
pointPriorityReader
.
addNewPage
(
pageElement
);
if
(!
pointPriorityReader
.
addNewPageIfPageNotEmpty
(
pageElement
))
{
return
;
}
// write data points of the current page into chunk writer
TimeValuePair
point
;
...
...
@@ -352,7 +355,7 @@ public abstract class SeriesCompactionExecutor {
||
nextPageElement
.
needForceDecoding
)
{
// next page is overlapped or modified, then deserialize it
summary
.
pageOverlapOrModified
++;
pointPriorityReader
.
addNewPage
(
nextPageElement
);
pointPriorityReader
.
addNewPage
IfPageNotEmpty
(
nextPageElement
);
}
else
{
// has none overlap or modified pages, flush it to chunk writer directly
summary
.
pageFakeOverlap
+=
1
;
...
...
iotdb-core/datanode/src/main/java/org/apache/iotdb/db/storageengine/dataregion/compaction/execute/utils/executor/fast/element/PointElement.java
浏览文件 @
f80c2894
...
...
@@ -41,6 +41,9 @@ public class PointElement {
}
else
{
this
.
pointReader
=
pageElement
.
batchData
.
getTsBlockAlignedRowIterator
();
}
if
(!
pointReader
.
hasNextTimeValuePair
())
{
return
;
}
this
.
timeValuePair
=
pointReader
.
nextTimeValuePair
();
this
.
timestamp
=
timeValuePair
.
getTimestamp
();
this
.
priority
=
pageElement
.
priority
;
...
...
iotdb-core/datanode/src/main/java/org/apache/iotdb/db/storageengine/dataregion/compaction/execute/utils/reader/PointPriorityReader.java
浏览文件 @
f80c2894
...
...
@@ -170,8 +170,10 @@ public class PointPriorityReader {
* Add a new overlapped page.
*
* @throws IOException if io errors occurred
* @return whether page is added into the queue
*/
public
void
addNewPage
(
PageElement
pageElement
)
throws
IOException
{
public
boolean
addNewPageIfPageNotEmpty
(
PageElement
pageElement
)
throws
IOException
,
IllegalPathException
,
WriteProcessException
{
if
(
currentPointElement
!=
null
)
{
nextPointInOtherPage
=
Math
.
min
(
nextPointInOtherPage
,
pageElement
.
startTime
);
if
(
currentPoint
.
getTimestamp
()
>=
nextPointInOtherPage
)
{
...
...
@@ -179,6 +181,14 @@ public class PointPriorityReader {
currentPointElement
=
null
;
}
}
pointQueue
.
add
(
new
PointElement
(
pageElement
));
PointElement
pointElement
=
new
PointElement
(
pageElement
);
boolean
pageIsNotEmpty
=
pointElement
.
timeValuePair
!=
null
;
if
(
pageIsNotEmpty
)
{
pointQueue
.
add
(
pointElement
);
}
else
{
removePage
.
call
(
pageElement
);
}
return
pageIsNotEmpty
;
}
}
iotdb-core/datanode/src/test/java/org/apache/iotdb/db/storageengine/dataregion/compaction/FastCompactionPerformerWithEmptyPageTest.java
0 → 100644
浏览文件 @
f80c2894
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package
org.apache.iotdb.db.storageengine.dataregion.compaction
;
import
org.apache.iotdb.commons.exception.IllegalPathException
;
import
org.apache.iotdb.commons.exception.MetadataException
;
import
org.apache.iotdb.commons.path.PartialPath
;
import
org.apache.iotdb.db.exception.StorageEngineException
;
import
org.apache.iotdb.db.storageengine.dataregion.compaction.execute.performer.impl.FastCompactionPerformer
;
import
org.apache.iotdb.db.storageengine.dataregion.compaction.execute.task.CrossSpaceCompactionTask
;
import
org.apache.iotdb.db.storageengine.dataregion.compaction.utils.CompactionTestFileWriter
;
import
org.apache.iotdb.db.storageengine.dataregion.tsfile.TsFileResource
;
import
org.apache.iotdb.tsfile.exception.write.WriteProcessException
;
import
org.apache.iotdb.tsfile.file.metadata.ChunkMetadata
;
import
org.apache.iotdb.tsfile.file.metadata.enums.CompressionType
;
import
org.apache.iotdb.tsfile.file.metadata.enums.TSEncoding
;
import
org.apache.iotdb.tsfile.read.TsFileSequenceReader
;
import
org.apache.iotdb.tsfile.read.common.TimeRange
;
import
org.junit.After
;
import
org.junit.Assert
;
import
org.junit.Before
;
import
org.junit.Test
;
import
java.io.IOException
;
import
java.util.Arrays
;
import
java.util.List
;
import
java.util.Map
;
import
java.util.concurrent.atomic.AtomicInteger
;
public
class
FastCompactionPerformerWithEmptyPageTest
extends
AbstractCompactionTest
{
@Before
public
void
setUp
()
throws
IOException
,
WriteProcessException
,
MetadataException
,
InterruptedException
{
super
.
setUp
();
}
@After
public
void
tearDown
()
throws
IOException
,
StorageEngineException
{
super
.
tearDown
();
}
@Test
public
void
test1
()
throws
IOException
,
IllegalPathException
{
String
device
=
"root.testsg.d1"
;
TsFileResource
seqFile1
=
createEmptyFileAndResource
(
true
);
try
(
CompactionTestFileWriter
writer
=
new
CompactionTestFileWriter
(
seqFile1
))
{
writer
.
startChunkGroup
(
"d1"
);
writer
.
generateSimpleAlignedSeriesToCurrentDeviceWithNullValue
(
Arrays
.
asList
(
"s1"
,
"s2"
,
"s3"
),
new
TimeRange
[][]
{
new
TimeRange
[]
{
new
TimeRange
(
10
,
30
)}},
TSEncoding
.
RLE
,
CompressionType
.
UNCOMPRESSED
,
Arrays
.
asList
(
false
,
true
,
true
));
writer
.
generateSimpleAlignedSeriesToCurrentDeviceWithNullValue
(
Arrays
.
asList
(
"s1"
,
"s2"
,
"s3"
),
new
TimeRange
[][]
{
new
TimeRange
[]
{
new
TimeRange
(
40
,
50
)}},
TSEncoding
.
RLE
,
CompressionType
.
UNCOMPRESSED
,
Arrays
.
asList
(
false
,
false
,
false
));
writer
.
endChunkGroup
();
writer
.
endFile
();
}
seqFile1
.
updateStartTime
(
device
,
10
);
seqFile1
.
updateEndTime
(
device
,
50
);
seqFile1
.
serialize
();
generateModsFile
(
Arrays
.
asList
(
new
PartialPath
(
"root.testsg.d1.s1"
)),
seqFile1
,
0
,
31
);
TsFileResource
unseqFile1
=
createEmptyFileAndResource
(
false
);
try
(
CompactionTestFileWriter
writer
=
new
CompactionTestFileWriter
(
unseqFile1
))
{
writer
.
startChunkGroup
(
"d1"
);
writer
.
generateSimpleAlignedSeriesToCurrentDevice
(
Arrays
.
asList
(
"s1"
,
"s2"
,
"s3"
),
new
TimeRange
[][]
{
new
TimeRange
[]
{
new
TimeRange
(
20
,
34
)}},
TSEncoding
.
RLE
,
CompressionType
.
UNCOMPRESSED
);
writer
.
endChunkGroup
();
writer
.
endFile
();
}
unseqFile1
.
updateStartTime
(
device
,
20
);
unseqFile1
.
updateEndTime
(
device
,
34
);
unseqFile1
.
serialize
();
CrossSpaceCompactionTask
task
=
new
CrossSpaceCompactionTask
(
0
,
tsFileManager
,
Arrays
.
asList
(
seqFile1
),
Arrays
.
asList
(
unseqFile1
),
new
FastCompactionPerformer
(
true
),
new
AtomicInteger
(
0
),
0
,
0
);
try
{
Assert
.
assertTrue
(
task
.
start
());
}
catch
(
Exception
e
)
{
Assert
.
fail
();
}
TsFileResource
result
=
tsFileManager
.
getTsFileList
(
true
).
get
(
0
);
result
.
buildDeviceTimeIndex
();
Assert
.
assertEquals
(
20
,
result
.
getStartTime
(
device
));
Assert
.
assertEquals
(
50
,
result
.
getEndTime
(
device
));
validateSeqFiles
(
true
);
try
(
TsFileSequenceReader
reader
=
new
TsFileSequenceReader
(
result
.
getTsFilePath
()))
{
Map
<
String
,
List
<
ChunkMetadata
>>
chunkMetadataInDevice
=
reader
.
readChunkMetadataInDevice
(
device
);
long
startTime
=
Long
.
MAX_VALUE
,
endTime
=
Long
.
MIN_VALUE
;
List
<
ChunkMetadata
>
chunkMetadataList
=
chunkMetadataInDevice
.
get
(
"s1"
);
for
(
ChunkMetadata
chunkMetadata
:
chunkMetadataList
)
{
startTime
=
Math
.
min
(
startTime
,
chunkMetadata
.
getStartTime
());
endTime
=
Math
.
max
(
endTime
,
chunkMetadata
.
getEndTime
());
}
Assert
.
assertEquals
(
20
,
startTime
);
Assert
.
assertEquals
(
50
,
endTime
);
}
}
}
iotdb-core/datanode/src/test/java/org/apache/iotdb/db/storageengine/dataregion/compaction/utils/CompactionTestFileWriter.java
浏览文件 @
f80c2894
...
...
@@ -31,12 +31,13 @@ import org.apache.iotdb.tsfile.write.schema.IMeasurementSchema;
import
org.apache.iotdb.tsfile.write.schema.MeasurementSchema
;
import
org.apache.iotdb.tsfile.write.writer.TsFileIOWriter
;
import
java.io.Closeable
;
import
java.io.IOException
;
import
java.util.ArrayList
;
import
java.util.List
;
import
java.util.Random
;
public
class
CompactionTestFileWriter
{
public
class
CompactionTestFileWriter
implements
Closeable
{
private
TsFileResource
resource
;
private
TsFileIOWriter
fileWriter
;
...
...
@@ -170,6 +171,34 @@ public class CompactionTestFileWriter {
}
}
public
void
generateSimpleAlignedSeriesToCurrentDeviceWithNullValue
(
List
<
String
>
measurementNames
,
TimeRange
[]
toGenerateChunkTimeRanges
,
TSEncoding
encoding
,
CompressionType
compressionType
,
List
<
Boolean
>
nullMeasurements
)
throws
IOException
{
List
<
IMeasurementSchema
>
measurementSchemas
=
new
ArrayList
<>();
for
(
String
measurementName
:
measurementNames
)
{
measurementSchemas
.
add
(
new
MeasurementSchema
(
measurementName
,
TSDataType
.
INT32
,
encoding
,
compressionType
));
}
for
(
TimeRange
toGenerateChunk
:
toGenerateChunkTimeRanges
)
{
AlignedChunkWriterImpl
alignedChunkWriter
=
new
AlignedChunkWriterImpl
(
measurementSchemas
);
currentDeviceStartTime
=
Math
.
min
(
toGenerateChunk
.
getMin
(),
currentDeviceStartTime
);
currentDeviceEndTime
=
Math
.
max
(
toGenerateChunk
.
getMax
(),
currentDeviceEndTime
);
for
(
long
time
=
toGenerateChunk
.
getMin
();
time
<=
toGenerateChunk
.
getMax
();
time
++)
{
alignedChunkWriter
.
getTimeChunkWriter
().
write
(
time
);
for
(
int
i
=
0
;
i
<
measurementNames
.
size
();
i
++)
{
alignedChunkWriter
.
getValueChunkWriterByIndex
(
i
)
.
write
(
time
,
new
Random
().
nextInt
(),
nullMeasurements
.
get
(
i
));
}
}
alignedChunkWriter
.
writeToFileWriter
(
fileWriter
);
}
}
public
void
generateSimpleAlignedSeriesToCurrentDevice
(
List
<
String
>
measurementNames
,
TimeRange
[][]
toGenerateChunkPageTimeRanges
,
...
...
@@ -203,6 +232,40 @@ public class CompactionTestFileWriter {
}
}
public
void
generateSimpleAlignedSeriesToCurrentDeviceWithNullValue
(
List
<
String
>
measurementNames
,
TimeRange
[][]
toGenerateChunkPageTimeRanges
,
TSEncoding
encoding
,
CompressionType
compressionType
,
List
<
Boolean
>
nullMeasurement
)
throws
IOException
{
List
<
IMeasurementSchema
>
measurementSchemas
=
new
ArrayList
<>();
for
(
String
measurementName
:
measurementNames
)
{
measurementSchemas
.
add
(
new
MeasurementSchema
(
measurementName
,
TSDataType
.
INT32
,
encoding
,
compressionType
));
}
for
(
TimeRange
[]
toGenerateChunk
:
toGenerateChunkPageTimeRanges
)
{
AlignedChunkWriterImpl
alignedChunkWriter
=
new
AlignedChunkWriterImpl
(
measurementSchemas
);
for
(
TimeRange
toGeneratePageTimeRange
:
toGenerateChunk
)
{
currentDeviceStartTime
=
Math
.
min
(
toGeneratePageTimeRange
.
getMin
(),
currentDeviceStartTime
);
currentDeviceEndTime
=
Math
.
max
(
toGeneratePageTimeRange
.
getMax
(),
currentDeviceEndTime
);
for
(
long
time
=
toGeneratePageTimeRange
.
getMin
();
time
<=
toGeneratePageTimeRange
.
getMax
();
time
++)
{
alignedChunkWriter
.
write
(
time
);
for
(
int
i
=
0
;
i
<
measurementNames
.
size
();
i
++)
{
alignedChunkWriter
.
getValueChunkWriterByIndex
(
i
)
.
getPageWriter
()
.
write
(
time
,
new
Random
().
nextInt
(),
nullMeasurement
.
get
(
i
));
}
}
alignedChunkWriter
.
sealCurrentPage
();
}
alignedChunkWriter
.
writeToFileWriter
(
fileWriter
);
}
}
public
void
generateSimpleAlignedSeriesToCurrentDevice
(
List
<
String
>
measurementNames
,
TimeRange
[][][]
toGenerateChunkPageTimeRanges
,
...
...
@@ -235,4 +298,38 @@ public class CompactionTestFileWriter {
alignedChunkWriter
.
writeToFileWriter
(
fileWriter
);
}
}
public
void
generateSimpleAlignedSeriesToCurrentDeviceWithNullValue
(
List
<
String
>
measurementNames
,
TimeRange
[][][]
toGenerateChunkPageTimeRanges
,
TSEncoding
encoding
,
CompressionType
compressionType
,
List
<
Boolean
>
nullMeasurements
)
throws
IOException
{
List
<
IMeasurementSchema
>
measurementSchemas
=
new
ArrayList
<>();
for
(
String
measurementName
:
measurementNames
)
{
measurementSchemas
.
add
(
new
MeasurementSchema
(
measurementName
,
TSDataType
.
INT32
,
encoding
,
compressionType
));
}
for
(
TimeRange
[][]
toGenerateChunk
:
toGenerateChunkPageTimeRanges
)
{
AlignedChunkWriterImpl
alignedChunkWriter
=
new
AlignedChunkWriterImpl
(
measurementSchemas
);
for
(
TimeRange
[]
toGeneratePageTimeRanges
:
toGenerateChunk
)
{
for
(
TimeRange
pointsTimeRange
:
toGeneratePageTimeRanges
)
{
currentDeviceStartTime
=
Math
.
min
(
pointsTimeRange
.
getMin
(),
currentDeviceStartTime
);
currentDeviceEndTime
=
Math
.
max
(
pointsTimeRange
.
getMax
(),
currentDeviceEndTime
);
for
(
long
time
=
pointsTimeRange
.
getMin
();
time
<=
pointsTimeRange
.
getMax
();
time
++)
{
alignedChunkWriter
.
write
(
time
);
for
(
int
i
=
0
;
i
<
measurementNames
.
size
();
i
++)
{
alignedChunkWriter
.
getValueChunkWriterByIndex
(
i
)
.
getPageWriter
()
.
write
(
time
,
new
Random
().
nextInt
(),
nullMeasurements
.
get
(
i
));
}
}
}
alignedChunkWriter
.
sealCurrentPage
();
}
alignedChunkWriter
.
writeToFileWriter
(
fileWriter
);
}
}
}
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录