Skip to content

Commit

Permalink
Add #204 Align onboard APIs
Browse files Browse the repository at this point in the history
  • Loading branch information
albinpa committed Oct 11, 2023
1 parent ae5a7d9 commit d23cbb3
Show file tree
Hide file tree
Showing 15 changed files with 242 additions and 97 deletions.
22 changes: 22 additions & 0 deletions src/common/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,11 @@ type status struct {
Message string
}

type statusv2 struct {
ErrorCode int `json:"errorCode"`
ErrorDescription string `json:"errorDescription"`
}

// OrgRole Organization role definition
type OrgRole struct {
ID int
Expand Down Expand Up @@ -133,6 +138,23 @@ func HandleError(w http.ResponseWriter, code int, message string, err error) {
w.Write(response)
}

func HandleErrorV2(w http.ResponseWriter, code int, message string, err error) {
s := statusv2{
ErrorCode: code,
ErrorDescription: message,
}
response, _ := json.Marshal(s)

pc, fn, line, _ := runtime.Caller(1)

log.Printf("%v with err:%v in %s[%s:%d]", message, err,
filepath.Base(runtime.FuncForPC(pc).Name()), filepath.Base(fn), line)

w.WriteHeader(code)
w.Header().Set("Content-Type", "application/json")
w.Write(response)
}

// GetRandomString Generate a random alpha numeric string of requested length
func GetRandomString(length int) string {
rand.Seed(time.Now().UnixNano())
Expand Down
32 changes: 29 additions & 3 deletions src/handlerv2/getorganizationbyid_handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,20 +8,46 @@ import (
"github.com/bb-consent/api/src/common"
"github.com/bb-consent/api/src/config"
"github.com/bb-consent/api/src/org"
"go.mongodb.org/mongo-driver/bson/primitive"
)

type organizationResp struct {
ID primitive.ObjectID `bson:"_id,omitempty" json:"id"`
Name string `json:"name"`
Location string `json:"location"`
PolicyURL string `json:"policyUrl"`
CoverImageID string `json:"coverImageId"`
CoverImageURL string `json:"coverImageUrl"`
LogoImageID string `json:"logoImageId"`
LogoImageURL string `json:"logoImageUrl"`
}

type getOrgResp struct {
Organization organizationResp `json:"organization"`
}

// GetOrganizationByID Gets a single organization by given id
func GetOrganizationByID(w http.ResponseWriter, r *http.Request) {
organizationID := r.Header.Get(config.OrganizationId)
o, err := org.Get(organizationID)

if err != nil {
m := fmt.Sprintf("Failed to get organization by ID :%v", organizationID)
common.HandleError(w, http.StatusNotFound, m, err)
common.HandleErrorV2(w, http.StatusNotFound, m, err)
return
}

oResp := organizationResp{
ID: o.ID,
Name: o.Name,
Location: o.Location,
PolicyURL: o.PolicyURL,
CoverImageID: o.CoverImageID,
CoverImageURL: o.CoverImageURL,
LogoImageID: o.LogoImageID,
LogoImageURL: o.LogoImageURL,
}

w.Header().Set(config.ContentTypeHeader, config.ContentTypeJSON)
response, _ := json.Marshal(organization{o})
response, _ := json.Marshal(getOrgResp{oResp})
w.Write(response)
}
13 changes: 10 additions & 3 deletions src/handlerv2/gettoken_handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@ import (
)

type tokenReq struct {
RefreshToken string `valid:"required"`
ClientID string `valid:"required"`
RefreshToken string `valid:"required" json:"refreshToken"`
ClientID string `valid:"required" json:"clientId"`
}

// GetToken return access token when refresh token is given
Expand Down Expand Up @@ -67,7 +67,14 @@ func GetToken(w http.ResponseWriter, r *http.Request) {

var tok iamToken
json.Unmarshal(body, &tok)
response, _ := json.Marshal(tok)
tResp := tokenResp{
AccessToken: tok.AccessToken,
ExpiresIn: tok.ExpiresIn,
RefreshExpiresIn: tok.RefreshExpiresIn,
RefreshToken: tok.RefreshToken,
TokenType: tok.TokenType,
}
response, _ := json.Marshal(tResp)
w.WriteHeader(resp.StatusCode)
w.Header().Set(config.ContentTypeHeader, config.ContentTypeJSON)
w.Write(response)
Expand Down
29 changes: 19 additions & 10 deletions src/handlerv2/loginadminuser_handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,16 @@ import (
)

type loginReq struct {
Username string `valid:"required,email"`
Password string `valid:"required"`
Username string `json:"username" valid:"required,email"`
Password string `json:"password" valid:"required"`
}

type loginResp struct {
User user.User
Token iamToken
AccessToken string `json:"accessToken"`
ExpiresIn int `json:"expiresIn"`
RefreshExpiresIn int `json:"refreshExpiresIn"`
RefreshToken string `json:"refreshToken"`
TokenType string `json:"tokenType"`
}

// LoginAdminUser Implements the admin users login
Expand All @@ -39,7 +42,7 @@ func LoginAdminUser(w http.ResponseWriter, r *http.Request) {

if !valid {
log.Printf("Invalid request params for authentication")
common.HandleError(w, http.StatusBadRequest, err.Error(), err)
common.HandleErrorV2(w, http.StatusBadRequest, err.Error(), err)
return
}

Expand All @@ -53,33 +56,39 @@ func LoginAdminUser(w http.ResponseWriter, r *http.Request) {
return
}
m := fmt.Sprintf("Failed to get token for user:%v", lReq.Username)
common.HandleError(w, status, m, err)
common.HandleErrorV2(w, status, m, err)
return
}
accessToken, err := token.ParseToken(t.AccessToken)
if err != nil {
m := fmt.Sprintf("Failed to parse token for user:%v", lReq.Username)
common.HandleError(w, status, m, err)
common.HandleErrorV2(w, status, m, err)
return
}

u, err := user.GetByIamID(accessToken.IamID)
if err != nil {
m := fmt.Sprintf("User: %v does not exist", lReq.Username)
common.HandleError(w, http.StatusUnauthorized, m, err)
common.HandleErrorV2(w, http.StatusUnauthorized, m, err)
return
}

if len(u.Roles) == 0 {
//Normal user can not login with this API.
m := fmt.Sprintf("Non Admin User: %v tried admin login", lReq.Username)
common.HandleError(w, http.StatusForbidden, m, err)
common.HandleErrorV2(w, http.StatusForbidden, m, err)
return
}

actionLog := fmt.Sprintf("%v logged in", u.Email)
actionlog.LogOrgSecurityCalls(u.ID.Hex(), u.Email, u.Roles[0].OrgID, actionLog)
lResp := loginResp{u, t}
lResp := loginResp{
AccessToken: t.AccessToken,
ExpiresIn: t.ExpiresIn,
RefreshExpiresIn: t.RefreshExpiresIn,
RefreshToken: t.RefreshToken,
TokenType: t.TokenType,
}
resp, _ := json.Marshal(lResp)
w.WriteHeader(http.StatusOK)
w.Header().Set(config.ContentTypeHeader, config.ContentTypeJSON)
Expand Down
45 changes: 33 additions & 12 deletions src/handlerv2/loginuser_handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,23 @@ import (
"github.com/asaskevich/govalidator"
"github.com/bb-consent/api/src/common"
"github.com/bb-consent/api/src/config"
"github.com/bb-consent/api/src/token"
"github.com/bb-consent/api/src/user"
)

type tokenResp struct {
AccessToken string `json:"accessToken"`
ExpiresIn int `json:"expiresIn"`
RefreshExpiresIn int `json:"refreshExpiresIn"`
RefreshToken string `json:"refreshToken"`
TokenType string `json:"tokenType"`
}

type userLoginResp struct {
Individual user.UserV2 `json:"individual"`
Token tokenResp `json:"token"`
}

// LoginUser Implements the user login
func LoginUser(w http.ResponseWriter, r *http.Request) {
var lReq loginReq
Expand All @@ -29,7 +43,7 @@ func LoginUser(w http.ResponseWriter, r *http.Request) {

if !valid {
log.Printf("Invalid request params for authentication")
common.HandleError(w, http.StatusBadRequest, err.Error(), err)
common.HandleErrorV2(w, http.StatusBadRequest, err.Error(), err)
return
}

Expand All @@ -43,27 +57,34 @@ func LoginUser(w http.ResponseWriter, r *http.Request) {
return
}
m := fmt.Sprintf("Failed to get token for user:%v", lReq.Username)
common.HandleError(w, status, m, err)
common.HandleErrorV2(w, status, m, err)
return
}
sanitizedUserName := common.Sanitize(lReq.Username)

//TODO: Remove me when the auth server is per dev environment
u, err := user.GetByEmail(sanitizedUserName)
accessToken, err := token.ParseToken(t.AccessToken)
if err != nil {
m := fmt.Sprintf("Login failed for non existant user:%v", lReq.Username)
common.HandleError(w, http.StatusUnauthorized, m, err)
m := fmt.Sprintf("Failed to parse token for user:%v", lReq.Username)
common.HandleErrorV2(w, status, m, err)
return
}

if len(u.Roles) > 0 {
m := fmt.Sprintf("Login not allowed for admin users:%v", lReq.Username)
common.HandleError(w, http.StatusUnauthorized, m, err)
u, err := user.GetByIamIDV2(accessToken.IamID)
if err != nil {
m := fmt.Sprintf("User: %v does not exist", lReq.Username)
common.HandleErrorV2(w, status, m, err)
return
}
tResp := tokenResp{
AccessToken: t.AccessToken,
ExpiresIn: t.ExpiresIn,
RefreshExpiresIn: t.RefreshExpiresIn,
RefreshToken: t.RefreshToken,
TokenType: t.TokenType,
}

resp, _ := json.Marshal(t)
lResp := userLoginResp{u, tResp}
resp, _ := json.Marshal(lResp)
w.WriteHeader(http.StatusOK)
w.Header().Set(config.ContentTypeHeader, config.ContentTypeJSON)
w.Write(resp)

}
15 changes: 6 additions & 9 deletions src/handlerv2/updateorganization_handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,10 +14,10 @@ import (
)

type orgUpdateReq struct {
Name string
Location string
Description string
PolicyURL string
Name string `json:"name"`
Location string `json:"location"`
Description string `json:"description"`
PolicyURL string `json:"policyUrl"`
}

// UpdateOrganization Updates an organization
Expand All @@ -33,7 +33,7 @@ func UpdateOrganization(w http.ResponseWriter, r *http.Request) {
o, err := org.Get(organizationID)
if err != nil {
m := fmt.Sprintf("Failed to get organization: %v", organizationID)
common.HandleError(w, http.StatusInternalServerError, m, err)
common.HandleErrorV2(w, http.StatusInternalServerError, m, err)
return
}

Expand All @@ -53,12 +53,9 @@ func UpdateOrganization(w http.ResponseWriter, r *http.Request) {
orgResp, err := org.Update(o)
if err != nil {
m := fmt.Sprintf("Failed to update organization: %v", organizationID)
common.HandleError(w, http.StatusInternalServerError, m, err)
common.HandleErrorV2(w, http.StatusInternalServerError, m, err)
return
}
go user.UpdateOrganizationsSubscribedUsers(orgResp)
//response, _ := json.Marshal(organization{orgResp})
//w.Header().Set(config.ContentTypeHeader, config.ContentTypeJSON)
w.WriteHeader(http.StatusAccepted)
//w.Write(response)
}
19 changes: 14 additions & 5 deletions src/handlerv2/updateorganizationcoverimage_handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,14 +13,19 @@ import (
"github.com/bb-consent/api/src/org"
)

type coverImageResp struct {
CoverImageId string `json:"coverImageId"`
CoverImageUrl string `json:"coverImageUrl"`
}

// UpdateOrganizationCoverImage Inserts the image and update the id to user
func UpdateOrganizationCoverImage(w http.ResponseWriter, r *http.Request) {
organizationID := r.Header.Get(config.OrganizationId)

file, _, err := r.FormFile("orgimage")
if err != nil {
m := fmt.Sprintf("Failed to extract image organization: %v", organizationID)
common.HandleError(w, http.StatusInternalServerError, m, err)
common.HandleErrorV2(w, http.StatusInternalServerError, m, err)
return
}
defer file.Close()
Expand All @@ -29,26 +34,30 @@ func UpdateOrganizationCoverImage(w http.ResponseWriter, r *http.Request) {
_, err = io.Copy(buf, file)
if err != nil {
m := fmt.Sprintf("Failed to copy image organization: %v", organizationID)
common.HandleError(w, http.StatusInternalServerError, m, err)
common.HandleErrorV2(w, http.StatusInternalServerError, m, err)
return
}

imageID, err := image.Add(buf.Bytes())
if err != nil {
m := fmt.Sprintf("Failed to store image in data store organization: %v", organizationID)
common.HandleError(w, http.StatusInternalServerError, m, err)
common.HandleErrorV2(w, http.StatusInternalServerError, m, err)
return
}

imageURL := "https://" + r.Host + "/v1/organizations/" + organizationID + "/image/" + imageID
o, err := org.UpdateCoverImage(organizationID, imageID, imageURL)
if err != nil {
m := fmt.Sprintf("Failed to update organization: %v with image: %v details", organizationID, imageID)
common.HandleError(w, http.StatusInternalServerError, m, err)
common.HandleErrorV2(w, http.StatusInternalServerError, m, err)
return
}
respBody := coverImageResp{
CoverImageId: o.CoverImageID,
CoverImageUrl: o.CoverImageURL,
}

response, _ := json.Marshal(organization{o})
response, _ := json.Marshal(respBody)
w.Header().Set(config.ContentTypeHeader, config.ContentTypeJSON)
w.WriteHeader(http.StatusOK)
w.Write(response)
Expand Down
Loading

0 comments on commit d23cbb3

Please sign in to comment.