Skip to content

feat: Preserve Meal Groupings and Add "Copy Entire Day" to Food Diary#862

Merged
CodeWithCJ merged 6 commits intomainfrom
dev
Mar 7, 2026
Merged

feat: Preserve Meal Groupings and Add "Copy Entire Day" to Food Diary#862
CodeWithCJ merged 6 commits intomainfrom
dev

Conversation

@CodeWithCJ
Copy link
Owner

@CodeWithCJ CodeWithCJ commented Mar 7, 2026

Tip

Help us review and merge your PR faster!
Please ensure you have completed the Checklist below.
For Frontend changes, please run pnpm run validate to check for any errors.
PRs that include tests and clear screenshots are highly preferred!

Description

Provide a brief summary of your changes.

This PR introduces significant improvements to the Food Diary copying workflow, moving from a "flat" copy to a "deep" copy that preserves organizational structure.

Key Changes:

  • Meal Grouping Preservation: Refactored the backend copy engine to replicate food_entry_meals containers. When a meal is copied, the system now recreates the "container" on the target day and re-links all
    food items, keeping your diary visually and structurally consistent.
  • "Copy Entire Day" Feature: Added a new master workflow to copy every meal and food item from one day to another in a single action.
  • UI Enhancements:
    • Added a new "Copy Day" dropdown in the DailyProgress (Energy Goal) card.
    • Added "Copy all from yesterday" (one-click) and "Copy entire day to date" (calendar picker).
    • Enhanced CopyFoodEntryDialog to dynamically adapt between single-meal and whole-day copy modes.
  • Reliability & Safety:
    • Duplicate Prevention: Updated database checks to be "Meal-Aware," allowing the same food to exist in different meal containers without being incorrectly skipped during a copy.
    • Timezone Safety: Dates are now calculated on the frontend and passed as strings, ensuring "yesterday" is always accurate relative to the user's local time.

Related Issue

PR type [ ] Issue [x] New Feature [ ] Documentation
Linked Issue: # #741

Checklist

Please check all that apply:

  • [MANDATORY for new feature] Alignment: I have raised a GitHub issue and it was reviewed/approved by maintainers
  • Tests: I have included automated tests for my changes.
  • [MANDATORY for UI changes] Screenshots: I have attached "Before" vs "After" screenshots below.
  • [MANDATORY for Frontend changes] Quality: I have run pnpm run validate (especially for Frontend).
  • Translations: I have only updated the English (en) translation file (if applicable).
  • Architecture: My code follows the existing architecture standards.
  • Database Security: I have updated rls_policies.sql for any new user-specific tables.
  • [MANDATORY - ALL] Integrity & License: I certify this is my own work, free of malicious code(phishing, malware, etc.) and I agree to the License terms.

Screenshots (if applicable)

Before

[Insert screenshot/GIF here]

After

[Insert screenshot/GIF here]
image

…sing locally instead of applying any date filter.
…onality

 Key Changes:
   * Meal Grouping Preservation: Refactored the backend copy engine to replicate food_entry_meals containers. When a meal is copied, the system now recreates the "container" on the target day and re-links all
     food items, keeping your diary visually and structurally consistent.
   * "Copy Entire Day" Feature: Added a new master workflow to copy every meal and food item from one day to another in a single action.
   * UI Enhancements:
       * Added a new "Copy Day" dropdown in the DailyProgress (Energy Goal) card.
       * Added "Copy all from yesterday" (one-click) and "Copy entire day to date" (calendar picker).
       * Enhanced CopyFoodEntryDialog to dynamically adapt between single-meal and whole-day copy modes.
   * Reliability & Safety:
       * Duplicate Prevention: Updated database checks to be "Meal-Aware," allowing the same food to exist in different meal containers without being incorrectly skipped during a copy.
       * Timezone Safety: Dates are now calculated on the frontend and passed as strings, ensuring "yesterday" is always accurate relative to the user's local time.
@gemini-code-assist
Copy link
Contributor

Summary of Changes

Hello, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request significantly enhances the food diary's copying capabilities by introducing a 'deep copy' mechanism that preserves meal groupings and allows for the copying of an entire day's food entries. It provides users with more flexible and accurate options for managing their food logs, streamlining the process of replicating daily nutrition data while maintaining data integrity and user experience.

Highlights

  • Meal Grouping Preservation: Refactored the backend copy engine to replicate food_entry_meals containers, ensuring that when a meal is copied, its structural consistency and visual grouping are maintained on the target day.
  • Copy Entire Day Feature: Introduced a new workflow allowing users to copy all meals and food items from one day to another in a single action, including one-click 'Copy all from yesterday' and 'Copy entire day to date' with a calendar picker.
  • UI Enhancements: Added a new 'Copy Day' dropdown in the DailyProgress card and enhanced the CopyFoodEntryDialog to dynamically adapt between single-meal and whole-day copy modes.
  • Reliability & Safety: Updated database checks to be 'Meal-Aware' to prevent incorrect skipping of duplicate foods in different meal containers, and ensured timezone safety by calculating dates on the frontend and passing them as strings.
Changelog
  • SparkyFitnessFrontend/src/api/Diary/foodEntryService.ts
    • Added new asynchronous functions copyAllFoodEntries and copyAllFoodEntriesFromYesterday to handle API calls for copying entire days.
  • SparkyFitnessFrontend/src/hooks/Diary/useFoodEntries.ts
    • Imported the new copyAllFoodEntries and copyAllFoodEntriesFromYesterday API functions.
    • Added useCopyAllFoodEntriesMutation and useCopyAllFoodEntriesFromYesterdayMutation React Query hooks for managing the state and side effects of these new copy operations.
  • SparkyFitnessFrontend/src/pages/Diary/CopyFoodEntryDialog.tsx
    • Introduced isAllDayCopy state to conditionally render UI elements based on whether the dialog is for copying a single meal or an entire day.
    • Updated dialog titles and descriptions to be dynamic based on the isAllDayCopy flag.
    • Implemented logic to hide the meal type selection dropdown when performing an 'all day' copy.
    • Added state management to reset the selected meal type when the dialog opens.
  • SparkyFitnessFrontend/src/pages/Diary/DailyProgress.tsx
    • Reordered the useCalculatedBMR and useAdaptiveTdee hook calls for better logical grouping.
    • Wrapped the CardTitle in a div to accommodate new UI controls for copying food entries.
  • SparkyFitnessFrontend/src/pages/Diary/DiaryTopControls.tsx
    • Imported necessary components and hooks for the new copy functionality, including Button, ClipboardCopy, History, and CopyFoodEntryDialog.
    • Added state isCopyDialogOpen to control the visibility of the CopyFoodEntryDialog.
    • Implemented handleCopyAllFromYesterday and handleCopyAllToDate functions to trigger the respective copy mutations.
    • Integrated new UI buttons ('Copy entire day to date' and 'Copy all from yesterday') into the DailyProgress card header.
    • Included the CopyFoodEntryDialog component, configured for 'all day' copying.
  • SparkyFitnessServer/models/foodEntry.js
    • Modified the getFoodEntryByDetails function to accept an optional foodEntryMealId parameter.
    • Updated the SQL query in getFoodEntryByDetails to include food_entry_meal_id in the duplicate check, allowing for meal-aware duplicate prevention.
  • SparkyFitnessServer/routes/foodEntryRoutes.js
    • Added a new POST route /food-entries/copy-all for copying all food entries from a source date to a target date.
    • Added a new POST route /food-entries/copy-all-yesterday for copying all food entries from the previous day to a target date.
    • Included Swagger documentation for the new /food-entries/copy-all and /food-entries/copy-all-yesterday endpoints.
  • SparkyFitnessServer/services/fitbitService.js
    • Adjusted the syncFitbitData function to pass null for the startDate parameter when processing raw activities, effectively skipping the date safety filter during local replay.
  • SparkyFitnessServer/services/foodEntryService.js
    • Enhanced the copyFoodEntries function to include logic for duplicating food_entry_meals containers and linking copied food entries to these new containers.
    • Introduced a mealMapping to track original and new food_entry_meal_ids during the deep copy process.
    • Refactored copyFoodEntriesFromYesterday to delegate its core logic to the more generalized copyFoodEntries function.
    • Added a new copyAllFoodEntries function that orchestrates the copying of all food entries for an entire day by iterating through all meal types and calling copyFoodEntries for each.
    • Implemented copyAllFoodEntriesFromYesterday to calculate yesterday's date and then utilize copyAllFoodEntries.
    • Exported the newly added copyAllFoodEntries and copyAllFoodEntriesFromYesterday functions.
  • SparkyFitnessServer/services/stravaService.js
    • Modified the syncStravaData function to pass null for the startDate parameter when processing raw activities, effectively skipping the date safety filter during local replay.
  • docker/.env.example
    • Updated the default value for SPARKY_FITNESS_FRONTEND_URL from http://localhost:3010 to http://localhost:3004.
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

Copy link
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces a valuable "Copy Entire Day" feature and refactors the backend copy logic to preserve meal groupings, which is a great enhancement for user experience. The backend changes are well-structured, with good code reuse in the service layer. The frontend is updated to support the new functionality. I've identified a couple of areas for improvement in the React components related to best practices and type safety, which I've detailed in the comments.

@CodeWithCJ CodeWithCJ merged commit 988a02d into main Mar 7, 2026
6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant