diff --git a/.idea/dataSources.xml b/.idea/dataSources.xml index 8904924..c6d5757 100644 --- a/.idea/dataSources.xml +++ b/.idea/dataSources.xml @@ -1,11 +1,18 @@ - + postgresql true org.postgresql.Driver - jdbc:postgresql://localhost:5432/hy_passport + jdbc:postgresql://localhost:5432/hy_identity + $ProjectFileDir$ + + + postgresql + true + org.postgresql.Driver + jdbc:postgresql://id.solsynth.dev:5432/identity $ProjectFileDir$ diff --git a/pkg/database/migrator.go b/pkg/database/migrator.go index fae7a6f..36699db 100644 --- a/pkg/database/migrator.go +++ b/pkg/database/migrator.go @@ -10,6 +10,7 @@ func RunMigration(source *gorm.DB) error { &models.Account{}, &models.AuthFactor{}, &models.AccountProfile{}, + &models.AccountPage{}, &models.AccountContact{}, &models.AuthSession{}, &models.AuthChallenge{}, diff --git a/pkg/models/accounts.go b/pkg/models/accounts.go index 7d0a962..f72a7ec 100644 --- a/pkg/models/accounts.go +++ b/pkg/models/accounts.go @@ -17,6 +17,7 @@ type Account struct { Avatar string `json:"avatar"` Banner string `json:"banner"` Profile AccountProfile `json:"profile"` + PersonalPage AccountPage `json:"personal_page"` Sessions []AuthSession `json:"sessions"` Challenges []AuthChallenge `json:"challenges"` Factors []AuthFactor `json:"factors"` diff --git a/pkg/models/profiles.go b/pkg/models/profiles.go index 8ff124f..1800953 100644 --- a/pkg/models/profiles.go +++ b/pkg/models/profiles.go @@ -1,6 +1,9 @@ package models -import "time" +import ( + "gorm.io/datatypes" + "time" +) type AccountProfile struct { BaseModel @@ -11,3 +14,18 @@ type AccountProfile struct { Birthday *time.Time `json:"birthday"` AccountID uint `json:"account_id"` } + +type AccountPage struct { + BaseModel + + Content string `json:"content"` + Script string `json:"script"` + Style string `json:"style"` + Links datatypes.JSONSlice[AccountPageLinks] `json:"links"` + AccountID uint `json:"account_id"` +} + +type AccountPageLinks struct { + Label string `json:"label"` + Url string `json:"url"` +} diff --git a/pkg/server/page_api.go b/pkg/server/page_api.go new file mode 100644 index 0000000..cdf2eee --- /dev/null +++ b/pkg/server/page_api.go @@ -0,0 +1,69 @@ +package server + +import ( + "git.solsynth.dev/hydrogen/identity/pkg/database" + "git.solsynth.dev/hydrogen/identity/pkg/models" + "github.com/gofiber/fiber/v2" +) + +func getPersonalPage(c *fiber.Ctx) error { + alias := c.Params("alias") + + var account models.Account + if err := database.C. + Where(&models.Account{Name: alias}). + First(&account).Error; err != nil { + return fiber.NewError(fiber.StatusBadRequest, err.Error()) + } + + var page models.AccountPage + if err := database.C. + Where(&models.AccountPage{AccountID: account.ID}). + First(&page).Error; err != nil { + return fiber.NewError(fiber.StatusBadRequest, err.Error()) + } + + return c.JSON(page) +} + +func getOwnPersonalPage(c *fiber.Ctx) error { + user := c.Locals("principal").(models.Account) + + var page models.AccountPage + if err := database.C. + Where(&models.AccountPage{AccountID: user.ID}). + FirstOrCreate(&page, &models.AccountPage{AccountID: user.ID}).Error; err != nil { + return fiber.NewError(fiber.StatusBadRequest, err.Error()) + } + + return c.JSON(page) +} + +func editPersonalPage(c *fiber.Ctx) error { + user := c.Locals("principal").(models.Account) + + var data struct { + Content string `json:"content"` + Links []models.AccountPageLinks `json:"links"` + } + + if err := BindAndValidate(c, &data); err != nil { + return err + } + + var page models.AccountPage + if err := database.C. + Where(&models.AccountPage{AccountID: user.ID}). + FirstOrInit(&page).Error; err != nil { + return fiber.NewError(fiber.StatusInternalServerError, err.Error()) + } + + page.Content = data.Content + page.Links = data.Links + + if err := database.C.Save(&page).Error; err != nil { + return fiber.NewError(fiber.StatusInternalServerError, err.Error()) + } + + return c.SendStatus(fiber.StatusOK) +} diff --git a/pkg/server/startup.go b/pkg/server/startup.go index 46f36c0..74b2aeb 100644 --- a/pkg/server/startup.go +++ b/pkg/server/startup.go @@ -77,7 +77,9 @@ func NewServer() { me.Put("/banner", authMiddleware, setBanner) me.Get("/", authMiddleware, getUserinfo) + me.Get("/page", authMiddleware, getOwnPersonalPage) me.Put("/", authMiddleware, editUserinfo) + me.Put("/page", authMiddleware, editPersonalPage) me.Get("/events", authMiddleware, getEvents) me.Get("/challenges", authMiddleware, getChallenges) me.Get("/sessions", authMiddleware, getSessions) @@ -86,6 +88,12 @@ func NewServer() { me.Post("/confirm", doRegisterConfirm) } + directory := api.Group("/users/:alias").Name("User Directory") + { + directory.Get("/", getOtherUserinfo) + directory.Get("/page", getPersonalPage) + } + api.Post("/users", doRegister) api.Put("/auth", startChallenge) diff --git a/pkg/server/userinfo..go b/pkg/server/userinfo..go new file mode 100644 index 0000000..7dc9287 --- /dev/null +++ b/pkg/server/userinfo..go @@ -0,0 +1,21 @@ +package server + +import ( + "git.solsynth.dev/hydrogen/identity/pkg/database" + "git.solsynth.dev/hydrogen/identity/pkg/models" + "github.com/gofiber/fiber/v2" +) + +func getOtherUserinfo(c *fiber.Ctx) error { + alias := c.Params("alias") + + var account models.Account + if err := database.C. + Where(&models.Account{Name: alias}). + Omit("sessions", "challenges", "factors", "events", "clients", "notifications", "notify_subscribers"). + First(&account).Error; err != nil { + return fiber.NewError(fiber.StatusBadRequest, err.Error()) + } + + return c.JSON(account) +} diff --git a/pkg/views/src/layouts/user-center.vue b/pkg/views/src/layouts/user-center.vue index 407452c..ddb0690 100644 --- a/pkg/views/src/layouts/user-center.vue +++ b/pkg/views/src/layouts/user-center.vue @@ -6,6 +6,7 @@ + @@ -17,3 +18,5 @@ + \ No newline at end of file diff --git a/pkg/views/src/router/index.ts b/pkg/views/src/router/index.ts index f06410b..e9eea4b 100644 --- a/pkg/views/src/router/index.ts +++ b/pkg/views/src/router/index.ts @@ -26,6 +26,12 @@ const router = createRouter({ component: () => import("@/views/personalize.vue"), meta: { title: "Your personality" }, }, + { + path: "/me/personal-page", + name: "personal-page", + component: () => import("@/views/personal-page.vue"), + meta: { title: "Your personal page" }, + }, { path: "/me/security", name: "security", diff --git a/pkg/views/src/views/personal-page.vue b/pkg/views/src/views/personal-page.vue new file mode 100644 index 0000000..782b1df --- /dev/null +++ b/pkg/views/src/views/personal-page.vue @@ -0,0 +1,71 @@ + + + diff --git a/pkg/views/src/views/personalize.vue b/pkg/views/src/views/personalize.vue index a841f08..220a185 100644 --- a/pkg/views/src/views/personalize.vue +++ b/pkg/views/src/views/personalize.vue @@ -48,7 +48,7 @@ -