const db = require('../models'); const Users = db.users; const PollutionReports = db.pollution_reports; const EcoActionLogs = db.eco_action_logs; const CommunityChallenges = db.community_challenges; const ChallengeParticipations = db.challenge_participations; const RewardTransactions = db.reward_transactions; const RewardsCatalog = db.rewards_catalog; const EducationArticles = db.education_articles; const ClimateAlerts = db.climate_alerts; const PollutionReportsData = [ { // type code here for "relation_one" field "pollution_type": "burning_waste", "latitude": -26.3052, "longitude": 31.1367, "location_text": "Near Mbabane River footbridge", // type code here for "images" field "description": "Small pile of mixed household waste near the riverbank.", "status": "resolved", "is_offline_draft": true, "occurred_at": new Date('2026-03-18T14:10:00Z'), "submitted_at": new Date('2026-03-18T14:20:00Z'), }, { // type code here for "relation_one" field "pollution_type": "illegal_dumping", "latitude": -26.4972, "longitude": 31.3802, "location_text": "Behind Manzini market parking area", // type code here for "images" field "description": "Smoke from burning plastic and paper observed in open area.", "status": "rejected", "is_offline_draft": true, "occurred_at": new Date('2026-03-19T09:30:00Z'), "submitted_at": new Date('2026-03-19T09:41:00Z'), }, { // type code here for "relation_one" field "pollution_type": "burning_waste", "latitude": -26.4575, "longitude": 31.9526, "location_text": "Stream near Siteki community fields", // type code here for "images" field "description": "Oily sheen and litter visible along stream edge.", "status": "rejected", "is_offline_draft": true, "occurred_at": new Date('2026-03-20T12:05:00Z'), "submitted_at": new Date('2026-03-21T08:15:00Z'), }, { // type code here for "relation_one" field "pollution_type": "water_pollution", "latitude": -26.5438, "longitude": 31.1832, "location_text": "Roadside near Malkerns junction", // type code here for "images" field "description": "Construction rubble dumped in drainage channel.", "status": "rejected", "is_offline_draft": true, "occurred_at": new Date('2026-03-15T17:50:00Z'), "submitted_at": new Date('2026-03-15T18:05:00Z'), }, ]; const EcoActionLogsData = [ { // type code here for "relation_one" field "log_date": new Date('2026-03-21T00:00:00Z'), "transport_type": "car", "energy_use": "electricity", "waste_disposal_method": "proper_bin", "transport_points": 18, "energy_points": 30, "waste_points": 25, "total_points": 73, "eco_score": 73.0, "notes": "Used shared taxi and avoided single-use plastics.", }, { // type code here for "relation_one" field "log_date": new Date('2026-03-21T00:00:00Z'), "transport_type": "taxi", "energy_use": "wood", "waste_disposal_method": "burning", "transport_points": 30, "energy_points": 30, "waste_points": 35, "total_points": 95, "eco_score": 95.0, "notes": "Walked to shops and separated recyclables.", }, { // type code here for "relation_one" field "log_date": new Date('2026-03-20T00:00:00Z'), "transport_type": "walk", "energy_use": "electricity", "waste_disposal_method": "proper_bin", "transport_points": 10, "energy_points": 12, "waste_points": 25, "total_points": 47, "eco_score": 47.0, "notes": "Needed car for errands; reduced waste at home.", }, { // type code here for "relation_one" field "log_date": new Date('2026-03-19T00:00:00Z'), "transport_type": "walk", "energy_use": "charcoal", "waste_disposal_method": "recycle", "transport_points": 18, "energy_points": 15, "waste_points": 5, "total_points": 38, "eco_score": 38.0, "notes": "Used wood for cooking and disposed waste by burning.", }, ]; const CommunityChallengesData = [ { "title": "Plant 50 Trees in March", "summary": "Community tree planting across neighborhoods to improve shade and reduce erosion.", "challenge_type": "reduce_waste", "status": "upcoming", "start_at": new Date('2026-03-01T00:00:00Z'), "end_at": new Date('2026-03-31T23:59:00Z'), "points_per_completion": 40, "max_completions_per_user": 3, // type code here for "images" field "rules": "Log each planting day with a photo and location if possible.", }, { "title": "Weekend Litter Cleanup", "summary": "Join a weekend cleanup around markets and taxi ranks to reduce dumping.", "challenge_type": "clean_environment", "status": "completed", "start_at": new Date('2026-03-15T00:00:00Z'), "end_at": new Date('2026-04-15T23:59:00Z'), "points_per_completion": 25, "max_completions_per_user": 6, // type code here for "images" field "rules": "Work in groups where possible; report hotspots after cleanup.", }, { "title": "Reduce Waste at Home", "summary": "Cut household waste by reusing containers and separating recyclables.", "challenge_type": "plant_trees", "status": "completed", "start_at": new Date('2026-04-01T00:00:00Z'), "end_at": new Date('2026-04-30T23:59:00Z'), "points_per_completion": 20, "max_completions_per_user": 10, // type code here for "images" field "rules": "Track actions weekly; share one tip with the community.", }, { "title": "School Yard Greening", "summary": "Support local schools with small tree planting and cleanup activities.", "challenge_type": "clean_environment", "status": "active", "start_at": new Date('2026-02-01T00:00:00Z'), "end_at": new Date('2026-02-28T23:59:00Z'), "points_per_completion": 35, "max_completions_per_user": 2, // type code here for "images" field "rules": "Coordinate with school contact; prioritize indigenous trees.", }, ]; const ChallengeParticipationsData = [ { // type code here for "relation_one" field // type code here for "relation_one" field "participation_status": "left", "progress_count": 2, "points_earned": 80, "joined_at": new Date('2026-03-05T10:00:00Z'), "completed_at": new Date('2026-03-20T11:30:00Z'), }, { // type code here for "relation_one" field // type code here for "relation_one" field "participation_status": "completed", "progress_count": 4, "points_earned": 100, "joined_at": new Date('2026-03-16T08:10:00Z'), "completed_at": new Date('2026-03-23T09:45:00Z'), }, { // type code here for "relation_one" field // type code here for "relation_one" field "participation_status": "completed", "progress_count": 1, "points_earned": 25, "joined_at": new Date('2026-03-18T07:20:00Z'), "completed_at": new Date('2026-03-18T07:20:00Z'), }, { // type code here for "relation_one" field // type code here for "relation_one" field "participation_status": "left", "progress_count": 1, "points_earned": 35, "joined_at": new Date('2026-02-10T12:00:00Z'), "completed_at": new Date('2026-02-20T13:05:00Z'), }, ]; const RewardTransactionsData = [ { // type code here for "relation_one" field "source_type": "challenge_completion", "points": 30, "source_reference": "pollution_reports:1", "note": "Points for verified report submission.", "earned_at": new Date('2026-03-18T14:25:00Z'), }, { // type code here for "relation_one" field "source_type": "pollution_report", "points": 100, "source_reference": "challenge_participations:2", "note": "Completed Weekend Litter Cleanup milestones.", "earned_at": new Date('2026-03-23T10:00:00Z'), }, { // type code here for "relation_one" field "source_type": "challenge_completion", "points": 80, "source_reference": "challenge_participations:1", "note": "Tree planting progress logged.", "earned_at": new Date('2026-03-20T12:00:00Z'), }, { // type code here for "relation_one" field "source_type": "pollution_report", "points": 20, "source_reference": "pollution_reports:3", "note": "Submitted water pollution report (offline sync).", "earned_at": new Date('2026-03-21T08:20:00Z'), }, ]; const RewardsCatalogData = [ { "title": "Reusable Shopping Bag", "description": "Durable bag to reduce single-use plastic usage.", "points_cost": 120, "availability_status": "limited", // type code here for "images" field "terms": "Limited to one per user per month.", }, { "title": "Tree Seedling Voucher", "description": "Voucher redeemable for one indigenous tree seedling.", "points_cost": 200, "availability_status": "limited", // type code here for "images" field "terms": "Redeem at partner nursery locations while stock lasts.", }, { "title": "Water Bottle", "description": "Refillable bottle to encourage reducing plastic waste.", "points_cost": 180, "availability_status": "limited", // type code here for "images" field "terms": "Colors may vary based on availability.", }, { "title": "Community Recognition Badge", "description": "Digital badge displayed on your profile for consistent eco actions.", "points_cost": 75, "availability_status": "limited", // type code here for "images" field "terms": "Badge is non-transferable and appears after redemption.", }, ]; const EducationArticlesData = [ { "title": "Simple Ways to Reduce Household Waste", "category": "soil_erosion_prevention", "excerpt": "Small daily changes can significantly cut waste at home.", "content": "Start by separating recyclables, reusing containers, and choosing products with less packaging. Keep a small sorting area and set a weekly routine for disposal.", // type code here for "images" field "publish_status": "draft", "published_at": new Date('2026-03-10T08:00:00Z'), }, { "title": "Preventing Soil Erosion in Your Yard", "category": "pollution_reduction", "excerpt": "Protect soil with plants, mulch, and smart water flow control.", "content": "Plant ground cover, add mulch, and create gentle terraces on slopes. Direct runoff with small channels and avoid leaving bare soil exposed during heavy rains.", // type code here for "images" field "publish_status": "published", "published_at": new Date('2026-03-12T09:30:00Z'), }, { "title": "Climate Awareness: Heat Safety Tips", "category": "pollution_reduction", "excerpt": "Prepare for high heat with hydration and shade.", "content": "Drink water regularly, avoid peak sun hours, and check on vulnerable neighbors. Use light clothing and keep indoor spaces ventilated when possible.", // type code here for "images" field "publish_status": "published", "published_at": new Date('2026-03-14T06:45:00Z'), }, { "title": "How to Report Pollution Safely", "category": "soil_erosion_prevention", "excerpt": "Report issues without putting yourself at risk.", "content": "Keep a safe distance, avoid handling hazardous waste, and capture a clear photo and location. Submit the report and encourage community action through challenges.", // type code here for "images" field "publish_status": "published", "published_at": new Date('2026-03-16T11:15:00Z'), }, ]; const ClimateAlertsData = [ { "title": "High Heat Expected", "message": "Temperatures will be high this week. Stay hydrated and avoid outdoor work during midday.", "severity": "warning", "alert_type": "heavy_rains", "starts_at": new Date('2026-03-24T00:00:00Z'), "ends_at": new Date('2026-03-28T23:59:00Z'), "is_active": true, }, { "title": "Heavy Rains Coming", "message": "Heavy rains expected in some areas. Clear drains and avoid crossing flooded roads.", "severity": "info", "alert_type": "general", "starts_at": new Date('2026-03-26T00:00:00Z'), "ends_at": new Date('2026-03-27T23:59:00Z'), "is_active": true, }, { "title": "Warm Afternoons", "message": "Afternoon temperatures slightly above average. Plan outdoor activities early.", "severity": "critical", "alert_type": "heavy_rains", "starts_at": new Date('2026-03-20T00:00:00Z'), "ends_at": new Date('2026-03-22T23:59:00Z'), "is_active": false, }, { "title": "Localized Showers", "message": "Short showers possible in the evenings. Keep waste secured to prevent runoff.", "severity": "warning", "alert_type": "general", "starts_at": new Date('2026-03-18T00:00:00Z'), "ends_at": new Date('2026-03-19T23:59:00Z'), "is_active": false, }, ]; // Similar logic for "relation_many" async function associatePollutionReportWithReporter() { const relatedReporter0 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const PollutionReport0 = await PollutionReports.findOne({ order: [['id', 'ASC']], offset: 0 }); if (PollutionReport0?.setReporter) { await PollutionReport0. setReporter(relatedReporter0); } const relatedReporter1 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const PollutionReport1 = await PollutionReports.findOne({ order: [['id', 'ASC']], offset: 1 }); if (PollutionReport1?.setReporter) { await PollutionReport1. setReporter(relatedReporter1); } const relatedReporter2 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const PollutionReport2 = await PollutionReports.findOne({ order: [['id', 'ASC']], offset: 2 }); if (PollutionReport2?.setReporter) { await PollutionReport2. setReporter(relatedReporter2); } const relatedReporter3 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const PollutionReport3 = await PollutionReports.findOne({ order: [['id', 'ASC']], offset: 3 }); if (PollutionReport3?.setReporter) { await PollutionReport3. setReporter(relatedReporter3); } } async function associateEcoActionLogWithUser() { const relatedUser0 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const EcoActionLog0 = await EcoActionLogs.findOne({ order: [['id', 'ASC']], offset: 0 }); if (EcoActionLog0?.setUser) { await EcoActionLog0. setUser(relatedUser0); } const relatedUser1 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const EcoActionLog1 = await EcoActionLogs.findOne({ order: [['id', 'ASC']], offset: 1 }); if (EcoActionLog1?.setUser) { await EcoActionLog1. setUser(relatedUser1); } const relatedUser2 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const EcoActionLog2 = await EcoActionLogs.findOne({ order: [['id', 'ASC']], offset: 2 }); if (EcoActionLog2?.setUser) { await EcoActionLog2. setUser(relatedUser2); } const relatedUser3 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const EcoActionLog3 = await EcoActionLogs.findOne({ order: [['id', 'ASC']], offset: 3 }); if (EcoActionLog3?.setUser) { await EcoActionLog3. setUser(relatedUser3); } } async function associateChallengeParticipationWithChallenge() { const relatedChallenge0 = await CommunityChallenges.findOne({ offset: Math.floor(Math.random() * (await CommunityChallenges.count())), }); const ChallengeParticipation0 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 0 }); if (ChallengeParticipation0?.setChallenge) { await ChallengeParticipation0. setChallenge(relatedChallenge0); } const relatedChallenge1 = await CommunityChallenges.findOne({ offset: Math.floor(Math.random() * (await CommunityChallenges.count())), }); const ChallengeParticipation1 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 1 }); if (ChallengeParticipation1?.setChallenge) { await ChallengeParticipation1. setChallenge(relatedChallenge1); } const relatedChallenge2 = await CommunityChallenges.findOne({ offset: Math.floor(Math.random() * (await CommunityChallenges.count())), }); const ChallengeParticipation2 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 2 }); if (ChallengeParticipation2?.setChallenge) { await ChallengeParticipation2. setChallenge(relatedChallenge2); } const relatedChallenge3 = await CommunityChallenges.findOne({ offset: Math.floor(Math.random() * (await CommunityChallenges.count())), }); const ChallengeParticipation3 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 3 }); if (ChallengeParticipation3?.setChallenge) { await ChallengeParticipation3. setChallenge(relatedChallenge3); } } async function associateChallengeParticipationWithUser() { const relatedUser0 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const ChallengeParticipation0 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 0 }); if (ChallengeParticipation0?.setUser) { await ChallengeParticipation0. setUser(relatedUser0); } const relatedUser1 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const ChallengeParticipation1 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 1 }); if (ChallengeParticipation1?.setUser) { await ChallengeParticipation1. setUser(relatedUser1); } const relatedUser2 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const ChallengeParticipation2 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 2 }); if (ChallengeParticipation2?.setUser) { await ChallengeParticipation2. setUser(relatedUser2); } const relatedUser3 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const ChallengeParticipation3 = await ChallengeParticipations.findOne({ order: [['id', 'ASC']], offset: 3 }); if (ChallengeParticipation3?.setUser) { await ChallengeParticipation3. setUser(relatedUser3); } } async function associateRewardTransactionWithUser() { const relatedUser0 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const RewardTransaction0 = await RewardTransactions.findOne({ order: [['id', 'ASC']], offset: 0 }); if (RewardTransaction0?.setUser) { await RewardTransaction0. setUser(relatedUser0); } const relatedUser1 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const RewardTransaction1 = await RewardTransactions.findOne({ order: [['id', 'ASC']], offset: 1 }); if (RewardTransaction1?.setUser) { await RewardTransaction1. setUser(relatedUser1); } const relatedUser2 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const RewardTransaction2 = await RewardTransactions.findOne({ order: [['id', 'ASC']], offset: 2 }); if (RewardTransaction2?.setUser) { await RewardTransaction2. setUser(relatedUser2); } const relatedUser3 = await Users.findOne({ offset: Math.floor(Math.random() * (await Users.count())), }); const RewardTransaction3 = await RewardTransactions.findOne({ order: [['id', 'ASC']], offset: 3 }); if (RewardTransaction3?.setUser) { await RewardTransaction3. setUser(relatedUser3); } } module.exports = { up: async (queryInterface, Sequelize) => { await PollutionReports.bulkCreate(PollutionReportsData); await EcoActionLogs.bulkCreate(EcoActionLogsData); await CommunityChallenges.bulkCreate(CommunityChallengesData); await ChallengeParticipations.bulkCreate(ChallengeParticipationsData); await RewardTransactions.bulkCreate(RewardTransactionsData); await RewardsCatalog.bulkCreate(RewardsCatalogData); await EducationArticles.bulkCreate(EducationArticlesData); await ClimateAlerts.bulkCreate(ClimateAlertsData); await Promise.all([ // Similar logic for "relation_many" await associatePollutionReportWithReporter(), await associateEcoActionLogWithUser(), await associateChallengeParticipationWithChallenge(), await associateChallengeParticipationWithUser(), await associateRewardTransactionWithUser(), ]); }, down: async (queryInterface, Sequelize) => { await queryInterface.bulkDelete('pollution_reports', null, {}); await queryInterface.bulkDelete('eco_action_logs', null, {}); await queryInterface.bulkDelete('community_challenges', null, {}); await queryInterface.bulkDelete('challenge_participations', null, {}); await queryInterface.bulkDelete('reward_transactions', null, {}); await queryInterface.bulkDelete('rewards_catalog', null, {}); await queryInterface.bulkDelete('education_articles', null, {}); await queryInterface.bulkDelete('climate_alerts', null, {}); }, };