go.charczuk.com@v0.0.0-20240327042549-bc490516bd1a/projects/chirp/pkg/controller/profile.go (about)

     1  /*
     2  
     3  Copyright (c) 2023 - Present. Will Charczuk. All rights reserved.
     4  Use of this source code is governed by a MIT license that can be found in the LICENSE file at the root of the repository.
     5  
     6  */
     7  
     8  package controller
     9  
    10  import (
    11  	"fmt"
    12  	"net/http"
    13  
    14  	"go.charczuk.com/projects/chirp/pkg/config"
    15  	"go.charczuk.com/projects/chirp/pkg/model"
    16  	"go.charczuk.com/sdk/apputil"
    17  	"go.charczuk.com/sdk/uuid"
    18  	"go.charczuk.com/sdk/web"
    19  )
    20  
    21  type Profile struct {
    22  	apputil.BaseController
    23  
    24  	Config config.Config
    25  	Model  model.Manager
    26  }
    27  
    28  func (p Profile) Register(app *web.App) {
    29  	app.Get("/profile", web.NestMiddleware(p.profile, web.SessionRequired))
    30  	app.Get("/profile/:user", web.NestMiddleware(p.profile, web.SessionRequired))
    31  	app.Get("/profile/:user/:tab", web.NestMiddleware(p.profile, web.SessionRequired))
    32  	app.Post("/profile.follow", web.NestMiddleware(p.profileFollow, web.SessionRequired))
    33  	app.Post("/profile.unfollow", web.NestMiddleware(p.profileUnfollow, web.SessionRequired))
    34  }
    35  
    36  type profileViewModel struct {
    37  	Tab    string
    38  	User   model.UserFull
    39  	Chirps []model.ChirpFull
    40  }
    41  
    42  func (p Profile) profile(r web.Context) web.Result {
    43  	sessionUserID := p.GetUserID(r)
    44  	var user model.UserFull
    45  	var err error
    46  	var found bool
    47  	if routeUsername, _ := web.RouteValue[string](r, "user"); routeUsername != "" {
    48  		user, found, err = p.Model.UserByUsername(r, sessionUserID, routeUsername)
    49  		if err != nil {
    50  			return r.Views().InternalError(err)
    51  		}
    52  		if !found {
    53  			return r.Views().NotFound()
    54  		}
    55  	} else {
    56  		user, found, err = p.Model.User(r, sessionUserID, sessionUserID)
    57  		if err != nil {
    58  			return r.Views().InternalError(err)
    59  		}
    60  		if !found {
    61  			return r.Views().NotFound()
    62  		}
    63  	}
    64  
    65  	var after *uuid.UUID
    66  	if queryAfter, _ := web.QueryValue[uuid.UUID](r, "after"); !queryAfter.IsZero() {
    67  		after = &queryAfter
    68  	}
    69  
    70  	tab := "posts"
    71  	if routeTab, _ := web.RouteValue[string](r, "tab"); routeTab != "" {
    72  		tab = routeTab
    73  	}
    74  
    75  	var chirps []model.ChirpFull
    76  	switch tab {
    77  	case "posts":
    78  		chirps, err = p.Model.ProfilePosts(r, sessionUserID, user.ID, DEFAULT_HOME_FEED_LENGTH, after)
    79  	case "replies":
    80  		chirps, err = p.Model.ProfileReplies(r, sessionUserID, user.ID, DEFAULT_HOME_FEED_LENGTH, after)
    81  	case "likes":
    82  		chirps, err = p.Model.ProfileLikes(r, sessionUserID, user.ID, DEFAULT_HOME_FEED_LENGTH, after)
    83  	default:
    84  		return r.Views().BadRequest(fmt.Errorf("invalid profile tab %q", tab))
    85  	}
    86  	if err != nil {
    87  		return r.Views().InternalError(err)
    88  	}
    89  	if err != nil {
    90  		return r.Views().InternalError(err)
    91  	}
    92  	return r.Views().View("profile", profileViewModel{
    93  		Tab:    tab,
    94  		User:   user,
    95  		Chirps: chirps,
    96  	})
    97  }
    98  
    99  func (p Profile) profileFollow(r web.Context) web.Result {
   100  	sessionUserID := p.GetUserID(r)
   101  	targetUserID, err := web.FormValue[uuid.UUID](r, "id")
   102  	if err != nil {
   103  		return r.Views().BadRequest(err)
   104  	}
   105  	targetUser, found, err := p.Model.User(r, sessionUserID, targetUserID)
   106  	if err != nil {
   107  		return r.Views().InternalError(err)
   108  	}
   109  	if !found {
   110  		return r.Views().NotFound()
   111  	}
   112  
   113  	if err = p.Model.Follow(r, sessionUserID, targetUserID); err != nil {
   114  		return r.Views().InternalError(err)
   115  	}
   116  	return web.RedirectWithMethodf(http.MethodGet, "/profile/%s", targetUser.Email)
   117  }
   118  
   119  func (p Profile) profileUnfollow(r web.Context) web.Result {
   120  	sessionUserID := p.GetUserID(r)
   121  	targetUserID, err := web.FormValue[uuid.UUID](r, "id")
   122  	if err != nil {
   123  		return r.Views().BadRequest(err)
   124  	}
   125  	_, found, err := p.Model.User(r, sessionUserID, targetUserID)
   126  	if err != nil {
   127  		return r.Views().InternalError(err)
   128  	}
   129  	if !found {
   130  		return r.Views().NotFound()
   131  	}
   132  	if err = p.Model.Unfollow(r, sessionUserID, targetUserID); err != nil {
   133  		return r.Views().InternalError(err)
   134  	}
   135  	return web.RedirectWithMethodf(http.MethodGet, "/home")
   136  }