- Add new `app` package to manage application initialization and lifecycle - Refactor `main.go` to use new application management approach - Implement graceful shutdown with context timeout and signal handling - Add dependency injection container initialization - Enhance logging with configurable log levels and structured logging - Update configuration loading and server initialization process - Modify Jitsi configuration in `.env` for custom deployment - Improve error handling and logging throughout application startup - Centralize application startup and shutdown logic in single package Introduces a more robust and flexible application management system with improved initialization, logging, and shutdown capabilities.
166 lines
5.8 KiB
Go
166 lines
5.8 KiB
Go
package services
|
|
|
|
import (
|
|
"time"
|
|
|
|
"attune-heart-therapy/internal/models"
|
|
|
|
"github.com/stripe/stripe-go/v76"
|
|
)
|
|
|
|
// UserService handles user-related operations
|
|
type UserService interface {
|
|
Register(req RegisterRequest) (*models.User, error)
|
|
Login(email, password string) (*models.User, string, error) // returns user and JWT token
|
|
GetProfile(userID uint) (*models.User, error)
|
|
UpdateProfile(userID uint, req UpdateProfileRequest) (*models.User, error)
|
|
CreateAdmin(req CreateAdminRequest) (*models.User, error)
|
|
}
|
|
|
|
// BookingService handles booking operations
|
|
type BookingService interface {
|
|
GetAvailableSlots(date time.Time) ([]models.Schedule, error)
|
|
CreateBooking(userID uint, req BookingRequest) (*models.Booking, error)
|
|
GetUserBookings(userID uint) ([]models.Booking, error)
|
|
CancelBooking(userID, bookingID uint) error
|
|
RescheduleBooking(userID, bookingID uint, newScheduleID uint) error
|
|
}
|
|
|
|
// PaymentService handles Stripe integration
|
|
type PaymentService interface {
|
|
CreatePaymentIntent(amount float64, currency string) (*stripe.PaymentIntent, error)
|
|
ConfirmPayment(paymentIntentID string) (*stripe.PaymentIntent, error)
|
|
HandleWebhook(payload []byte, signature string) error
|
|
}
|
|
|
|
// NotificationService handles email notifications
|
|
type NotificationService interface {
|
|
SendWelcomeEmail(user *models.User) error
|
|
SendPaymentNotification(user *models.User, booking *models.Booking, success bool) error
|
|
SendMeetingInfo(user *models.User, booking *models.Booking) error
|
|
SendReminder(user *models.User, booking *models.Booking) error
|
|
ScheduleReminder(bookingID uint, reminderTime time.Time) error
|
|
ProcessPendingNotifications() error
|
|
}
|
|
|
|
// JitsiService handles video conference integration
|
|
type JitsiService interface {
|
|
CreateMeeting(bookingID uint, scheduledAt time.Time) (*JitsiMeeting, error)
|
|
GetMeetingURL(roomID string) string
|
|
DeleteMeeting(roomID string) error
|
|
}
|
|
|
|
// AdminService handles admin dashboard operations
|
|
type AdminService interface {
|
|
GetDashboardStats() (*DashboardStats, error)
|
|
GetFinancialReports(startDate, endDate time.Time) (*FinancialReport, error)
|
|
CreateSchedule(req CreateScheduleRequest) (*models.Schedule, error)
|
|
UpdateSchedule(scheduleID uint, req UpdateScheduleRequest) (*models.Schedule, error)
|
|
GetAllUsers(limit, offset int) ([]models.User, int64, error)
|
|
GetAllBookings(limit, offset int) ([]models.Booking, int64, error)
|
|
}
|
|
|
|
// JobManagerService handles background job operations
|
|
type JobManagerService interface {
|
|
Start() error
|
|
Stop() error
|
|
IsRunning() bool
|
|
ScheduleRemindersForBooking(bookingID uint, userID uint, meetingTime time.Time) error
|
|
CancelRemindersForBooking(bookingID uint) error
|
|
}
|
|
|
|
// JitsiMeeting represents a Jitsi meeting
|
|
type JitsiMeeting struct {
|
|
RoomID string `json:"room_id"`
|
|
RoomURL string `json:"room_url"`
|
|
}
|
|
|
|
// Request/Response DTOs
|
|
type RegisterRequest struct {
|
|
FirstName string `json:"first_name" binding:"required"`
|
|
LastName string `json:"last_name" binding:"required"`
|
|
Email string `json:"email" binding:"required,email"`
|
|
Phone string `json:"phone"`
|
|
Location string `json:"location"`
|
|
DateOfBirth time.Time `json:"date_of_birth"`
|
|
Password string `json:"password" binding:"required,min=6"`
|
|
}
|
|
|
|
type UpdateProfileRequest struct {
|
|
FirstName string `json:"first_name"`
|
|
LastName string `json:"last_name"`
|
|
Phone string `json:"phone"`
|
|
Location string `json:"location"`
|
|
DateOfBirth time.Time `json:"date_of_birth"`
|
|
}
|
|
|
|
type BookingRequest struct {
|
|
ScheduleID uint `json:"schedule_id" binding:"required"`
|
|
Notes string `json:"notes"`
|
|
Amount float64 `json:"amount" binding:"required"`
|
|
}
|
|
|
|
// Payment DTOs
|
|
type CreatePaymentIntentRequest struct {
|
|
Amount float64 `json:"amount" binding:"required,gt=0"`
|
|
Currency string `json:"currency"`
|
|
}
|
|
|
|
type ConfirmPaymentRequest struct {
|
|
PaymentIntentID string `json:"payment_intent_id" binding:"required"`
|
|
}
|
|
|
|
// Admin DTOs
|
|
type DashboardStats struct {
|
|
TotalUsers int64 `json:"total_users"`
|
|
ActiveUsers int64 `json:"active_users"`
|
|
TotalBookings int64 `json:"total_bookings"`
|
|
UpcomingBookings int64 `json:"upcoming_bookings"`
|
|
CompletedBookings int64 `json:"completed_bookings"`
|
|
CancelledBookings int64 `json:"cancelled_bookings"`
|
|
TotalRevenue float64 `json:"total_revenue"`
|
|
MonthlyRevenue float64 `json:"monthly_revenue"`
|
|
}
|
|
|
|
type FinancialReport struct {
|
|
StartDate time.Time `json:"start_date"`
|
|
EndDate time.Time `json:"end_date"`
|
|
TotalRevenue float64 `json:"total_revenue"`
|
|
TotalBookings int64 `json:"total_bookings"`
|
|
AverageBooking float64 `json:"average_booking"`
|
|
DailyBreakdown []DailyFinancialSummary `json:"daily_breakdown"`
|
|
MonthlyBreakdown []MonthlyFinancialSummary `json:"monthly_breakdown"`
|
|
}
|
|
|
|
type DailyFinancialSummary struct {
|
|
Date time.Time `json:"date"`
|
|
Revenue float64 `json:"revenue"`
|
|
Bookings int64 `json:"bookings"`
|
|
}
|
|
|
|
type MonthlyFinancialSummary struct {
|
|
Month string `json:"month"`
|
|
Revenue float64 `json:"revenue"`
|
|
Bookings int64 `json:"bookings"`
|
|
}
|
|
|
|
type CreateScheduleRequest struct {
|
|
StartTime time.Time `json:"start_time" binding:"required"`
|
|
EndTime time.Time `json:"end_time" binding:"required"`
|
|
MaxBookings int `json:"max_bookings" binding:"required,min=1"`
|
|
}
|
|
|
|
type UpdateScheduleRequest struct {
|
|
StartTime *time.Time `json:"start_time"`
|
|
EndTime *time.Time `json:"end_time"`
|
|
MaxBookings *int `json:"max_bookings"`
|
|
IsAvailable *bool `json:"is_available"`
|
|
}
|
|
|
|
type CreateAdminRequest struct {
|
|
FirstName string `json:"first_name" validate:"required,min=2,max=100"`
|
|
LastName string `json:"last_name" validate:"required,min=2,max=100"`
|
|
Email string `json:"email" validate:"required,email"`
|
|
Password string `json:"password" validate:"required,min=8"`
|
|
}
|