diff --git a/go/cli/mcap/cmd/filter_test.go b/go/cli/mcap/cmd/filter_test.go index 0b902c141e..314eb50869 100644 --- a/go/cli/mcap/cmd/filter_test.go +++ b/go/cli/mcap/cmd/filter_test.go @@ -304,9 +304,9 @@ func TestRecover(t *testing.T) { assert.Equal(t, 0, attachmentCounter) assert.Equal(t, 0, metadataCounter) assert.InDeltaMapValues(t, map[uint16]int{ - 1: 87, - 2: 87, - 3: 87, + 1: 88, + 2: 88, + 3: 88, }, messageCounter, 0.0) }) diff --git a/go/mcap/mcap.go b/go/mcap/mcap.go index a8a04e88f1..04587198ad 100644 --- a/go/mcap/mcap.go +++ b/go/mcap/mcap.go @@ -166,6 +166,10 @@ func (idx *MessageIndex) Reset() { idx.currentIndex = 0 } +func (idx *MessageIndex) IsEmpty() bool { + return idx.currentIndex == 0 +} + // Entries lists the entries in the message index. func (idx *MessageIndex) Entries() []MessageIndexEntry { return idx.Records[:idx.currentIndex] diff --git a/go/mcap/version.go b/go/mcap/version.go index c731b8e9a4..e5eb06b4a7 100644 --- a/go/mcap/version.go +++ b/go/mcap/version.go @@ -1,4 +1,4 @@ package mcap // Version of the MCAP library. -var Version = "v1.0.0" +var Version = "v1.0.1" diff --git a/go/mcap/writer.go b/go/mcap/writer.go index a8b9f372f9..4a9f0ffa0e 100644 --- a/go/mcap/writer.go +++ b/go/mcap/writer.go @@ -463,7 +463,8 @@ func (w *Writer) flushActiveChunk() error { messageIndexOffsets := make(map[uint16]uint64) if !w.opts.SkipMessageIndexing { for _, chanID := range w.channelIDs { - if messageIndex, ok := w.messageIndexes[chanID]; ok { + messageIndex, ok := w.messageIndexes[chanID] + if ok && !messageIndex.IsEmpty() { messageIndexOffsets[messageIndex.ChannelID] = w.w.Size() err = w.WriteMessageIndex(messageIndex) if err != nil { diff --git a/go/mcap/writer_test.go b/go/mcap/writer_test.go index bfc33e54a9..e105b8ae46 100644 --- a/go/mcap/writer_test.go +++ b/go/mcap/writer_test.go @@ -150,6 +150,7 @@ func TestChunkedReadWrite(t *testing.T) { buf := &bytes.Buffer{} w, err := NewWriter(buf, &WriterOptions{ Chunked: true, + ChunkSize: 1, Compression: compression, IncludeCRC: true, OverrideLibrary: true, @@ -174,6 +175,12 @@ func TestChunkedReadWrite(t *testing.T) { "callerid": "100", // cspell:disable-line }, })) + assert.Nil(t, w.WriteChannel(&Channel{ + ID: 2, + Topic: "/test2", + MessageEncoding: "ros1", + SchemaID: 1, + })) assert.Nil(t, w.WriteMessage(&Message{ ChannelID: 1, Sequence: 0, @@ -186,13 +193,25 @@ func TestChunkedReadWrite(t *testing.T) { 4, }, })) + assert.Nil(t, w.WriteMessage(&Message{ + ChannelID: 2, + Sequence: 0, + LogTime: 100, + PublishTime: 100, + Data: []byte{ + 1, + 2, + 3, + 4, + }, + })) assert.Nil(t, w.Close()) - assert.Equal(t, 1, len(w.ChunkIndexes)) + assert.Equal(t, 2, len(w.ChunkIndexes)) assert.Equal(t, 0, len(w.AttachmentIndexes)) - assert.Equal(t, uint64(1), w.Statistics.MessageCount) + assert.Equal(t, uint64(2), w.Statistics.MessageCount) assert.Equal(t, uint32(0), w.Statistics.AttachmentCount) - assert.Equal(t, uint32(1), w.Statistics.ChannelCount) - assert.Equal(t, uint32(1), w.Statistics.ChunkCount) + assert.Equal(t, uint32(2), w.Statistics.ChannelCount) + assert.Equal(t, uint32(2), w.Statistics.ChunkCount) assert.Equal(t, int(w.Offset()), buf.Len()) lexer, err := NewLexer(buf) assert.Nil(t, err) @@ -201,13 +220,20 @@ func TestChunkedReadWrite(t *testing.T) { TokenHeader, TokenSchema, TokenChannel, + TokenChannel, + TokenMessage, + // Note: one message index per chunk, meaning that message indices for channels + // not present in the chunk are not written. + TokenMessageIndex, TokenMessage, TokenMessageIndex, TokenDataEnd, TokenSchema, TokenChannel, + TokenChannel, TokenStatistics, TokenChunkIndex, + TokenChunkIndex, TokenSummaryOffset, TokenSummaryOffset, TokenSummaryOffset,