[Cases] Save draft user comment#146327
Conversation
|
Pinging @elastic/response-ops-cases (Feature:Cases) |
| bottomRightContent?: React.ReactNode; | ||
| caseTitle?: string; | ||
| caseTags?: string[]; | ||
| draftCommentStorageKey?: string; |
There was a problem hiding this comment.
If I'm understanding the MarkdownEditorForm correctly, it's used by the description and the comments. I think we could make it a required prop if we applied the same logic you have here for the description and then we wouldn't need to check if it is defined. Would it be complicated to add it to description?
There was a problem hiding this comment.
Adding draftCommentStorageKey to description is not complicated. I thought it as an optional feature, hence optional prop. I am okay to make it mandatory prop.
Correction:
we don't need to add it to description as we are creating storage key in UserActionMarkdown. So it handles storing draft for comments and description while editing them. I will make it a required key and remove the check.
Now that you mentioned description, do we need to store draft description while user is creating a case?
Right now I have handled Edit scenarios after the case is created.
There was a problem hiding this comment.
do we need to store draft description while user is creating a case?
Na, let's just do the edit scenario 👍
There was a problem hiding this comment.
In that case I will keep draftCommentStorageKey?: string; optional as MarkdownEditorForm is also used in description of create cases.
|
|
||
| useDebounce( | ||
| () => { | ||
| if (isFirstRender.current) { |
There was a problem hiding this comment.
Just curious, how come we want to ignore the first render? Is it because it would store the initial value before the user starts typing?
Could we instead just compare the field.value with initialValue and see if they're equal?
There was a problem hiding this comment.
yes, every time you visit a case, you get an empty newComment key stored in the session eventhough user didn't touch the markdown.
i.e. xpack.cases.caseView.{caseId}.{newComment}.markdownEditor
So we want to ignore first render so that it doesn't store newComment markdown key with empty value.
Unfortunately initialValue is undefined for newComment markdown until submit(add comment) is triggered. That's why initialValue is not helpful to detect first render.
|
|
||
| useEffect(() => { | ||
| if (initialValue && initialValue !== field.value) { | ||
| field.setErrors([{ message: i18n.COMMENT_VERSION_CONFLICT_ERROR }]); |
There was a problem hiding this comment.
Thinking about this more, do we really need the user to refresh? We just want them to be aware that something changed under them. Maybe an alternative would be to some warning text that it change and saving will overwrite 🤷♂️
If we set the errors we still let the user save the change but nothing happens, I wonder if we should disable the save button if want to continue with this type of solution.
There was a problem hiding this comment.
I like the first approach, showing warning text instead of error as user is already in writing a comment and suddenly disabling the save button is a preventive action. So just a text warning suggesting that comment has changed, and letting user decide makes sense.
There was a problem hiding this comment.
So just a text warning suggesting that comment has changed, and letting user decide makes sense.
Sounds good to me!
…-ref HEAD~1..HEAD --fix'
… in Markdown after added
|
|
||
| removeItemFromSessionStorate(draftStorageKey); | ||
|
|
||
| /* had to add to this check that session key is removed to avaoid weird issue that on reset |
| caseId: string, | ||
| commentId: string | ||
| ): string => { | ||
| const appIdKey = appId !== '' ? appId : 'kibana'; |
There was a problem hiding this comment.
Let's default it to cases instead of kibana.
There was a problem hiding this comment.
We are returning key as return cases.${appIdKey}.${caseIdKey}.${commentIdKey}.markdownEditor so if we put cases when no appId, it will be cases.cases.${caseId}.${commentId}.markdownEditor
There was a problem hiding this comment.
shall I put const appIdKey = appId !== '' ? appId : 'default'; ?
There was a problem hiding this comment.
I think is better to put const appIdKey = appId !== '' ? appId : 'cases';
peteharverson
left a comment
There was a problem hiding this comment.
Functionally this LGTM. Suggest any other edits to the UX, such as making the messaging clearer when the comment being edited has been updated, be done in a follow-up.
|
@elasticmachine merge upstream |
| if (isFirstRender.current) { | ||
| if (isEmpty(sessionValue) && !isEmpty(field.value)) { | ||
| /* this condition is used to for lens draft comment, | ||
| when user selects and visualization and comes back to Markdown editor, | ||
| it is a first render for Markdown editor, however field has value of visualization which is not stored in session | ||
| hence saving this item in session storage | ||
| */ | ||
|
|
||
| setSessionValue(field.value); | ||
| } | ||
| isFirstRender.current = false; | ||
| return; | ||
| } | ||
| setSessionValue(field.value); |
There was a problem hiding this comment.
I am not 100% sure and maybe I miss something but I think this can be simplified as:
| if (isFirstRender.current) { | |
| if (isEmpty(sessionValue) && !isEmpty(field.value)) { | |
| /* this condition is used to for lens draft comment, | |
| when user selects and visualization and comes back to Markdown editor, | |
| it is a first render for Markdown editor, however field has value of visualization which is not stored in session | |
| hence saving this item in session storage | |
| */ | |
| setSessionValue(field.value); | |
| } | |
| isFirstRender.current = false; | |
| return; | |
| } | |
| setSessionValue(field.value); | |
| if (isFirstRender.current) { | |
| isFirstRender.current = false; | |
| } | |
| setSessionValue(field.value); |
There was a problem hiding this comment.
I just saw this test should not update the session value when it is first render so probably I am wrong 🙂.
There was a problem hiding this comment.
hmm.. may be. let me verify this in local
There was a problem hiding this comment.
spoke too early. It fails the test with jest.advanceTimersByTime. better to not update it.
There was a problem hiding this comment.
Weird, with my code the test should not pass as it will update the value in the first render. Could you please remind me why we do not want to update the session value on the first render? I do not remember.
| </MockHookWrapperComponent> | ||
| ); | ||
|
|
||
| expect(result.container.querySelector('textarea')!.value).toEqual('value set in storage'); |
There was a problem hiding this comment.
nit: this can be done expect(result.getByText('value set in storage')).toBeInTheDocument()
…nce block, unit tests updated
💚 Build Succeeded
Metrics [docs]Module Count
Async chunks
Page load bundle
Unknown metric groupsESLint disabled in files
ESLint disabled line counts
Total ESLint disabled count
History
To update your PR or re-run it, just comment with: |
Thank you for the help :) |
* main: (21 commits) [Profiling] Remove link to 'Other' bucket (elastic#147523) [Synthetics UI] Add missing configuration options to the add/edit monitor forms (elastic#147265) [DOCS] Updates what's new pages (elastic#147483) [Fleet][Endpoint][RBAC V2] Update fleet router and config to allow API access via RBAC controls (elastic#145361) [Guided onboarding] Update guide IDs (elastic#147348) [Synthetics] Add synthetics settings alerting default (elastic#147339) [Security Solution][Endpoint] Fix Policy form being displayed as Read Only when displayed in Fleet pages (elastic#147212) [Cases] Save draft user comment (elastic#146327) [API Docs] Fix `--plugin` filter (elastic#147500) [Fleet] added a logic to use `destinationId` when tagging imported SOs (elastic#147439) Do not skip UPDATE_TARGET_MAPPINGS if upgrading to a newer stack version (elastic#147503) [Discover] Validate if Data View time field exists on Alert creation / editing (elastic#146324) [Discover] Fix Discover navigation from Lens embeddable (elastic#147000) Allow users to Update API Keys (elastic#146237) Update dependency xstate to ^4.35.0 (main) (elastic#147463) [Behavioral Analytics] Remove feature flag to hide functionality (elastic#147429) [Fleet] Add agent policy `inactivity_timeout`experimental setting (elastic#147432) [APM] Switching service groups from grid to flex layout (elastic#147448) [Fleet] Add missing endpoints to openApi specs (elastic#147452) [AO] Allow providing custom time range for Alert Summary Widget (elastic#147253) ...

Summary
This PR saves user's draft comment in a
session storage.Fixed below scenarios requested by users:
Draft.comment.mov
Checklist
Delete any items that are not applicable to this PR.
Passed Flakey tests suite:
https://buildkite.com/elastic/kibana-flaky-test-suite-runner/builds/1647