@@ -703,6 +703,8 @@ struct FoodItemAnalysis {
703703 let fiber : Double ?
704704 let protein : Double ?
705705 let assessmentNotes : String ?
706+ // Optional per-item absorption time (hours) if provided by the AI
707+ let absorptionTimeHours : Double ?
706708}
707709
708710/// Type of image being analyzed
@@ -1924,7 +1926,11 @@ private func parseOpenAIResponse(content: String) throws -> AIFoodAnalysisResult
19241926 fat: extractNumber ( from: itemData, keys: [ " fat " ] ) . map { max ( 0 , $0) } ,
19251927 fiber: extractNumber ( from: itemData, keys: [ " fiber " ] ) . map { max ( 0 , $0) } ,
19261928 protein: extractNumber ( from: itemData, keys: [ " protein " ] ) . map { max ( 0 , $0) } ,
1927- assessmentNotes: extractString ( from: itemData, keys: [ " assessment_notes " ] )
1929+ assessmentNotes: extractString ( from: itemData, keys: [ " assessment_notes " ] ) ,
1930+ absorptionTimeHours: {
1931+ if let v = extractNumber ( from: itemData, keys: [ " absorption_time_hours " ] ) { return min ( max ( v, 0 ) , 24 ) }
1932+ return nil
1933+ } ( )
19281934 )
19291935 detailedFoodItems. append ( foodItem)
19301936 }
@@ -2407,7 +2413,8 @@ Use visual references for portion estimates. Compare to USDA serving sizes.
24072413 fat: extractNumber ( from: itemData, keys: [ " fat " ] ) . map { max ( 0 , $0) } , // Bounds checking
24082414 fiber: extractNumber ( from: itemData, keys: [ " fiber " ] ) . map { max ( 0 , $0) } , // Bounds checking
24092415 protein: extractNumber ( from: itemData, keys: [ " protein " ] ) . map { max ( 0 , $0) } , // Bounds checking
2410- assessmentNotes: extractString ( from: itemData, keys: [ " assessment_notes " ] )
2416+ assessmentNotes: extractString ( from: itemData, keys: [ " assessment_notes " ] ) ,
2417+ absorptionTimeHours: nil
24112418 )
24122419 detailedFoodItems. append ( foodItem)
24132420 } catch {
@@ -2440,7 +2447,8 @@ Use visual references for portion estimates. Compare to USDA serving sizes.
24402447 fat: totalFat,
24412448 fiber: totalFiber,
24422449 protein: totalProtein,
2443- assessmentNotes: " Legacy format - combined nutrition values "
2450+ assessmentNotes: " Legacy format - combined nutrition values " ,
2451+ absorptionTimeHours: nil
24442452 )
24452453 detailedFoodItems = [ singleItem]
24462454 }
@@ -2459,7 +2467,8 @@ Use visual references for portion estimates. Compare to USDA serving sizes.
24592467 fat: 10.0 ,
24602468 fiber: 5.0 ,
24612469 protein: 15.0 ,
2462- assessmentNotes: " Safe fallback nutrition estimate - please verify actual food for accuracy "
2470+ assessmentNotes: " Safe fallback nutrition estimate - please verify actual food for accuracy " ,
2471+ absorptionTimeHours: nil
24632472 )
24642473 detailedFoodItems = [ fallbackItem]
24652474 }
@@ -3161,7 +3170,11 @@ class GoogleGeminiFoodAnalysisService {
31613170 fat: extractNumber ( from: itemData, keys: [ " fat " ] ) ,
31623171 fiber: extractNumber ( from: itemData, keys: [ " fiber " ] ) ,
31633172 protein: extractNumber ( from: itemData, keys: [ " protein " ] ) ,
3164- assessmentNotes: extractString ( from: itemData, keys: [ " assessment_notes " ] )
3173+ assessmentNotes: extractString ( from: itemData, keys: [ " assessment_notes " ] ) ,
3174+ absorptionTimeHours: {
3175+ if let v = extractNumber ( from: itemData, keys: [ " absorption_time_hours " ] ) { return min ( max ( v, 0 ) , 24 ) }
3176+ return nil
3177+ } ( )
31653178 )
31663179 detailedFoodItems. append ( foodItem)
31673180 } catch {
@@ -3189,7 +3202,11 @@ class GoogleGeminiFoodAnalysisService {
31893202 fat: totalFat,
31903203 fiber: totalFiber,
31913204 protein: totalProtein,
3192- assessmentNotes: " Legacy format - combined nutrition values "
3205+ assessmentNotes: " Legacy format - combined nutrition values " ,
3206+ absorptionTimeHours: {
3207+ if let v = extractNumber ( from: nutritionData, keys: [ " absorption_time_hours " ] ) { return min ( max ( v, 0 ) , 24 ) }
3208+ return nil
3209+ } ( )
31933210 )
31943211 detailedFoodItems = [ singleItem]
31953212 }
@@ -3211,7 +3228,11 @@ class GoogleGeminiFoodAnalysisService {
32113228 fat: 10.0 ,
32123229 fiber: 5.0 ,
32133230 protein: 15.0 ,
3214- assessmentNotes: " Safe fallback nutrition estimate - check actual food for accuracy "
3231+ assessmentNotes: " Safe fallback nutrition estimate - check actual food for accuracy " ,
3232+ absorptionTimeHours: {
3233+ if let v = extractNumber ( from: nutritionData, keys: [ " absorption_time_hours " ] ) { return min ( max ( v, 0 ) , 24 ) }
3234+ return nil
3235+ } ( )
32153236 )
32163237 detailedFoodItems = [ fallbackItem]
32173238 }
@@ -3477,7 +3498,8 @@ class BasicFoodAnalysisService {
34773498 fat: estimateFat ( for: selectedFood, portion: portionSize) ,
34783499 fiber: estimateFiber ( for: selectedFood, portion: portionSize) ,
34793500 protein: estimateProtein ( for: selectedFood, portion: portionSize) ,
3480- assessmentNotes: " Basic estimate based on typical portions and common nutrition values. For diabetes management, monitor actual blood glucose response. "
3501+ assessmentNotes: " Basic estimate based on typical portions and common nutrition values. For diabetes management, monitor actual blood glucose response. " ,
3502+ absorptionTimeHours: nil
34813503 )
34823504 ]
34833505 }
@@ -3843,7 +3865,8 @@ class ClaudeFoodAnalysisService {
38433865 fat: extractClaudeNumber ( from: item, keys: [ " fat " ] ) . map { max ( 0 , $0) } , // Bounds checking
38443866 fiber: extractClaudeNumber ( from: item, keys: [ " fiber " ] ) . map { max ( 0 , $0) } , // Bounds checking
38453867 protein: extractClaudeNumber ( from: item, keys: [ " protein " ] ) . map { max ( 0 , $0) } , // Bounds checking
3846- assessmentNotes: extractClaudeString ( from: item, keys: [ " assessment_notes " ] )
3868+ assessmentNotes: extractClaudeString ( from: item, keys: [ " assessment_notes " ] ) ,
3869+ absorptionTimeHours: nil
38473870 )
38483871 foodItems. append ( foodItem)
38493872 } catch {
@@ -3877,7 +3900,8 @@ class ClaudeFoodAnalysisService {
38773900 fat: totalFat. map { max ( 0 , $0) } , // Bounds checking
38783901 fiber: totalFiber. map { max ( 0 , $0) } ,
38793902 protein: totalProtein. map { max ( 0 , $0) } , // Bounds checking
3880- assessmentNotes: " Safe fallback nutrition estimate - please verify actual food for accuracy "
3903+ assessmentNotes: " Safe fallback nutrition estimate - please verify actual food for accuracy " ,
3904+ absorptionTimeHours: nil
38813905 )
38823906 ]
38833907 }
0 commit comments