-
Notifications
You must be signed in to change notification settings - Fork 241
Fix batch pin index calculation logic and improve logging #499
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -51,7 +51,7 @@ func NewBatchManager(ctx context.Context, ni sysmessaging.LocalNodeInfo, di data | |
| startupOffsetRetryAttempts: config.GetInt(config.OrchestratorStartupAttempts), | ||
| dispatchers: make(map[fftypes.MessageType]*dispatcher), | ||
| shoulderTap: make(chan bool, 1), | ||
| newMessages: make(chan int64, readPageSize), | ||
| newMessages: make(chan int64), | ||
| sequencerClosed: make(chan struct{}), | ||
| retry: &retry.Retry{ | ||
| InitialDelay: config.GetDuration(config.BatchRetryInitDelay), | ||
|
|
@@ -219,18 +219,20 @@ func (bm *batchManager) assembleMessageData(msg *fftypes.Message) (data []*fftyp | |
| if !foundAll { | ||
| return nil, i18n.NewError(bm.ctx, i18n.MsgDataNotFound, msg.Header.ID) | ||
| } | ||
| log.L(bm.ctx).Infof("Detected new batch-pinned message %s", msg.Header.ID) | ||
| log.L(bm.ctx).Infof("Detected new batch-pinned message %s sequence=%d", msg.Header.ID, msg.Sequence) | ||
| return data, nil | ||
| } | ||
|
|
||
| func (bm *batchManager) markRewind(rewindTo int64) { | ||
| bm.rewindMux.Lock() | ||
| // Make sure we only rewind backwards - as we might get multiple shoulder taps | ||
| // for different message sequences during a single poll cycle. | ||
| if bm.rewindTo < 0 || rewindTo < bm.rewindTo { | ||
| previousRewind := bm.rewindTo | ||
|
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is just to allow logging |
||
| if previousRewind < 0 || rewindTo < previousRewind { | ||
| bm.rewindTo = rewindTo | ||
| } | ||
| bm.rewindMux.Unlock() | ||
| log.L(bm.ctx).Debugf("Marking rewind to sequence=%d (previous=%d)", rewindTo, previousRewind) | ||
| } | ||
|
|
||
| func (bm *batchManager) popRewind() int64 { | ||
|
|
@@ -245,6 +247,7 @@ func (bm *batchManager) readPage() ([]*fftypes.Message, error) { | |
|
|
||
| rewindTo := bm.popRewind() | ||
| if rewindTo >= 0 && rewindTo < bm.offset { | ||
| log.L(bm.ctx).Debugf("Rewinding to sequence=%d", rewindTo) | ||
| if err := bm.updateOffset(true, rewindTo); err != nil { | ||
| return nil, err | ||
| } | ||
|
|
@@ -335,7 +338,7 @@ func (bm *batchManager) newEventNotifications() { | |
| return | ||
| } | ||
| l.Debugf("New message sequence notification: %d", m) | ||
| bm.markRewind(m) | ||
| bm.markRewind(m - 1) | ||
| case <-bm.ctx.Done(): | ||
| l.Debugf("Exiting due to cancelled context") | ||
| return | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -183,6 +183,20 @@ func (ag *aggregator) getPins(ctx context.Context, filter database.Filter) ([]ff | |
| return ls, err | ||
| } | ||
|
|
||
| func (ag *aggregator) extractBatchMessagePin(batch *fftypes.Batch, requiredIndex int64) (totalBatchPins int64, msg *fftypes.Message, msgBaseIndex int64) { | ||
|
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The re-write of this logic, is the main thing here. We trigger from the
|
||
| for _, batchMsg := range batch.Payload.Messages { | ||
| batchMsgBaseIdx := totalBatchPins | ||
| for i := 0; i < len(batchMsg.Header.Topics); i++ { | ||
| if totalBatchPins == requiredIndex { | ||
| msg = batchMsg | ||
| msgBaseIndex = batchMsgBaseIdx | ||
| } | ||
| totalBatchPins++ | ||
| } | ||
| } | ||
| return totalBatchPins, msg, msgBaseIndex | ||
| } | ||
|
|
||
| func (ag *aggregator) processPins(ctx context.Context, pins []*fftypes.Pin, state *batchState) (err error) { | ||
| l := log.L(ctx) | ||
|
|
||
|
|
@@ -192,7 +206,6 @@ func (ag *aggregator) processPins(ctx context.Context, pins []*fftypes.Pin, stat | |
| // We must check all the contexts in the message, and mark them dispatched together. | ||
| dupMsgCheck := make(map[fftypes.UUID]bool) | ||
| for _, pin := range pins { | ||
| l.Debugf("Aggregating pin %.10d batch=%s hash=%s masked=%t", pin.Sequence, pin.Batch, pin.Hash, pin.Masked) | ||
|
|
||
| if batch == nil || *batch.ID != *pin.Batch { | ||
| batch, err = ag.database.GetBatchByID(ctx, pin.Batch) | ||
|
|
@@ -206,23 +219,14 @@ func (ag *aggregator) processPins(ctx context.Context, pins []*fftypes.Pin, stat | |
| } | ||
|
|
||
| // Extract the message from the batch - where the index is of a topic within a message | ||
| var msg *fftypes.Message | ||
| var i int64 = -1 | ||
|
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. In the case of |
||
| var msgBaseIndex int64 | ||
| for iM := 0; i < pin.Index && iM < len(batch.Payload.Messages); iM++ { | ||
| msg = batch.Payload.Messages[iM] | ||
| msgBaseIndex = i | ||
| for iT := 0; i < pin.Index && iT < len(msg.Header.Topics); iT++ { | ||
| i++ | ||
| } | ||
| } | ||
|
|
||
| if i < pin.Index { | ||
| l.Errorf("Batch %s does not have message-topic index %d - pin %s is invalid", pin.Batch, pin.Index, pin.Hash) | ||
| batchPinCount, msg, msgBaseIndex := ag.extractBatchMessagePin(batch, pin.Index) | ||
| if msg == nil { | ||
| l.Errorf("Pin %.10d outside of range: batch=%s pinCount=%d pinIndex=%d hash=%s masked=%t", pin.Sequence, pin.Batch, batchPinCount, pin.Index, pin.Hash, pin.Masked) | ||
| continue | ||
| } | ||
| l.Tracef("Batch %s message %d: %+v", batch.ID, pin.Index, msg) | ||
| if msg == nil || msg.Header.ID == nil { | ||
|
|
||
| l.Debugf("Aggregating pin %.10d batch=%s msg=%s pinIndex=%d msgBaseIndex=%d hash=%s masked=%t", pin.Sequence, pin.Batch, msg.Header.ID, pin.Index, msgBaseIndex, pin.Hash, pin.Masked) | ||
| if msg.Header.ID == nil { | ||
| l.Errorf("null message entry %d in batch '%s'", pin.Index, batch.ID) | ||
| continue | ||
| } | ||
|
|
@@ -243,21 +247,23 @@ func (ag *aggregator) processPins(ctx context.Context, pins []*fftypes.Pin, stat | |
| } | ||
|
|
||
| func (ag *aggregator) processMessage(ctx context.Context, batch *fftypes.Batch, pin *fftypes.Pin, msgBaseIndex int64, msg *fftypes.Message, state *batchState) (err error) { | ||
| l := log.L(ctx) | ||
|
|
||
| // Check if it's ready to be processed | ||
| unmaskedContexts := make([]*fftypes.Bytes32, 0, len(msg.Header.Topics)) | ||
| nextPins := make([]*nextPinState, 0, len(msg.Header.Topics)) | ||
| if pin.Masked { | ||
| // Private messages have one or more masked "pin" hashes that allow us to work | ||
| // out if it's the next message in the sequence, given the previous messages | ||
| if msg.Header.Group == nil || len(msg.Pins) == 0 || len(msg.Header.Topics) != len(msg.Pins) { | ||
| log.L(ctx).Errorf("Message '%s' in batch '%s' has invalid pin data pins=%v topics=%v", msg.Header.ID, batch.ID, msg.Pins, msg.Header.Topics) | ||
| l.Errorf("Message '%s' in batch '%s' has invalid pin data pins=%v topics=%v", msg.Header.ID, batch.ID, msg.Pins, msg.Header.Topics) | ||
| return nil | ||
| } | ||
| for i, pinStr := range msg.Pins { | ||
| var msgContext fftypes.Bytes32 | ||
| err := msgContext.UnmarshalText([]byte(pinStr)) | ||
| if err != nil { | ||
| log.L(ctx).Errorf("Message '%s' in batch '%s' has invalid pin at index %d: '%s'", msg.Header.ID, batch.ID, i, pinStr) | ||
| l.Errorf("Message '%s' in batch '%s' has invalid pin at index %d: '%s'", msg.Header.ID, batch.ID, i, pinStr) | ||
| return nil | ||
| } | ||
| nextPin, err := state.CheckMaskedContextReady(ctx, msg, msg.Header.Topics[i], pin.Sequence, &msgContext) | ||
|
|
@@ -272,14 +278,15 @@ func (ag *aggregator) processMessage(ctx context.Context, batch *fftypes.Batch, | |
| h.Write([]byte(topic)) | ||
| msgContext := fftypes.HashResult(h) | ||
| unmaskedContexts = append(unmaskedContexts, msgContext) | ||
| ready, err := state.CheckUnmaskedContextReady(ctx, *msgContext, msg, msg.Header.Topics[i], pin.Sequence) | ||
| ready, err := state.CheckUnmaskedContextReady(ctx, msgContext, msg, msg.Header.Topics[i], pin.Sequence) | ||
| if err != nil || !ready { | ||
| return err | ||
| } | ||
| } | ||
|
|
||
| } | ||
|
|
||
| l.Debugf("Attempt dispatch msg=%s broadcastContexts=%v privatePins=%v", msg.Header.ID, unmaskedContexts, msg.Pins) | ||
| dispatched, err := ag.attemptMessageDispatch(ctx, msg, state) | ||
| if err != nil { | ||
| return err | ||
|
|
||
Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Seemed arbitrary that we had a page size here, as we have a dedicated goroutine reading from it