From 9ed9029e8a701b1fc894ca15c955f5340c4860b2 Mon Sep 17 00:00:00 2001 From: rikimaru0345 Date: Wed, 31 Jan 2024 16:29:12 +0100 Subject: [PATCH 1/2] frontend: don't re-request messages on save to get raw data, instead always include it in every search; otherwise on fast moving topics our reuqest is outdated by the time the user clicks the save messages button (also, we are not even guaranteed that we get the messages from the exact same partitions and offsets each time) --- .../pages/topics/Tab.Messages/index.tsx | 44 ++++++------------- 1 file changed, 14 insertions(+), 30 deletions(-) diff --git a/frontend/src/components/pages/topics/Tab.Messages/index.tsx b/frontend/src/components/pages/topics/Tab.Messages/index.tsx index 5f7e9521d..f928c79ae 100644 --- a/frontend/src/components/pages/topics/Tab.Messages/index.tsx +++ b/frontend/src/components/pages/topics/Tab.Messages/index.tsx @@ -618,7 +618,7 @@ export class TopicMessageView extends Component { Save Messages - this.downloadMessages = null}onRequireRawPayload={() => this.executeMessageSearch(true)} /> + this.downloadMessages = null} onRequireRawPayload={() => this.executeMessageSearch()} /> { (this.messageSource?.data?.length > 0) && @@ -639,7 +639,7 @@ export class TopicMessageView extends Component { this.expandedKeys.push(key); } - async executeMessageSearch(includeRawPayload: boolean = false): Promise { + async executeMessageSearch(): Promise { const searchParams = uiState.topicSettings.searchParams; const canUseFilters = (api.topicPermissions.get(this.props.topic.topicName)?.canUseSearchFilters ?? true) && !isServerless(); @@ -676,7 +676,7 @@ export class TopicMessageView extends Component { startTimestamp: searchParams.startTimestamp, maxResults: searchParams.maxResults, filterInterpreterCode: encodeBase64(sanitizeString(filterCode)), - includeRawPayload: includeRawPayload, + includeRawPayload: true, keyDeserializer: uiState.topicSettings.keyDeserializer, valueDeserializer: uiState.topicSettings.valueDeserializer, @@ -734,7 +734,6 @@ class SaveMessagesDialog extends Component<{ }> { @observable isOpen = false; @observable format = 'json' as 'json' | 'csv'; - @observable isLoadingRawMessage = false; @observable includeRawContent = false; radioStyle = { display: 'block', lineHeight: '30px' }; @@ -784,14 +783,10 @@ class SaveMessagesDialog extends Component<{ - - @@ -801,30 +796,16 @@ class SaveMessagesDialog extends Component<{ } async saveMessages() { - let messages = this.props.messages; - if (messages == null) + const messages = this.props.messages; + if (!messages) { + console.error('cannot save messages, props array is empty'); return; - - try { - if (this.includeRawContent) { - const originalUserSelection = [...messages]; - - // We do not have the raw content (wasn't requested initially) - // so we must restart the message search - this.isLoadingRawMessage = true; - messages = await this.props.onRequireRawPayload(); - - // Here, we do not know whether the user selected to download all messages, or only one. - // So we need to filter all newly downloaded messages against the original user selection - messages = messages.filter(m => originalUserSelection.any(x => m.partitionID == x.partitionID && m.offset == x.offset)); - } - } - finally { - this.isLoadingRawMessage = false; } const cleanMessages = this.cleanMessages(messages); + console.log('saving cleaned messages; messages: ' + messages.length); + const json = toJson(cleanMessages, 4); const link = document.createElement('a'); @@ -842,13 +823,16 @@ class SaveMessagesDialog extends Component<{ // create a copy of each message, omitting properties that don't make // sense for the user, like 'size' or caching properties like 'keyJson'. + const includeRaw = this.includeRawContent; const cleanPayload = function (p: Payload): Payload { if (!p) return undefined as any; const cleanedPayload = { payload: p.payload, - rawPayload: p.rawBytes ? base64FromUInt8Array(p.rawBytes) : undefined, + rawPayload: (includeRaw && p.rawBytes) + ? base64FromUInt8Array(p.rawBytes) + : undefined, encoding: p.encoding, } as any as Payload; From 22e9035c163e64ea62bbb7f5ef23c2b962c24576 Mon Sep 17 00:00:00 2001 From: rikimaru0345 Date: Wed, 31 Jan 2024 16:45:01 +0100 Subject: [PATCH 2/2] frontend: disable save messages button when there are no messages to save --- .../src/components/pages/topics/Tab.Messages/index.tsx | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/frontend/src/components/pages/topics/Tab.Messages/index.tsx b/frontend/src/components/pages/topics/Tab.Messages/index.tsx index f928c79ae..533d388af 100644 --- a/frontend/src/components/pages/topics/Tab.Messages/index.tsx +++ b/frontend/src/components/pages/topics/Tab.Messages/index.tsx @@ -786,7 +786,7 @@ class SaveMessagesDialog extends Component<{ - @@ -797,10 +797,9 @@ class SaveMessagesDialog extends Component<{ async saveMessages() { const messages = this.props.messages; - if (!messages) { - console.error('cannot save messages, props array is empty'); + if (!messages) return; - } + const cleanMessages = this.cleanMessages(messages);