Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
554e380
setup project folder structure for backend
Mohammad-Niyas Jun 8, 2026
dc9625a
feat: temporary commit on main for sync
Mohammad-Niyas Jun 9, 2026
877a3b5
add jwt, but athentication module still pending
Mohammad-Niyas Jun 9, 2026
c6ced1d
feat(auth): implement complete authentication system
Mohammad-Niyas Jun 23, 2026
e1a975e
Merge pull request #1 from Mohammad-Niyas/feat/auth
Mohammad-Niyas Jun 23, 2026
21ee921
implemented admin authentication
Mohammad-Niyas Jun 23, 2026
95cdd86
Merge pull request #2 from Mohammad-Niyas/feat/admin-auth
Mohammad-Niyas Jun 23, 2026
48936d4
implement ratelimiter using redis token bucket
Mohammad-Niyas Jun 27, 2026
86ba013
Merge pull request #3 from Mohammad-Niyas/feat/rate-limiter
Mohammad-Niyas Jun 27, 2026
369ad82
all domain models added
Mohammad-Niyas Jun 27, 2026
04f31ed
Merge pull request #4 from Mohammad-Niyas/feat/domain-models
Mohammad-Niyas Jun 27, 2026
20e0543
implemented aws s3 bucket
Mohammad-Niyas Jun 27, 2026
2260eef
added s3 bukcet
Mohammad-Niyas Jul 7, 2026
f498930
Merge pull request #5 from Mohammad-Niyas/feat/venue-crud
Mohammad-Niyas Jul 7, 2026
3f92f90
migrated venue and space models
Mohammad-Niyas Jul 8, 2026
077dcfd
Merge pull request #6 from Mohammad-Niyas/feat/venue-crud
Mohammad-Niyas Jul 8, 2026
e92d888
added venue-crud
Mohammad-Niyas Jul 9, 2026
6ed641a
bug fixed and venue toggel added
Mohammad-Niyas Jul 9, 2026
3d5cf0d
added ratelimiter and some bugs are fixed
Mohammad-Niyas Jul 9, 2026
d8776ce
Merge pull request #7 from Mohammad-Niyas/feat/venue-crud
Mohammad-Niyas Jul 9, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions back-end/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
# Block Environment Secrets
.env
*.env
back-end/.env
68 changes: 68 additions & 0 deletions back-end/cmd/api/main.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
package main

import (
"fmt"
"log"

"bookmyvenue/config"
"bookmyvenue/internal/domain"
"bookmyvenue/internal/handler"
"bookmyvenue/internal/repository"
"bookmyvenue/internal/router"
"bookmyvenue/internal/service"
"bookmyvenue/pkg/s3"
)

func main() {
cfg := config.LoadConfig()

db := config.ConnectDB(cfg)
rdb := config.ConnectRedis(cfg)

err := db.AutoMigrate(&domain.User{},
&domain.Admin{},
&domain.Venue{},
&domain.Space{},
&domain.Slot{},
&domain.Booking{},
&domain.Payment{},
&domain.PaymentAuditLog{},
&domain.Refund{},
&domain.CancellationPolicy{},
&domain.VenueEditDraft{},
&domain.OutboxEvent{},)

if err != nil {
log.Fatalf("Auto-migration failed: %v", err)
}

// S3 Client
s3Client, err := s3.NewS3Client(cfg)
if err != nil {
log.Printf("⚠️ S3 Client not initialized: %v (presigned URLs won't work)", err)
}

// User & Owner
userRepo := repository.NewUserRepository(db)
authService := service.NewAuthService(userRepo, cfg)
authHandler := handler.NewAuthHandler(authService)

// Admin
adminRepo := repository.NewAdminRepository(db)
adminAuthService := service.NewAdminAuthService(adminRepo, cfg)
adminAuthHandler := handler.NewAdminAuthHandler(adminAuthService)

// Venue
venueRepo := repository.NewVenueRepository(db)
spaceRepo := repository.NewSpaceRepository(db)
venueService := service.NewVenueService(venueRepo, spaceRepo, s3Client)
venueHandler := handler.NewVenueHandler(venueService)

r := router.SetupRouter(cfg,rdb, authHandler,adminAuthHandler,venueHandler)

port := fmt.Sprintf(":%s", cfg.ServerPort)
log.Printf("🚀 BookMyVenue server starting on port %s", cfg.ServerPort)
if err := r.Run(port); err != nil {
log.Fatalf("Server failed to start: %v", err)
}
}
135 changes: 135 additions & 0 deletions back-end/config/config.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
package config

import (
"log"
"os"
"strconv"

"github.com/joho/godotenv"
)

type Config struct {
// Database
DBHost string
DBPort string
DBUser string
DBPassword string
DBName string
DBSSLMode string
// Auth
JWTSecret string
AccessTokenExpiryMins int
RefreshTokenExpiryDays int
// Redis
RedisHost string
RedisPort string
RedisPassword string
RedisDB int
// AWS S3
AWSRegion string
AWSAccessKeyID string
AWSSecretAccessKey string
AWSS3Bucket string
// RabbitMQ
RabbitMQURL string
// Server
ServerPort string
}

func LoadConfig() *Config {

if err := godotenv.Load(); err != nil {
log.Println("No .env file found")
}

dbHost := os.Getenv("DB_HOST")
dbPort := os.Getenv("DB_PORT")
dbUser := os.Getenv("DB_USER")
dbPassword := os.Getenv("DB_PASSWORD")
dbName := os.Getenv("DB_NAME")
dbSSLMode := os.Getenv("DB_SSLMODE")
redisHost := getEnvOrDefault("REDIS_HOST", "localhost")
redisPort := getEnvOrDefault("REDIS_PORT", "6379")
redisPassword := os.Getenv("REDIS_PASSWORD")
redisDB := getEnvAsInt("REDIS_DB", 0)
awsRegion := getEnvOrDefault("AWS_REGION", "ap-south-1")
awsAccessKey := os.Getenv("AWS_ACCESS_KEY_ID")
awsSecretKey := os.Getenv("AWS_SECRET_ACCESS_KEY")
awsBucket := os.Getenv("AWS_S3_BUCKET")
rabbitURL := getEnvOrDefault("RABBITMQ_URL", "amqp://guest:guest@localhost:5672/")

if dbHost == "" {
dbHost = "localhost"
}
if dbPort == "" {
dbPort = "5432"
}
if dbUser == "" {
dbUser = "postgres"
}
if dbName == "" {
dbName = "bookmyvenue"
}
if dbSSLMode == "" {
dbSSLMode = "disable"
}

if dbPassword == "" {
log.Fatal("CRITICAL CONFIGURATION ERROR: DB_PASSWORD is not set in the environment variables!")
}

jwtSecret := os.Getenv("JWT_SECRET")
if jwtSecret == "" {
log.Fatal("CRITICAL: JWT_SECRET is not set!")
}

accessExpiry := getEnvAsInt("ACCESS_TOKEN_EXPIRY_MINS", 15)
refreshExpiry := getEnvAsInt("REFRESH_TOKEN_EXPIRY_DAYS", 30)

serverPort := getEnvOrDefault("SERVER_PORT", "8080")


return &Config{
DBHost: dbHost,
DBPort: dbPort,
DBUser: dbUser,
DBPassword: dbPassword,
DBName: dbName,
DBSSLMode: dbSSLMode,
JWTSecret: jwtSecret,
AccessTokenExpiryMins: accessExpiry,
RefreshTokenExpiryDays: refreshExpiry,
ServerPort: serverPort,
RedisHost: redisHost,
RedisPort: redisPort,
RedisPassword: redisPassword,
RedisDB: redisDB,
AWSRegion: awsRegion,
AWSAccessKeyID: awsAccessKey,
AWSSecretAccessKey: awsSecretKey,
AWSS3Bucket: awsBucket,
RabbitMQURL: rabbitURL,
}
}


func getEnvOrDefault(key, defaultVal string) string {
val := os.Getenv(key)
if val == "" {
return defaultVal
}
return val
}

func getEnvAsInt(key string, defaultVal int) int {
valStr := os.Getenv(key)
if valStr == "" {
return defaultVal
}
val, err := strconv.Atoi(valStr)
if err != nil {
log.Printf("WARNING: %s is not a valid integer, using default %d", key, defaultVal)
return defaultVal
}
return val
}
22 changes: 22 additions & 0 deletions back-end/config/db.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package config

import (
"fmt"
"log"

"gorm.io/driver/postgres"
"gorm.io/gorm"
)

func ConnectDB(cfg *Config) *gorm.DB {
dsn := fmt.Sprintf("host=%s user=%s password=%s dbname=%s port=%s sslmode=%s",
cfg.DBHost, cfg.DBUser, cfg.DBPassword, cfg.DBName, cfg.DBPort, cfg.DBSSLMode)

db, err := gorm.Open(postgres.Open(dsn), &gorm.Config{})
if err != nil {
log.Fatalf("CRITICAL DATABASE ERROR: Failed to connect to database: %v", err)
}

log.Println("Database connection successfully established!")
return db
}
26 changes: 26 additions & 0 deletions back-end/config/redis.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package config

import (
"context"
"fmt"
"log"
"time"

"github.com/redis/go-redis/v9"
)

func ConnectRedis(cfg *Config) *redis.Client {
rdb := redis.NewClient(&redis.Options{
Addr: fmt.Sprintf("%s:%s", cfg.RedisHost, cfg.RedisPort),
Password: cfg.RedisPassword,
DB: cfg.RedisDB,
})
ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
defer cancel()
_, err := rdb.Ping(ctx).Result()
if err != nil {
log.Fatalf("Failed to connect to Redis: %v", err)
}
log.Println("🔌 Connected to Redis successfully!")
return rdb
}
72 changes: 72 additions & 0 deletions back-end/go.mod
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
module bookmyvenue

go 1.25.5

require (
github.com/aws/aws-sdk-go-v2 v1.42.0
github.com/aws/aws-sdk-go-v2/config v1.32.25
github.com/aws/aws-sdk-go-v2/credentials v1.19.24
github.com/aws/aws-sdk-go-v2/service/s3 v1.104.0
github.com/gin-gonic/gin v1.12.0
github.com/golang-jwt/jwt/v5 v5.3.1
github.com/google/uuid v1.6.0
github.com/joho/godotenv v1.5.1
github.com/redis/go-redis/v9 v9.21.0
golang.org/x/crypto v0.48.0
gorm.io/driver/postgres v1.6.0
gorm.io/gorm v1.31.1
)

require (
github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.7.13 // indirect
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.18.29 // indirect
github.com/aws/aws-sdk-go-v2/internal/configsources v1.4.29 // indirect
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.7.29 // indirect
github.com/aws/aws-sdk-go-v2/internal/v4a v1.4.30 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.12 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.9.22 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.13.29 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.19.29 // indirect
github.com/aws/aws-sdk-go-v2/service/signin v1.2.0 // indirect
github.com/aws/aws-sdk-go-v2/service/sso v1.31.3 // indirect
github.com/aws/aws-sdk-go-v2/service/ssooidc v1.36.6 // indirect
github.com/aws/aws-sdk-go-v2/service/sts v1.43.3 // indirect
github.com/aws/smithy-go v1.27.1 // indirect
github.com/bytedance/gopkg v0.1.3 // indirect
github.com/bytedance/sonic v1.15.0 // indirect
github.com/bytedance/sonic/loader v0.5.0 // indirect
github.com/cespare/xxhash/v2 v2.3.0 // indirect
github.com/cloudwego/base64x v0.1.6 // indirect
github.com/gabriel-vasile/mimetype v1.4.12 // indirect
github.com/gin-contrib/sse v1.1.0 // indirect
github.com/go-playground/locales v0.14.1 // indirect
github.com/go-playground/universal-translator v0.18.1 // indirect
github.com/go-playground/validator/v10 v10.30.1 // indirect
github.com/goccy/go-json v0.10.5 // indirect
github.com/goccy/go-yaml v1.19.2 // indirect
github.com/jackc/pgpassfile v1.0.0 // indirect
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 // indirect
github.com/jackc/pgx/v5 v5.6.0 // indirect
github.com/jackc/puddle/v2 v2.2.2 // indirect
github.com/jinzhu/inflection v1.0.0 // indirect
github.com/jinzhu/now v1.1.5 // indirect
github.com/json-iterator/go v1.1.12 // indirect
github.com/klauspost/cpuid/v2 v2.3.0 // indirect
github.com/leodido/go-urn v1.4.0 // indirect
github.com/mattn/go-isatty v0.0.20 // indirect
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
github.com/modern-go/reflect2 v1.0.2 // indirect
github.com/pelletier/go-toml/v2 v2.2.4 // indirect
github.com/quic-go/qpack v0.6.0 // indirect
github.com/quic-go/quic-go v0.59.0 // indirect
github.com/twitchyliquid64/golang-asm v0.15.1 // indirect
github.com/ugorji/go/codec v1.3.1 // indirect
go.mongodb.org/mongo-driver/v2 v2.5.0 // indirect
go.uber.org/atomic v1.11.0 // indirect
golang.org/x/arch v0.22.0 // indirect
golang.org/x/net v0.51.0 // indirect
golang.org/x/sync v0.19.0 // indirect
golang.org/x/sys v0.41.0 // indirect
golang.org/x/text v0.34.0 // indirect
google.golang.org/protobuf v1.36.10 // indirect
)
Loading