From 11155d55effbf6a5864e939b9125ccc8754b953b Mon Sep 17 00:00:00 2001 From: ceyhuntopcu Date: Wed, 20 Mar 2024 20:42:59 -0400 Subject: [PATCH 1/4] Add email functionality and send condo fees to owners --- server/src/CondoUnit/controller.js | 89 +++++++++++++++++++++++++++++- 1 file changed, 88 insertions(+), 1 deletion(-) diff --git a/server/src/CondoUnit/controller.js b/server/src/CondoUnit/controller.js index 7381bb6c..4316b217 100644 --- a/server/src/CondoUnit/controller.js +++ b/server/src/CondoUnit/controller.js @@ -1,5 +1,31 @@ const pool = require('../../db') const queries = require('./queries') +const nodemailer = require('nodemailer') + +const transporter = nodemailer.createTransport({ + service: 'gmail', + auth: { + user: process.env.BUTLER_EMAIL, + pass: process.env.BUTLER_EMAIL_PASSWORD + } +}) + +const sendEmail = ({ to, subject, text }) => { + const mailOptions = { + from: process.env.BUTLER_EMAIL, + to, + subject, + text + } + + transporter.sendMail(mailOptions, (error, info) => { + if (error) { + console.error('Error sending email:', error) + } else { + console.log('Email sent:', info.response) + } + }) +} const getCondoUnits = (req, res) => { console.log('Get All Condo Units') @@ -142,11 +168,72 @@ const calculateTotalCondoFee = (req, res) => { }) } +const sendCondoFeesToOwners = (propertyId) => { + pool.query(queries.getCondoOwnersEmailsByProperty, [propertyId], (error, ownersResults) => { + if (error) { + console.error('Error fetching condo owners:', error) + return + } + + ownersResults.rows.forEach(owner => { + const condoId = owner.condoid + const ownerEmail = owner.user_email + + calculateTotalCondoFeeForEmail(condoId, (condoFeeInfo) => { + if (condoFeeInfo) { + sendEmail({ + to: ownerEmail, + subject: 'Your Condo Fees', + text: `Hello, here are your condo fees details:\n\n${JSON.stringify(condoFeeInfo, null, 2)}` + }) + } + }) + }) + }) +} + +const calculateTotalCondoFeeForEmail = (condoId, callback) => { + pool.query(queries.getCondoFeePerSqrft, [condoId], (error, feeResults) => { + if (error || feeResults.rowCount === 0) { + console.error('Error fetching condo fee or condo unit not found:', error) + callback(null) + } else { + const condoInformation = feeResults.rows[0] + const condoSize = condoInformation.size + const feePerSquareFoot = condoInformation.condo_fee_per_sqrft + const CondoFee = condoSize * feePerSquareFoot + + pool.query(queries.getCondoParkingFee, [condoId], (parkingError, parkingResults) => { + const parkingFee = parkingResults.rows.length > 0 ? parkingResults.rows[0].parking_fee : 0 + + pool.query(queries.getCondoLockerFee, [condoId], (lockerError, lockerResults) => { + const lockerFee = lockerResults.rows.length > 0 ? lockerResults.rows[0].locker_fee : 0 + + const condoFeeInfo = { + 'Condo Size': condoSize, + 'Fee Per Square Foot': feePerSquareFoot, + 'Condo Fee': CondoFee, + 'Additional Fees': { + 'Parking Fee': parkingFee, + 'Locker Fee': lockerFee + }, + 'Total Additional Fees': parkingFee + lockerFee, + 'Total Condo Fee': CondoFee + parkingFee + lockerFee + } + + callback(condoFeeInfo) + }) + }) + } + }) +} + module.exports = { getCondoUnits, getCondoUnitById, addCondoUnit, removeCondoUnit, updateCondoUnit, - calculateTotalCondoFee + calculateTotalCondoFee, + sendCondoFeesToOwners } From 2dc7f0c5532170f11fca8d3c32de39d6050a8eb0 Mon Sep 17 00:00:00 2001 From: ceyhuntopcu Date: Wed, 20 Mar 2024 20:43:03 -0400 Subject: [PATCH 2/4] Add query to get condo owners' emails by property --- server/src/CondoUnit/queries.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/server/src/CondoUnit/queries.js b/server/src/CondoUnit/queries.js index 6bc3ec24..9d310909 100644 --- a/server/src/CondoUnit/queries.js +++ b/server/src/CondoUnit/queries.js @@ -8,6 +8,7 @@ const updateCondoUnit = 'UPDATE condo_unit SET companyid = $1, property_id = $2, const getCondoFeePerSqrft = 'SELECT pp.condo_fee_per_sqrft, cu.size FROM property pp, condo_unit cu WHERE pp.property_id = cu.property_id AND cu.condoid = $1' const getCondoParkingFee = 'SELECT p.parking_fee FROM property p, condo_unit c, active_registration_key ark, assigned_parking_spot asp WHERE ark.condoid = $1 AND asp.userid = ark.userid AND c.condoid = $1 AND c.property_id = p.property_id' const getCondoLockerFee = 'SELECT p.locker_fee FROM property p, condo_unit c, active_registration_key ark, assigned_locker al WHERE ark.condoid = $1 AND al.userid = ark.userid AND c.condoid = $1 AND c.property_id = p.property_id' +const getCondoOwnersEmailsByProperty = 'SELECT cu.condoid, pu.email AS user_email FROM condo_unit cu INNER JOIN active_registration_key ark ON cu.condoid = ark.condoid INNER JOIN public_user pu ON ark.userid = pu.userid WHERE cu.property_id = $1' module.exports = { getCondoUnits, @@ -19,5 +20,6 @@ module.exports = { updateCondoUnit, getCondoFeePerSqrft, getCondoParkingFee, - getCondoLockerFee + getCondoLockerFee, + getCondoOwnersEmailsByProperty } From 119b3684e33908440fe03462f2d74d365d1475ad Mon Sep 17 00:00:00 2001 From: ceyhuntopcu Date: Wed, 20 Mar 2024 20:49:17 -0400 Subject: [PATCH 3/4] quick fix --- server/src/CondoUnit/controller.js | 50 ++++++++++++++++-------------- server/src/CondoUnit/routes.js | 1 + 2 files changed, 28 insertions(+), 23 deletions(-) diff --git a/server/src/CondoUnit/controller.js b/server/src/CondoUnit/controller.js index 4316b217..95c76f76 100644 --- a/server/src/CondoUnit/controller.js +++ b/server/src/CondoUnit/controller.js @@ -168,29 +168,33 @@ const calculateTotalCondoFee = (req, res) => { }) } -const sendCondoFeesToOwners = (propertyId) => { - pool.query(queries.getCondoOwnersEmailsByProperty, [propertyId], (error, ownersResults) => { - if (error) { - console.error('Error fetching condo owners:', error) - return - } - - ownersResults.rows.forEach(owner => { - const condoId = owner.condoid - const ownerEmail = owner.user_email - - calculateTotalCondoFeeForEmail(condoId, (condoFeeInfo) => { - if (condoFeeInfo) { - sendEmail({ - to: ownerEmail, - subject: 'Your Condo Fees', - text: `Hello, here are your condo fees details:\n\n${JSON.stringify(condoFeeInfo, null, 2)}` - }) - } - }) - }) - }) -} +const sendCondoFeesToOwners = (req, res) => { + const propertyId = req.body.propertyId; + + pool.query(queries.getCondoOwnersEmailsByProperty, [propertyId], (error, ownersResults) => { + if (error) { + console.error('Error fetching condo owners:', error); + return res.status(500).send('Error fetching condo owners'); + } + + ownersResults.rows.forEach(owner => { + const condoId = owner.condoid; + const ownerEmail = owner.user_email; + + calculateTotalCondoFeeForEmail(condoId, (condoFeeInfo) => { + if (condoFeeInfo) { + sendEmail({ + to: ownerEmail, + subject: 'Your Condo Fees', + text: `Hello, here are your condo fees details:\n\n${JSON.stringify(condoFeeInfo, null, 2)}` + }); + } + }); + }); + + res.send('Condo fees sent to owners'); + }); + }; const calculateTotalCondoFeeForEmail = (condoId, callback) => { pool.query(queries.getCondoFeePerSqrft, [condoId], (error, feeResults) => { diff --git a/server/src/CondoUnit/routes.js b/server/src/CondoUnit/routes.js index d5e7de25..8749faf7 100644 --- a/server/src/CondoUnit/routes.js +++ b/server/src/CondoUnit/routes.js @@ -10,5 +10,6 @@ router.post('/', authenticateToken, controller.addCondoUnit) router.post('/:condoid', authenticateToken, controller.calculateTotalCondoFee) router.delete('/:condoid', authenticateToken, controller.removeCondoUnit) router.patch('/:condoid', authenticateToken, controller.updateCondoUnit) +router.post('/send-fees', authenticateToken, controller.sendCondoFeesToOwners) module.exports = router From 53932c1f27712d0d2695d7b118ddd94bf77e14fb Mon Sep 17 00:00:00 2001 From: ceyhuntopcu Date: Thu, 21 Mar 2024 13:38:03 -0400 Subject: [PATCH 4/4] linting fix --- server/src/CondoUnit/controller.js | 52 +++++++++++++++--------------- 1 file changed, 26 insertions(+), 26 deletions(-) diff --git a/server/src/CondoUnit/controller.js b/server/src/CondoUnit/controller.js index 95c76f76..ce1b9187 100644 --- a/server/src/CondoUnit/controller.js +++ b/server/src/CondoUnit/controller.js @@ -169,32 +169,32 @@ const calculateTotalCondoFee = (req, res) => { } const sendCondoFeesToOwners = (req, res) => { - const propertyId = req.body.propertyId; - - pool.query(queries.getCondoOwnersEmailsByProperty, [propertyId], (error, ownersResults) => { - if (error) { - console.error('Error fetching condo owners:', error); - return res.status(500).send('Error fetching condo owners'); - } - - ownersResults.rows.forEach(owner => { - const condoId = owner.condoid; - const ownerEmail = owner.user_email; - - calculateTotalCondoFeeForEmail(condoId, (condoFeeInfo) => { - if (condoFeeInfo) { - sendEmail({ - to: ownerEmail, - subject: 'Your Condo Fees', - text: `Hello, here are your condo fees details:\n\n${JSON.stringify(condoFeeInfo, null, 2)}` - }); - } - }); - }); - - res.send('Condo fees sent to owners'); - }); - }; + const propertyId = req.body.propertyId + + pool.query(queries.getCondoOwnersEmailsByProperty, [propertyId], (error, ownersResults) => { + if (error) { + console.error('Error fetching condo owners:', error) + return res.status(500).send('Error fetching condo owners') + } + + ownersResults.rows.forEach(owner => { + const condoId = owner.condoid + const ownerEmail = owner.user_email + + calculateTotalCondoFeeForEmail(condoId, (condoFeeInfo) => { + if (condoFeeInfo) { + sendEmail({ + to: ownerEmail, + subject: 'Your Condo Fees', + text: `Hello, here are your condo fees details:\n\n${JSON.stringify(condoFeeInfo, null, 2)}` + }) + } + }) + }) + + res.send('Condo fees sent to owners') + }) +} const calculateTotalCondoFeeForEmail = (condoId, callback) => { pool.query(queries.getCondoFeePerSqrft, [condoId], (error, feeResults) => {