Spaces:
Runtime error
Runtime error
Commit ·
f36e990
1
Parent(s): 7afeb3e
Deploy files from GitHub repository
Browse files- controllers/venue_controller.go +24 -0
- models/dto/user_dto.go +2 -0
- models/dto/venue_dto.go +4 -2
- models/entity/entity.go +1 -0
- repositories/venue_repository.go +20 -0
- router/venue_router.go +1 -0
- services/class_service.go +3 -1
- services/user_service.go +4 -0
- services/venue_service.go +57 -0
controllers/venue_controller.go
CHANGED
|
@@ -9,6 +9,7 @@ import (
|
|
| 9 |
)
|
| 10 |
|
| 11 |
type VenueController interface {
|
|
|
|
| 12 |
GetOwnerVenues(ctx *gin.Context)
|
| 13 |
GetVenueDetail(ctx *gin.Context)
|
| 14 |
CreateVenue(ctx *gin.Context)
|
|
@@ -22,6 +23,29 @@ func NewVenueController(venueService services.VenueService) VenueController {
|
|
| 22 |
return &venueController{venueService: venueService}
|
| 23 |
}
|
| 24 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 25 |
// GetOwnerVenues godoc
|
| 26 |
// @Summary Get owner's venues
|
| 27 |
// @Description Returns a paginated list of venues owned by the current user.
|
|
|
|
| 9 |
)
|
| 10 |
|
| 11 |
type VenueController interface {
|
| 12 |
+
GetAllVenues(ctx *gin.Context)
|
| 13 |
GetOwnerVenues(ctx *gin.Context)
|
| 14 |
GetVenueDetail(ctx *gin.Context)
|
| 15 |
CreateVenue(ctx *gin.Context)
|
|
|
|
| 23 |
return &venueController{venueService: venueService}
|
| 24 |
}
|
| 25 |
|
| 26 |
+
// GetAllVenues godoc
|
| 27 |
+
// @Summary Get all venues
|
| 28 |
+
// @Description Returns a paginated list of all venues.
|
| 29 |
+
// @Tags Venue
|
| 30 |
+
// @Produce json
|
| 31 |
+
// @Param page query int false "Page number (default: 1)"
|
| 32 |
+
// @Param limit query int false "Items per page (default: 10, max: 50)"
|
| 33 |
+
// @Success 200 {object} dto.VenueListResponse
|
| 34 |
+
// @Failure 500 {object} dto.ErrorResponse
|
| 35 |
+
// @Router /api/v1/venues [get]
|
| 36 |
+
func (c *venueController) GetAllVenues(ctx *gin.Context) {
|
| 37 |
+
page, _ := strconv.Atoi(ctx.DefaultQuery("page", "1"))
|
| 38 |
+
limit, _ := strconv.Atoi(ctx.DefaultQuery("limit", "10"))
|
| 39 |
+
|
| 40 |
+
result, err := c.venueService.GetAllVenues(ctx.Request.Context(), page, limit)
|
| 41 |
+
if err != nil {
|
| 42 |
+
ResponseJSON(ctx, "", result, err)
|
| 43 |
+
return
|
| 44 |
+
}
|
| 45 |
+
|
| 46 |
+
ResponseJSON(ctx, "", result, nil)
|
| 47 |
+
}
|
| 48 |
+
|
| 49 |
// GetOwnerVenues godoc
|
| 50 |
// @Summary Get owner's venues
|
| 51 |
// @Description Returns a paginated list of venues owned by the current user.
|
models/dto/user_dto.go
CHANGED
|
@@ -18,6 +18,7 @@ type UpdateAboutYouRequest struct {
|
|
| 18 |
Province *string `json:"province"`
|
| 19 |
City *string `json:"city"`
|
| 20 |
DanceLevel *string `json:"dance_level"`
|
|
|
|
| 21 |
Interest []string `json:"interest"`
|
| 22 |
OtherInterest *string `json:"other_interest"`
|
| 23 |
Description *string `json:"description"`
|
|
@@ -47,6 +48,7 @@ type UserProfileResponse struct {
|
|
| 47 |
|
| 48 |
Gender *string `json:"gender"`
|
| 49 |
DanceLevel *string `json:"dance_level"`
|
|
|
|
| 50 |
Province *string `json:"province"`
|
| 51 |
City *string `json:"city"`
|
| 52 |
Description *string `json:"description"`
|
|
|
|
| 18 |
Province *string `json:"province"`
|
| 19 |
City *string `json:"city"`
|
| 20 |
DanceLevel *string `json:"dance_level"`
|
| 21 |
+
Rank *string `json:"rank"`
|
| 22 |
Interest []string `json:"interest"`
|
| 23 |
OtherInterest *string `json:"other_interest"`
|
| 24 |
Description *string `json:"description"`
|
|
|
|
| 48 |
|
| 49 |
Gender *string `json:"gender"`
|
| 50 |
DanceLevel *string `json:"dance_level"`
|
| 51 |
+
Rank *string `json:"rank"`
|
| 52 |
Province *string `json:"province"`
|
| 53 |
City *string `json:"city"`
|
| 54 |
Description *string `json:"description"`
|
models/dto/venue_dto.go
CHANGED
|
@@ -47,8 +47,10 @@ type VenueDetailOwner struct {
|
|
| 47 |
}
|
| 48 |
|
| 49 |
type VenueDetailMap struct {
|
| 50 |
-
VenueName string
|
| 51 |
-
Address string
|
|
|
|
|
|
|
| 52 |
}
|
| 53 |
|
| 54 |
type VenueDetailRatings struct {
|
|
|
|
| 47 |
}
|
| 48 |
|
| 49 |
type VenueDetailMap struct {
|
| 50 |
+
VenueName string `json:"venue_name"`
|
| 51 |
+
Address string `json:"address"`
|
| 52 |
+
Latitude float64 `json:"latitude"`
|
| 53 |
+
Longitude float64 `json:"longitude"`
|
| 54 |
}
|
| 55 |
|
| 56 |
type VenueDetailRatings struct {
|
models/entity/entity.go
CHANGED
|
@@ -22,6 +22,7 @@ type User struct {
|
|
| 22 |
Nickname string `json:"nickname,omitempty"`
|
| 23 |
Gender *string `json:"gender,omitempty"`
|
| 24 |
DanceLevel *string `json:"dance_level,omitempty"`
|
|
|
|
| 25 |
Province *string `json:"province,omitempty"`
|
| 26 |
City *string `json:"city,omitempty"`
|
| 27 |
Description *string `gorm:"type:text" json:"description,omitempty"`
|
|
|
|
| 22 |
Nickname string `json:"nickname,omitempty"`
|
| 23 |
Gender *string `json:"gender,omitempty"`
|
| 24 |
DanceLevel *string `json:"dance_level,omitempty"`
|
| 25 |
+
Rank *string `json:"rank,omitempty"`
|
| 26 |
Province *string `json:"province,omitempty"`
|
| 27 |
City *string `json:"city,omitempty"`
|
| 28 |
Description *string `gorm:"type:text" json:"description,omitempty"`
|
repositories/venue_repository.go
CHANGED
|
@@ -9,6 +9,7 @@ import (
|
|
| 9 |
)
|
| 10 |
|
| 11 |
type VenueRepository interface {
|
|
|
|
| 12 |
GetVenuesByOwnerUserID(ctx context.Context, userID string, limit, offset int) ([]entity.Venue, int64, error)
|
| 13 |
GetVenueByID(ctx context.Context, id string) (entity.Venue, error)
|
| 14 |
GetVenueOwnerByUserID(ctx context.Context, userID string) (*entity.VenueOwner, error)
|
|
@@ -25,6 +26,25 @@ func NewVenueRepository(db *gorm.DB) VenueRepository {
|
|
| 25 |
return &venueRepository{db}
|
| 26 |
}
|
| 27 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 28 |
func (r *venueRepository) GetVenuesByOwnerUserID(ctx context.Context, userID string, limit, offset int) ([]entity.Venue, int64, error) {
|
| 29 |
var venues []entity.Venue
|
| 30 |
var total int64
|
|
|
|
| 9 |
)
|
| 10 |
|
| 11 |
type VenueRepository interface {
|
| 12 |
+
GetVenues(ctx context.Context, limit, offset int) ([]entity.Venue, int64, error)
|
| 13 |
GetVenuesByOwnerUserID(ctx context.Context, userID string, limit, offset int) ([]entity.Venue, int64, error)
|
| 14 |
GetVenueByID(ctx context.Context, id string) (entity.Venue, error)
|
| 15 |
GetVenueOwnerByUserID(ctx context.Context, userID string) (*entity.VenueOwner, error)
|
|
|
|
| 26 |
return &venueRepository{db}
|
| 27 |
}
|
| 28 |
|
| 29 |
+
func (r *venueRepository) GetVenues(ctx context.Context, limit, offset int) ([]entity.Venue, int64, error) {
|
| 30 |
+
var venues []entity.Venue
|
| 31 |
+
var total int64
|
| 32 |
+
|
| 33 |
+
base := r.db.WithContext(ctx).Model(&entity.Venue{})
|
| 34 |
+
|
| 35 |
+
if err := base.Count(&total).Error; err != nil {
|
| 36 |
+
return nil, 0, err
|
| 37 |
+
}
|
| 38 |
+
|
| 39 |
+
err := base.
|
| 40 |
+
Preload("Owner").
|
| 41 |
+
Limit(limit).
|
| 42 |
+
Offset(offset).
|
| 43 |
+
Find(&venues).Error
|
| 44 |
+
|
| 45 |
+
return venues, total, err
|
| 46 |
+
}
|
| 47 |
+
|
| 48 |
func (r *venueRepository) GetVenuesByOwnerUserID(ctx context.Context, userID string, limit, offset int) ([]entity.Venue, int64, error) {
|
| 49 |
var venues []entity.Venue
|
| 50 |
var total int64
|
router/venue_router.go
CHANGED
|
@@ -10,6 +10,7 @@ func VenueRouterSetup(rg *gin.Engine, ctrl provider.ControllerProvider, mw provi
|
|
| 10 |
v1Group.Use(mw.ProvideAuthenticationMiddleware().VerifyAccount)
|
| 11 |
|
| 12 |
venueController := ctrl.ProvideVenueController()
|
|
|
|
| 13 |
v1Group.POST("", venueController.CreateVenue)
|
| 14 |
v1Group.GET("/me", venueController.GetOwnerVenues)
|
| 15 |
v1Group.GET("/:id", venueController.GetVenueDetail)
|
|
|
|
| 10 |
v1Group.Use(mw.ProvideAuthenticationMiddleware().VerifyAccount)
|
| 11 |
|
| 12 |
venueController := ctrl.ProvideVenueController()
|
| 13 |
+
v1Group.GET("", venueController.GetAllVenues)
|
| 14 |
v1Group.POST("", venueController.CreateVenue)
|
| 15 |
v1Group.GET("/me", venueController.GetOwnerVenues)
|
| 16 |
v1Group.GET("/:id", venueController.GetVenueDetail)
|
services/class_service.go
CHANGED
|
@@ -120,7 +120,9 @@ func (s *classService) buildInstructor(instructor entity.Instructor) dto.ClassIn
|
|
| 120 |
Subtitle: repositories.InstructorDefaultSubtitle,
|
| 121 |
IsMessageEnabled: true,
|
| 122 |
}
|
| 123 |
-
if instructor.Rank != "" {
|
|
|
|
|
|
|
| 124 |
info.Title = fmt.Sprintf("%s - Dance Instructor", instructor.Rank)
|
| 125 |
}
|
| 126 |
if instructor.User.ProfileMedia != nil {
|
|
|
|
| 120 |
Subtitle: repositories.InstructorDefaultSubtitle,
|
| 121 |
IsMessageEnabled: true,
|
| 122 |
}
|
| 123 |
+
if instructor.User.Rank != nil && *instructor.User.Rank != "" {
|
| 124 |
+
info.Title = fmt.Sprintf("%s - Dance Instructor", *instructor.User.Rank)
|
| 125 |
+
} else if instructor.Rank != "" {
|
| 126 |
info.Title = fmt.Sprintf("%s - Dance Instructor", instructor.Rank)
|
| 127 |
}
|
| 128 |
if instructor.User.ProfileMedia != nil {
|
services/user_service.go
CHANGED
|
@@ -149,6 +149,7 @@ func mapUserToProfileResponse(user entity.User) dto.UserProfileResponse {
|
|
| 149 |
Age: user.Age,
|
| 150 |
Gender: user.Gender,
|
| 151 |
DanceLevel: user.DanceLevel,
|
|
|
|
| 152 |
Province: user.Province,
|
| 153 |
City: user.City,
|
| 154 |
Description: user.Description,
|
|
@@ -198,6 +199,9 @@ func (s *userService) UpdateAboutYou(ctx context.Context, id string, req dto.Upd
|
|
| 198 |
if req.DanceLevel != nil {
|
| 199 |
user.DanceLevel = req.DanceLevel
|
| 200 |
}
|
|
|
|
|
|
|
|
|
|
| 201 |
if req.Province != nil {
|
| 202 |
user.Province = req.Province
|
| 203 |
}
|
|
|
|
| 149 |
Age: user.Age,
|
| 150 |
Gender: user.Gender,
|
| 151 |
DanceLevel: user.DanceLevel,
|
| 152 |
+
Rank: user.Rank,
|
| 153 |
Province: user.Province,
|
| 154 |
City: user.City,
|
| 155 |
Description: user.Description,
|
|
|
|
| 199 |
if req.DanceLevel != nil {
|
| 200 |
user.DanceLevel = req.DanceLevel
|
| 201 |
}
|
| 202 |
+
if req.Rank != nil {
|
| 203 |
+
user.Rank = req.Rank
|
| 204 |
+
}
|
| 205 |
if req.Province != nil {
|
| 206 |
user.Province = req.Province
|
| 207 |
}
|
services/venue_service.go
CHANGED
|
@@ -14,6 +14,7 @@ import (
|
|
| 14 |
)
|
| 15 |
|
| 16 |
type VenueService interface {
|
|
|
|
| 17 |
GetOwnerVenues(ctx context.Context, userID string, page, limit int) (dto.VenueListResponse, error)
|
| 18 |
GetVenueDetail(ctx context.Context, id string) (dto.VenueDetailResponse, error)
|
| 19 |
CreateVenue(ctx context.Context, userID string, req dto.CreateVenueRequest) (dto.VenueDetailResponse, error)
|
|
@@ -130,6 +131,8 @@ func (s *venueService) GetVenueDetail(ctx context.Context, id string) (dto.Venue
|
|
| 130 |
Map: dto.VenueDetailMap{
|
| 131 |
VenueName: venue.Name,
|
| 132 |
Address: venue.Address,
|
|
|
|
|
|
|
| 133 |
},
|
| 134 |
Facilities: facilitiesResponse,
|
| 135 |
ExtraFacilities: extraFacilities,
|
|
@@ -143,6 +146,60 @@ func (s *venueService) GetVenueDetail(ctx context.Context, id string) (dto.Venue
|
|
| 143 |
}, nil
|
| 144 |
}
|
| 145 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 146 |
func (s *venueService) GetOwnerVenues(ctx context.Context, userID string, page, limit int) (dto.VenueListResponse, error) {
|
| 147 |
if limit <= 0 || limit > 50 {
|
| 148 |
limit = 10
|
|
|
|
| 14 |
)
|
| 15 |
|
| 16 |
type VenueService interface {
|
| 17 |
+
GetAllVenues(ctx context.Context, page, limit int) (dto.VenueListResponse, error)
|
| 18 |
GetOwnerVenues(ctx context.Context, userID string, page, limit int) (dto.VenueListResponse, error)
|
| 19 |
GetVenueDetail(ctx context.Context, id string) (dto.VenueDetailResponse, error)
|
| 20 |
CreateVenue(ctx context.Context, userID string, req dto.CreateVenueRequest) (dto.VenueDetailResponse, error)
|
|
|
|
| 131 |
Map: dto.VenueDetailMap{
|
| 132 |
VenueName: venue.Name,
|
| 133 |
Address: venue.Address,
|
| 134 |
+
Latitude: venue.Latitude,
|
| 135 |
+
Longitude: venue.Longitude,
|
| 136 |
},
|
| 137 |
Facilities: facilitiesResponse,
|
| 138 |
ExtraFacilities: extraFacilities,
|
|
|
|
| 146 |
}, nil
|
| 147 |
}
|
| 148 |
|
| 149 |
+
func (s *venueService) GetAllVenues(ctx context.Context, page, limit int) (dto.VenueListResponse, error) {
|
| 150 |
+
if limit <= 0 || limit > 50 {
|
| 151 |
+
limit = 10
|
| 152 |
+
}
|
| 153 |
+
if page <= 0 {
|
| 154 |
+
page = 1
|
| 155 |
+
}
|
| 156 |
+
offset := (page - 1) * limit
|
| 157 |
+
|
| 158 |
+
venues, total, err := s.venueRepo.GetVenues(ctx, limit, offset)
|
| 159 |
+
if err != nil {
|
| 160 |
+
return dto.VenueListResponse{}, err
|
| 161 |
+
}
|
| 162 |
+
|
| 163 |
+
results := make([]dto.VenueResponse, 0, len(venues))
|
| 164 |
+
for _, v := range venues {
|
| 165 |
+
status := "Active"
|
| 166 |
+
if v.VerificationStatus != "" {
|
| 167 |
+
status = v.VerificationStatus
|
| 168 |
+
}
|
| 169 |
+
|
| 170 |
+
location := fmt.Sprintf("%s, %s", v.City, v.Province)
|
| 171 |
+
if v.City == "" && v.Province == "" {
|
| 172 |
+
location = "Unknown Location"
|
| 173 |
+
}
|
| 174 |
+
|
| 175 |
+
results = append(results, dto.VenueResponse{
|
| 176 |
+
ID: v.ID,
|
| 177 |
+
Name: v.Name,
|
| 178 |
+
Price: fmt.Sprintf("Rp%.0f / hour", v.MinimumConsumption),
|
| 179 |
+
Status: status,
|
| 180 |
+
Rooms: fmt.Sprintf("%d Person Capacity", v.Capacity),
|
| 181 |
+
Location: location,
|
| 182 |
+
Image: s.extractThumbnailFromVenueMedia(v.VenueMedia),
|
| 183 |
+
})
|
| 184 |
+
}
|
| 185 |
+
|
| 186 |
+
totalPages := int(total) / limit
|
| 187 |
+
if int(total)%limit != 0 {
|
| 188 |
+
totalPages++
|
| 189 |
+
}
|
| 190 |
+
|
| 191 |
+
return dto.VenueListResponse{
|
| 192 |
+
Venues: results,
|
| 193 |
+
Pagination: dto.Pagination{
|
| 194 |
+
Page: page,
|
| 195 |
+
Limit: limit,
|
| 196 |
+
TotalItems: int(total),
|
| 197 |
+
TotalPages: totalPages,
|
| 198 |
+
HasNextPage: page < totalPages,
|
| 199 |
+
},
|
| 200 |
+
}, nil
|
| 201 |
+
}
|
| 202 |
+
|
| 203 |
func (s *venueService) GetOwnerVenues(ctx context.Context, userID string, page, limit int) (dto.VenueListResponse, error) {
|
| 204 |
if limit <= 0 || limit > 50 {
|
| 205 |
limit = 10
|