@@ -118,6 +118,20 @@ function App() {
118118 setAwaitingClarification ( false ) ;
119119 setConfirmedBrief ( data . brief || null ) ;
120120
121+ // Restore availableProducts so product/color name detection works
122+ // when regenerating images in a restored conversation
123+ if ( data . brief ) {
124+ try {
125+ const productsResponse = await fetch ( '/api/products' ) ;
126+ if ( productsResponse . ok ) {
127+ const productsData = await productsResponse . json ( ) ;
128+ setAvailableProducts ( productsData . products || [ ] ) ;
129+ }
130+ } catch ( err ) {
131+ console . error ( 'Error loading products for restored conversation:' , err ) ;
132+ }
133+ }
134+
121135 if ( data . generated_content ) {
122136 const gc = data . generated_content ;
123137 let textContent = gc . text_content ;
@@ -325,13 +339,20 @@ function App() {
325339 let responseData : GeneratedContent | null = null ;
326340 let messageContent = '' ;
327341
342+ // Detect if the user's prompt mentions a different product/color name
343+ // BEFORE the API call so the correct product is sent and persisted
344+ const mentionedProduct = availableProducts . find ( p =>
345+ content . toLowerCase ( ) . includes ( p . product_name . toLowerCase ( ) )
346+ ) ;
347+ const productsForRequest = mentionedProduct ? [ mentionedProduct ] : selectedProducts ;
348+
328349 // Get previous prompt from image_content if available
329350 const previousPrompt = generatedContent . image_content ?. prompt_used ;
330351
331352 for await ( const response of streamRegenerateImage (
332353 content ,
333354 confirmedBrief ,
334- selectedProducts ,
355+ productsForRequest ,
335356 previousPrompt ,
336357 conversationId ,
337358 userId ,
@@ -345,8 +366,21 @@ function App() {
345366
346367 // Update generatedContent with new image
347368 if ( parsedContent . image_url || parsedContent . image_base64 ) {
369+ // Replace old color/product name in text_content when switching products
370+ const oldName = selectedProducts [ 0 ] ?. product_name ;
371+ const newName = mentionedProduct ?. product_name ;
372+ const nameRegex = oldName
373+ ? new RegExp ( oldName . replace ( / [ . * + ? ^ $ { } ( ) | [ \] \\ ] / g, '\\$&' ) , 'gi' )
374+ : undefined ;
375+ const swapName = ( s ?: string ) => {
376+ if ( ! s || ! oldName || ! newName || oldName === newName || ! nameRegex ) return s ;
377+ return s . replace ( nameRegex , ( ) => newName ) ;
378+ } ;
379+ const tc = generatedContent . text_content ;
380+
348381 responseData = {
349382 ...generatedContent ,
383+ text_content : mentionedProduct ? { ...tc , headline : swapName ( tc ?. headline ) , body : swapName ( tc ?. body ) , tagline : swapName ( tc ?. tagline ) , cta_text : swapName ( tc ?. cta_text ) } : tc ,
350384 image_content : {
351385 ...generatedContent . image_content ,
352386 image_url : parsedContent . image_url || generatedContent . image_content ?. image_url ,
@@ -356,6 +390,11 @@ function App() {
356390 } ;
357391 setGeneratedContent ( responseData ) ;
358392
393+ // Update the selected product/color name now that the new image is ready
394+ if ( mentionedProduct ) {
395+ setSelectedProducts ( [ mentionedProduct ] ) ;
396+ }
397+
359398 // Update the confirmed brief to include the modification
360399 // This ensures subsequent "Regenerate" clicks use the updated visual guidelines
361400 const updatedBrief = {
@@ -552,7 +591,7 @@ function App() {
552591 // Trigger refresh of chat history after message is sent
553592 setHistoryRefreshTrigger ( prev => prev + 1 ) ;
554593 }
555- } , [ conversationId , userId , confirmedBrief , pendingBrief , selectedProducts , generatedContent ] ) ;
594+ } , [ conversationId , userId , confirmedBrief , pendingBrief , selectedProducts , generatedContent , availableProducts ] ) ;
556595
557596 const handleBriefConfirm = useCallback ( async ( ) => {
558597 if ( ! pendingBrief ) return ;
0 commit comments