@@ -38,13 +38,17 @@ export const AiFeedbackActions: FC<AiFeedbackActionsProps> = props => {
3838 const [ userVote , setUserVote ] = useState < string | undefined > ( undefined )
3939 const [ upVotes , setUpVotes ] = useState < number > ( 0 )
4040 const [ downVotes , setDownVotes ] = useState < number > ( 0 )
41+ const [ isVotingInprogress , setVotingInprogress ] = useState ( false )
4142
4243 const { loginUserInfo } : ReviewAppContextModel = useContext ( ReviewAppContext )
4344 const { workflowId, workflowRun } : ReviewsContextModel = useReviewsContext ( )
4445
4546 const votesArr : any [ ] = ( props . actionType === 'runItem' ? ( props . feedback ?. votes ) : ( props . comment ?. votes ) ) || [ ]
4647
4748 const setInitialVotesForFeedback = useCallback ( ( ) : void => {
49+ // don't override optimistic updates while a vote mutation is in progress
50+ if ( isVotingInprogress ) return
51+
4852 const initialUp = props . feedback ?. upVotes ?? votesArr . filter ( v => String ( v . voteType )
4953 . toLowerCase ( )
5054 . includes ( 'up' ) ) . length
@@ -56,9 +60,12 @@ export const AiFeedbackActions: FC<AiFeedbackActionsProps> = props => {
5660 setUpVotes ( initialUp )
5761 setDownVotes ( initialDown )
5862 setUserVote ( myVote ?. voteType ?? undefined )
59- } , [ votesArr , props . feedback ] )
63+ } , [ votesArr , props . feedback , isVotingInprogress , loginUserInfo ?. userId ] )
6064
6165 const setInitialVotesForComment = useCallback ( ( ) : void => {
66+ // don't override optimistic updates while a vote mutation is in progress
67+ if ( isVotingInprogress ) return
68+
6269 const initialUp = votesArr . filter ( v => String ( v . voteType )
6370 . toLowerCase ( )
6471 . includes ( 'up' ) ) . length
@@ -70,18 +77,20 @@ export const AiFeedbackActions: FC<AiFeedbackActionsProps> = props => {
7077 setUpVotes ( initialUp )
7178 setDownVotes ( initialDown )
7279 setUserVote ( myVote ?. voteType ?? undefined )
73- } , [ votesArr ] )
80+ } , [ votesArr , isVotingInprogress , loginUserInfo ?. userId ] )
7481
7582 useEffect ( ( ) => {
7683 if ( props . actionType === 'runItem' ) {
7784 setInitialVotesForFeedback ( )
7885 } else {
7986 setInitialVotesForComment ( )
8087 }
81- } , [ props . actionType , props . feedback ?. id , votesArr . length , loginUserInfo ?. userId ] )
88+ } , [ props . actionType , props . feedback ?. id , votesArr . length , loginUserInfo ?. userId , isVotingInprogress ] )
8289
8390 const voteOnItem = useCallback ( async ( type : VOTE_TYPE ) => {
84- if ( ! workflowId || ! workflowRun ?. id ) return
91+ if ( ! workflowId || ! workflowRun ?. id || isVotingInprogress ) return
92+
93+ setVotingInprogress ( true )
8594 const current = userVote
8695 let up = false
8796 let down = false
@@ -136,11 +145,14 @@ export const AiFeedbackActions: FC<AiFeedbackActionsProps> = props => {
136145 setUserVote ( prevUserVote )
137146 setUpVotes ( prevUp )
138147 setDownVotes ( prevDown )
148+ } finally {
149+ setVotingInprogress ( false )
139150 }
140- } , [ workflowId , workflowRun , props . feedback ?. id , userVote , upVotes , downVotes ] )
151+ } , [ workflowId , workflowRun , props . feedback ?. id , userVote , upVotes , downVotes , isVotingInprogress ] )
141152
142153 const voteOnComment = useCallback ( async ( c : any , type : VOTE_TYPE ) => {
143- if ( ! workflowId || ! workflowRun ?. id ) return
154+ if ( ! workflowId || ! workflowRun ?. id || isVotingInprogress ) return
155+ setVotingInprogress ( true )
144156 const votes = ( c . votes || [ ] )
145157 const my = votes . find ( ( v : any ) => String ( v . createdBy ) === String ( loginUserInfo ?. userId ) )
146158 const current = my ?. voteType ?? undefined
@@ -196,8 +208,20 @@ export const AiFeedbackActions: FC<AiFeedbackActionsProps> = props => {
196208 setUserVote ( prevUserVote )
197209 setUpVotes ( prevUp )
198210 setDownVotes ( prevDown )
211+ } finally {
212+ setVotingInprogress ( false )
199213 }
200- } , [ workflowId , workflowRun , props . feedback ?. id , loginUserInfo ] )
214+ } , [
215+ workflowId ,
216+ workflowRun ,
217+ props . feedback ?. id ,
218+ props . comment ?. id ,
219+ loginUserInfo ,
220+ isVotingInprogress ,
221+ userVote ,
222+ upVotes ,
223+ downVotes ,
224+ ] )
201225
202226 const onVote = ( action : VOTE_TYPE ) : void => {
203227 if ( props . actionType === 'comment' ) {
@@ -213,6 +237,7 @@ export const AiFeedbackActions: FC<AiFeedbackActionsProps> = props => {
213237 type = 'button'
214238 className = { styles . actionBtn }
215239 onClick = { ( ) => onVote ( VOTE_TYPE . UPVOTE ) }
240+ disabled = { isVotingInprogress }
216241 >
217242 { userVote === 'UPVOTE' ? < IconThumbsUpFilled /> : < IconThumbsUp /> }
218243 < span className = { styles . count } > { upVotes } </ span >
@@ -222,6 +247,7 @@ export const AiFeedbackActions: FC<AiFeedbackActionsProps> = props => {
222247 type = 'button'
223248 className = { styles . actionBtn }
224249 onClick = { ( ) => onVote ( VOTE_TYPE . DOWNVOTE ) }
250+ disabled = { isVotingInprogress }
225251 >
226252 { userVote === 'DOWNVOTE' ? < IconThumbsDownFilled /> : < IconThumbsDown /> }
227253 < span className = { styles . count } > { downVotes } </ span >
0 commit comments