Background
The current model has a Profile entity sitting between Deal and the actual criteria objects:
Deal → Profile → ProfileActivity → Activity
→ ProfileLanguage → Language
→ ProfileSkill → Skill
→ Category (optional)
.info (optional string)
Both Opportunity and Volunteer inherit their shared criteria (languages, activities, skills) by navigating entity.deal.profile.*. The Profile entity was likely introduced to allow criteria reuse across multiple Deals (the schema allows one Profile to be referenced by many Deals), but in practice each Deal appears to have its own Profile — making it over-engineered.
Proposed Change
Remove Profile and collapse its M2M relationships directly onto Deal:
Deal → DealActivity → Activity
→ DealLanguage → Language
→ DealSkill → Skill
The profile.info and profile.category fields would need a new home — likely directly on Deal, or split to Opportunity / Volunteer depending on which actually uses them.
Impact Areas to Audit Before Making Changes
Before touching any code, the following must be scanned:
Acceptance Criteria
Notes
- This is a breaking change to the API response shape — coordinate with the FE team before merging
- Do NOT add migration columns/tables until the approach above is agreed upon
Background
The current model has a
Profileentity sitting betweenDealand the actual criteria objects:Both
OpportunityandVolunteerinherit their shared criteria (languages, activities, skills) by navigatingentity.deal.profile.*. TheProfileentity was likely introduced to allow criteria reuse across multiple Deals (the schema allows one Profile to be referenced by many Deals), but in practice each Deal appears to have its own Profile — making it over-engineered.Proposed Change
Remove
Profileand collapse its M2M relationships directly ontoDeal:The
profile.infoandprofile.categoryfields would need a new home — likely directly onDeal, or split toOpportunity/Volunteerdepending on which actually uses them.Impact Areas to Audit Before Making Changes
Before touching any code, the following must be scanned:
deal.profile(profile loading, eager joins)profilefields in API responsesdeal_activity,deal_language,deal_skill) must be created and oldprofile_activity,profile_language,profile_skilldata migrated before droppingprofilecategoryrelationship currently on Profile — decide where it movesprofile.infofield — decide where it movesAcceptance Criteria
Profile,ProfileActivity,ProfileLanguage,ProfileSkillentities are removedDealdirectly exposes activity, language, and skill M2M relationshipsNotes