573 lines
14 KiB
JavaScript
573 lines
14 KiB
JavaScript
require('reflect-metadata');
|
|
const { Sequelize } = require('sequelize-typescript');
|
|
const path = require('path');
|
|
const fs = require('fs');
|
|
|
|
let FoodItem;
|
|
let MealFood;
|
|
let PlannedFood;
|
|
let Meal;
|
|
let User;
|
|
let WaterLog;
|
|
let WeightLog;
|
|
let MealPlan;
|
|
let UserGoal;
|
|
let DailySummary;
|
|
let APICache;
|
|
const foodItemPath = path.join(__dirname, '../dist/models/food-item.model.js');
|
|
const mealFoodPath = path.join(__dirname, '../dist/models/meal-food.model.js');
|
|
const plannedFoodPath = path.join(__dirname, '../dist/models/planned-food.model.js');
|
|
const mealPath = path.join(__dirname, '../dist/models/meal.model.js');
|
|
const userPath = path.join(__dirname, '../dist/models/user.model.js');
|
|
const waterLogPath = path.join(__dirname, '../dist/models/water-log.model.js');
|
|
const weightLogPath = path.join(__dirname, '../dist/models/weight-log.model.js');
|
|
const mealPlanPath = path.join(__dirname, '../dist/models/meal-plan.model.js');
|
|
const userGoalPath = path.join(__dirname, '../dist/models/user-goal.model.js');
|
|
const dailySummaryPath = path.join(__dirname, '../dist/models/daily-summary.model.js');
|
|
const apiCachePath = path.join(__dirname, '../dist/models/api-cache.model.js');
|
|
if (fs.existsSync(foodItemPath)) {
|
|
const mod = require(foodItemPath);
|
|
FoodItem = mod.FoodItem;
|
|
} else {
|
|
console.error('Missing model: ' + foodItemPath);
|
|
process.exit(1);
|
|
}
|
|
if (fs.existsSync(mealFoodPath)) {
|
|
const mod = require(mealFoodPath);
|
|
MealFood = mod.MealFood;
|
|
}
|
|
if (fs.existsSync(plannedFoodPath)) {
|
|
const mod = require(plannedFoodPath);
|
|
PlannedFood = mod.PlannedFood;
|
|
}
|
|
if (fs.existsSync(mealPath)) {
|
|
const mod = require(mealPath);
|
|
Meal = mod.Meal;
|
|
}
|
|
if (fs.existsSync(userPath)) {
|
|
const mod = require(userPath);
|
|
User = mod.User;
|
|
}
|
|
if (fs.existsSync(waterLogPath)) {
|
|
const mod = require(waterLogPath);
|
|
WaterLog = mod.WaterLog;
|
|
}
|
|
if (fs.existsSync(weightLogPath)) {
|
|
const mod = require(weightLogPath);
|
|
WeightLog = mod.WeightLog;
|
|
}
|
|
if (fs.existsSync(mealPlanPath)) {
|
|
const mod = require(mealPlanPath);
|
|
MealPlan = mod.MealPlan;
|
|
}
|
|
if (fs.existsSync(userGoalPath)) {
|
|
const mod = require(userGoalPath);
|
|
UserGoal = mod.UserGoal;
|
|
}
|
|
if (fs.existsSync(dailySummaryPath)) {
|
|
const mod = require(dailySummaryPath);
|
|
DailySummary = mod.DailySummary;
|
|
}
|
|
if (fs.existsSync(apiCachePath)) {
|
|
const mod = require(apiCachePath);
|
|
APICache = mod.APICache;
|
|
}
|
|
|
|
// Database connection
|
|
const dbPath = process.env.DATABASE_URL
|
|
? process.env.DATABASE_URL.replace('sqlite://', '')
|
|
: path.join(__dirname, '../data/calorie_tracker.db');
|
|
|
|
// Ensure data directory exists if using sqlite file
|
|
if (!process.env.DATABASE_URL) {
|
|
const dataDir = path.dirname(dbPath);
|
|
if (!fs.existsSync(dataDir)) {
|
|
fs.mkdirSync(dataDir, { recursive: true });
|
|
}
|
|
}
|
|
|
|
const sequelize = new Sequelize({
|
|
dialect: 'sqlite',
|
|
storage: dbPath,
|
|
logging: false
|
|
});
|
|
const models = [FoodItem].concat([MealFood, PlannedFood, Meal, User, WaterLog, WeightLog, MealPlan, UserGoal, DailySummary, APICache].filter(Boolean));
|
|
sequelize.addModels(models);
|
|
|
|
const filipinoFoods = [
|
|
// Rice (Kanin)
|
|
{
|
|
name: 'White Rice',
|
|
name_tagalog: 'Kanin',
|
|
category: 'kanin',
|
|
calories: 206,
|
|
protein_g: 4.3,
|
|
carbs_g: 45,
|
|
fat_g: 0.4,
|
|
serving_description: '1 cup cooked',
|
|
serving_size_g: 158
|
|
},
|
|
{
|
|
name: 'Fried Rice',
|
|
name_tagalog: 'Sinangag',
|
|
category: 'kanin',
|
|
calories: 280,
|
|
protein_g: 5,
|
|
carbs_g: 42,
|
|
fat_g: 10,
|
|
serving_description: '1 cup',
|
|
serving_size_g: 170
|
|
},
|
|
|
|
// Main Dishes (Ulam)
|
|
{
|
|
name: 'Chicken Adobo',
|
|
name_tagalog: 'Adobong Manok',
|
|
category: 'ulam',
|
|
calories: 350,
|
|
protein_g: 35,
|
|
carbs_g: 5,
|
|
fat_g: 20,
|
|
serving_description: '1 serving (2 pieces)',
|
|
serving_size_g: 200
|
|
},
|
|
{
|
|
name: 'Pork Sinigang',
|
|
name_tagalog: 'Sinigang na Baboy',
|
|
category: 'sabaw',
|
|
calories: 280,
|
|
protein_g: 25,
|
|
carbs_g: 10,
|
|
fat_g: 15,
|
|
serving_description: '1 bowl',
|
|
serving_size_g: 350
|
|
},
|
|
{
|
|
name: 'Chicken Tinola',
|
|
name_tagalog: 'Tinolang Manok',
|
|
category: 'sabaw',
|
|
calories: 200,
|
|
protein_g: 28,
|
|
carbs_g: 8,
|
|
fat_g: 6,
|
|
serving_description: '1 bowl',
|
|
serving_size_g: 350
|
|
},
|
|
{
|
|
name: 'Bicol Express',
|
|
name_tagalog: 'Bicol Express',
|
|
category: 'ulam',
|
|
calories: 400,
|
|
protein_g: 20,
|
|
carbs_g: 10,
|
|
fat_g: 32,
|
|
serving_description: '1 serving',
|
|
serving_size_g: 200
|
|
},
|
|
{
|
|
name: 'Pork Sisig',
|
|
name_tagalog: 'Sisig',
|
|
category: 'ulam',
|
|
calories: 450,
|
|
protein_g: 25,
|
|
carbs_g: 8,
|
|
fat_g: 35,
|
|
serving_description: '1 serving',
|
|
serving_size_g: 180
|
|
},
|
|
{
|
|
name: 'Menudo',
|
|
name_tagalog: 'Menudo',
|
|
category: 'ulam',
|
|
calories: 320,
|
|
protein_g: 22,
|
|
carbs_g: 12,
|
|
fat_g: 20,
|
|
serving_description: '1 serving',
|
|
serving_size_g: 200
|
|
},
|
|
{
|
|
name: 'Kare-Kare',
|
|
name_tagalog: 'Kare-Kare',
|
|
category: 'ulam',
|
|
calories: 380,
|
|
protein_g: 24,
|
|
carbs_g: 18,
|
|
fat_g: 25,
|
|
serving_description: '1 serving',
|
|
serving_size_g: 250
|
|
},
|
|
{
|
|
name: 'Lechon Kawali',
|
|
name_tagalog: 'Lechon Kawali',
|
|
category: 'ulam',
|
|
calories: 500,
|
|
protein_g: 30,
|
|
carbs_g: 2,
|
|
fat_g: 42,
|
|
serving_description: '1 serving',
|
|
serving_size_g: 150
|
|
},
|
|
{
|
|
name: 'Pork Nilaga',
|
|
name_tagalog: 'Nilagang Baboy',
|
|
category: 'sabaw',
|
|
calories: 280,
|
|
protein_g: 28,
|
|
carbs_g: 12,
|
|
fat_g: 14,
|
|
serving_description: '1 bowl',
|
|
serving_size_g: 350
|
|
},
|
|
{
|
|
name: 'Beef Bulalo',
|
|
name_tagalog: 'Bulalo',
|
|
category: 'sabaw',
|
|
calories: 350,
|
|
protein_g: 32,
|
|
carbs_g: 8,
|
|
fat_g: 22,
|
|
serving_description: '1 bowl',
|
|
serving_size_g: 400
|
|
},
|
|
|
|
// Vegetables (Gulay)
|
|
{
|
|
name: 'Pinakbet',
|
|
name_tagalog: 'Pinakbet',
|
|
category: 'gulay',
|
|
calories: 150,
|
|
protein_g: 5,
|
|
carbs_g: 20,
|
|
fat_g: 6,
|
|
serving_description: '1 cup',
|
|
serving_size_g: 200
|
|
},
|
|
{
|
|
name: 'Laing',
|
|
name_tagalog: 'Laing',
|
|
category: 'gulay',
|
|
calories: 180,
|
|
protein_g: 6,
|
|
carbs_g: 15,
|
|
fat_g: 12,
|
|
serving_description: '1 cup',
|
|
serving_size_g: 180
|
|
},
|
|
{
|
|
name: 'Ginisang Monggo',
|
|
name_tagalog: 'Ginisang Monggo',
|
|
category: 'gulay',
|
|
calories: 200,
|
|
protein_g: 12,
|
|
carbs_g: 30,
|
|
fat_g: 4,
|
|
serving_description: '1 cup',
|
|
serving_size_g: 220
|
|
},
|
|
|
|
// Breakfast (Almusal)
|
|
{
|
|
name: 'Beef Tapa with Rice and Egg',
|
|
name_tagalog: 'Tapsilog',
|
|
category: 'almusal',
|
|
calories: 650,
|
|
protein_g: 45,
|
|
carbs_g: 60,
|
|
fat_g: 25,
|
|
serving_description: '1 plate',
|
|
serving_size_g: 400
|
|
},
|
|
{
|
|
name: 'Longganisa with Rice and Egg',
|
|
name_tagalog: 'Longsilog',
|
|
category: 'almusal',
|
|
calories: 700,
|
|
protein_g: 38,
|
|
carbs_g: 65,
|
|
fat_g: 32,
|
|
serving_description: '1 plate',
|
|
serving_size_g: 420
|
|
},
|
|
{
|
|
name: 'Tocino with Rice and Egg',
|
|
name_tagalog: 'Tocilog',
|
|
category: 'almusal',
|
|
calories: 680,
|
|
protein_g: 42,
|
|
carbs_g: 62,
|
|
fat_g: 28,
|
|
serving_description: '1 plate',
|
|
serving_size_g: 400
|
|
},
|
|
{
|
|
name: 'Fried Egg',
|
|
name_tagalog: 'Pritong Itlog',
|
|
category: 'almusal',
|
|
calories: 90,
|
|
protein_g: 6,
|
|
carbs_g: 1,
|
|
fat_g: 7,
|
|
serving_description: '1 egg',
|
|
serving_size_g: 50
|
|
},
|
|
|
|
// Snacks (Meryenda)
|
|
{
|
|
name: 'Pandesal',
|
|
name_tagalog: 'Pandesal',
|
|
category: 'meryenda',
|
|
calories: 120,
|
|
protein_g: 3,
|
|
carbs_g: 22,
|
|
fat_g: 2,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 40
|
|
},
|
|
{
|
|
name: 'Turon',
|
|
name_tagalog: 'Turon',
|
|
category: 'meryenda',
|
|
calories: 180,
|
|
protein_g: 2,
|
|
carbs_g: 35,
|
|
fat_g: 5,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 80
|
|
},
|
|
{
|
|
name: 'Bibingka',
|
|
name_tagalog: 'Bibingka',
|
|
category: 'meryenda',
|
|
calories: 220,
|
|
protein_g: 5,
|
|
carbs_g: 38,
|
|
fat_g: 6,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 100
|
|
},
|
|
{
|
|
name: 'Puto',
|
|
name_tagalog: 'Puto',
|
|
category: 'meryenda',
|
|
calories: 90,
|
|
protein_g: 2,
|
|
carbs_g: 18,
|
|
fat_g: 1,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 40
|
|
},
|
|
{
|
|
name: 'Lumpia',
|
|
name_tagalog: 'Lumpia',
|
|
category: 'meryenda',
|
|
calories: 100,
|
|
protein_g: 4,
|
|
carbs_g: 10,
|
|
fat_g: 5,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 50
|
|
},
|
|
{
|
|
name: 'Banana Cue',
|
|
name_tagalog: 'Banana Cue',
|
|
category: 'meryenda',
|
|
calories: 150,
|
|
protein_g: 1,
|
|
carbs_g: 32,
|
|
fat_g: 4,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 100
|
|
},
|
|
|
|
// Proteins
|
|
{
|
|
name: 'Grilled Tilapia',
|
|
name_tagalog: 'Inihaw na Tilapia',
|
|
category: 'ulam',
|
|
calories: 180,
|
|
protein_g: 32,
|
|
carbs_g: 0,
|
|
fat_g: 5,
|
|
serving_description: '1 whole fish',
|
|
serving_size_g: 150
|
|
},
|
|
{
|
|
name: 'Grilled Chicken',
|
|
name_tagalog: 'Inihaw na Manok',
|
|
category: 'ulam',
|
|
calories: 280,
|
|
protein_g: 40,
|
|
carbs_g: 0,
|
|
fat_g: 13,
|
|
serving_description: '1 breast',
|
|
serving_size_g: 150
|
|
},
|
|
{
|
|
name: 'Fried Bangus',
|
|
name_tagalog: 'Pritong Bangus',
|
|
category: 'ulam',
|
|
calories: 220,
|
|
protein_g: 28,
|
|
carbs_g: 0,
|
|
fat_g: 12,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 120
|
|
},
|
|
|
|
// Vegetables (Gulay)
|
|
{
|
|
name: 'Pinakbet',
|
|
name_tagalog: 'Pinakbet',
|
|
category: 'gulay',
|
|
calories: 150,
|
|
protein_g: 6,
|
|
carbs_g: 15,
|
|
fat_g: 8,
|
|
serving_description: '1 cup',
|
|
serving_size_g: 200
|
|
},
|
|
{
|
|
name: 'Ginisang Monggo',
|
|
name_tagalog: 'Ginisang Monggo',
|
|
category: 'gulay',
|
|
calories: 220,
|
|
protein_g: 15,
|
|
carbs_g: 30,
|
|
fat_g: 6,
|
|
serving_description: '1 cup',
|
|
serving_size_g: 240
|
|
},
|
|
{
|
|
name: 'Chopsuey',
|
|
name_tagalog: 'Chopsuey',
|
|
category: 'gulay',
|
|
calories: 180,
|
|
protein_g: 12,
|
|
carbs_g: 10,
|
|
fat_g: 10,
|
|
serving_description: '1 cup',
|
|
serving_size_g: 200
|
|
},
|
|
{
|
|
name: 'Laing',
|
|
name_tagalog: 'Laing',
|
|
category: 'gulay',
|
|
calories: 250,
|
|
protein_g: 5,
|
|
carbs_g: 12,
|
|
fat_g: 22,
|
|
serving_description: '1 serving',
|
|
serving_size_g: 150
|
|
},
|
|
|
|
// Breakfast
|
|
{
|
|
name: 'Tapsilog',
|
|
name_tagalog: 'Tapsilog',
|
|
category: 'almusal',
|
|
calories: 550,
|
|
protein_g: 35,
|
|
carbs_g: 45,
|
|
fat_g: 25,
|
|
serving_description: '1 order (rice, egg, beef)',
|
|
serving_size_g: 350
|
|
},
|
|
{
|
|
name: 'Longsilog',
|
|
name_tagalog: 'Longsilog',
|
|
category: 'almusal',
|
|
calories: 600,
|
|
protein_g: 20,
|
|
carbs_g: 45,
|
|
fat_g: 35,
|
|
serving_description: '1 order (rice, egg, sausage)',
|
|
serving_size_g: 350
|
|
},
|
|
{
|
|
name: 'Pandesal',
|
|
name_tagalog: 'Pandesal',
|
|
category: 'almusal',
|
|
calories: 35,
|
|
protein_g: 1.5,
|
|
carbs_g: 6,
|
|
fat_g: 0.5,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 30
|
|
},
|
|
|
|
// Desserts/Snacks
|
|
{
|
|
name: 'Halo-Halo',
|
|
name_tagalog: 'Halo-Halo',
|
|
category: 'meryenda',
|
|
calories: 450,
|
|
protein_g: 12,
|
|
carbs_g: 85,
|
|
fat_g: 8,
|
|
serving_description: '1 glass',
|
|
serving_size_g: 400
|
|
},
|
|
{
|
|
name: 'Leche Flan',
|
|
name_tagalog: 'Leche Flan',
|
|
category: 'meryenda',
|
|
calories: 220,
|
|
protein_g: 5,
|
|
carbs_g: 25,
|
|
fat_g: 10,
|
|
serving_description: '1 slice',
|
|
serving_size_g: 80
|
|
},
|
|
{
|
|
name: 'Turon',
|
|
name_tagalog: 'Turon',
|
|
category: 'meryenda',
|
|
calories: 200,
|
|
protein_g: 2,
|
|
carbs_g: 35,
|
|
fat_g: 7,
|
|
serving_description: '1 piece',
|
|
serving_size_g: 100
|
|
}
|
|
];
|
|
|
|
async function seed() {
|
|
try {
|
|
await sequelize.authenticate();
|
|
console.log('Database connection has been established successfully.');
|
|
|
|
// Sync database (create tables if not exists)
|
|
await sequelize.sync();
|
|
|
|
let addedCount = 0;
|
|
|
|
for (const foodData of filipinoFoods) {
|
|
// Check if already exists
|
|
const existing = await FoodItem.findOne({
|
|
where: {
|
|
name: foodData.name,
|
|
is_filipino: true
|
|
}
|
|
});
|
|
|
|
if (!existing) {
|
|
await FoodItem.create({
|
|
...foodData,
|
|
source: 'filipino',
|
|
is_filipino: true
|
|
});
|
|
addedCount++;
|
|
}
|
|
}
|
|
|
|
console.log(`Successfully added ${addedCount} Filipino foods to the database!`);
|
|
} catch (error) {
|
|
console.error('Error seeding Filipino foods:', error);
|
|
} finally {
|
|
await sequelize.close();
|
|
}
|
|
}
|
|
|
|
seed();
|