forked from phc/website
Aggiunte tante cose relative al profilo utente
This commit is contained in:
+26
-14
@@ -4,32 +4,44 @@ import "fmt"
|
||||
|
||||
var ErrInvalidSession = fmt.Errorf(`invalid session token`)
|
||||
|
||||
type User interface {
|
||||
GetUsername() string
|
||||
GetName() string
|
||||
GetSurname() string
|
||||
GetFullName() string
|
||||
type User struct {
|
||||
Username string `json:"username"`
|
||||
Name string `json:"name"`
|
||||
Surname string `json:"surname"`
|
||||
FullName string `json:"fullName"`
|
||||
Email string `json:"email"`
|
||||
}
|
||||
|
||||
type Session interface {
|
||||
GetUsername() string
|
||||
GetToken() string
|
||||
func (u User) WithDefaultFullName() User {
|
||||
return User{
|
||||
Username: u.Username,
|
||||
Name: u.Name,
|
||||
Surname: u.Surname,
|
||||
Email: u.Email,
|
||||
|
||||
FullName: u.Username + " " + u.Surname,
|
||||
}
|
||||
}
|
||||
|
||||
type Session struct {
|
||||
Username string `json:"username"`
|
||||
Token string `json:"token"`
|
||||
}
|
||||
|
||||
type AuthenticatorService interface {
|
||||
GetUser(username string) (User, error)
|
||||
GetUsers() ([]User, error)
|
||||
GetSession(token string) (Session, error)
|
||||
Login(username, password string) (Session, error)
|
||||
GetUser(username string) (*User, error)
|
||||
GetUsers() ([]*User, error)
|
||||
GetSession(token string) (*Session, error)
|
||||
Login(username, password string) (*Session, error)
|
||||
}
|
||||
|
||||
func UserForSession(as AuthenticatorService, token string) (User, error) {
|
||||
func UserForSession(as AuthenticatorService, token string) (*User, error) {
|
||||
session, err := as.GetSession(token)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
user, err := as.GetUser(session.GetUsername())
|
||||
user, err := as.GetUser(session.Username)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
+23
-46
@@ -7,47 +7,24 @@ import (
|
||||
"log"
|
||||
"net/http"
|
||||
"path"
|
||||
"time"
|
||||
)
|
||||
|
||||
type LDAPUser struct {
|
||||
Username string `json:"username"`
|
||||
type ldapUser struct {
|
||||
User
|
||||
NumericId int `json:"id"`
|
||||
Name string `json:"name"`
|
||||
Surname string `json:"surname"`
|
||||
Email string `json:"email"`
|
||||
Role string `json:"role"`
|
||||
Gecos string `json:"gecos"`
|
||||
}
|
||||
|
||||
func (u LDAPUser) GetUsername() string {
|
||||
return u.Username
|
||||
}
|
||||
func (u ldapUser) AsUser() *User {
|
||||
return &User{
|
||||
Username: u.Username,
|
||||
Name: u.Name,
|
||||
Surname: u.Surname,
|
||||
Email: u.Email,
|
||||
|
||||
func (u LDAPUser) GetName() string {
|
||||
return u.Name
|
||||
}
|
||||
|
||||
func (u LDAPUser) GetSurname() string {
|
||||
return u.Surname
|
||||
}
|
||||
|
||||
func (u LDAPUser) GetFullName() string {
|
||||
return u.Gecos
|
||||
}
|
||||
|
||||
type SimpleSession struct {
|
||||
Token string `json:"token"`
|
||||
Username string `json:"username"`
|
||||
CreatedOn time.Time `json:"createdOn"`
|
||||
}
|
||||
|
||||
func (s SimpleSession) GetUsername() string {
|
||||
return s.Username
|
||||
}
|
||||
|
||||
func (s SimpleSession) GetToken() string {
|
||||
return s.Token
|
||||
FullName: u.Gecos,
|
||||
}
|
||||
}
|
||||
|
||||
type LDAPAuthService struct {
|
||||
@@ -99,31 +76,31 @@ func (a *LDAPAuthService) doPostRequest(url string, request interface{}, respons
|
||||
return json.NewDecoder(res.Body).Decode(response)
|
||||
}
|
||||
|
||||
func (a *LDAPAuthService) GetUser(username string) (User, error) {
|
||||
var user LDAPUser
|
||||
func (a *LDAPAuthService) GetUser(username string) (*User, error) {
|
||||
var user ldapUser
|
||||
if err := a.doGetRequest(fmt.Sprintf("/user/%s", username), &user); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &user, nil
|
||||
return user.AsUser(), nil
|
||||
}
|
||||
|
||||
func (a *LDAPAuthService) GetUsers() ([]User, error) {
|
||||
ldapUsers := []*LDAPUser{}
|
||||
func (a *LDAPAuthService) GetUsers() ([]*User, error) {
|
||||
ldapUsers := []*ldapUser{}
|
||||
if err := a.doGetRequest(fmt.Sprintf("/users"), &ldapUsers); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
users := make([]User, len(ldapUsers))
|
||||
users := make([]*User, len(ldapUsers))
|
||||
for i, u := range ldapUsers {
|
||||
users[i] = u
|
||||
users[i] = u.AsUser()
|
||||
}
|
||||
|
||||
return users, nil
|
||||
}
|
||||
|
||||
func (a *LDAPAuthService) GetSession(token string) (Session, error) {
|
||||
var response SimpleSession
|
||||
func (a *LDAPAuthService) GetSession(token string) (*Session, error) {
|
||||
var response Session
|
||||
if err := a.doGetRequest(fmt.Sprintf("/session/%s", token), &response); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@@ -131,14 +108,14 @@ func (a *LDAPAuthService) GetSession(token string) (Session, error) {
|
||||
return &response, nil
|
||||
}
|
||||
|
||||
func (a *LDAPAuthService) Login(username, password string) (Session, error) {
|
||||
body := map[string]interface{}{
|
||||
func (a *LDAPAuthService) Login(username, password string) (*Session, error) {
|
||||
reqBody := map[string]interface{}{
|
||||
"username": username,
|
||||
"password": password,
|
||||
}
|
||||
|
||||
var response SimpleSession
|
||||
if err := a.doPostRequest(fmt.Sprintf("/login"), body, &response); err != nil {
|
||||
var response Session
|
||||
if err := a.doPostRequest(fmt.Sprintf("/login"), reqBody, &response); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
|
||||
+46
-52
@@ -7,108 +7,102 @@ import (
|
||||
)
|
||||
|
||||
var exampleMemoryUsers = &Memory{
|
||||
Users: map[string]*MemoryUser{
|
||||
Users: map[string]*memoryUser{
|
||||
"aziis98": {
|
||||
Username: "aziis98",
|
||||
Name: "Antonio",
|
||||
Surname: "De Lucreziis",
|
||||
User: User{
|
||||
Username: "aziis98",
|
||||
Name: "Antonio",
|
||||
Surname: "De Lucreziis",
|
||||
Email: "aziis98@example.org",
|
||||
}.WithDefaultFullName(),
|
||||
Password: "123",
|
||||
},
|
||||
"bachoseven": {
|
||||
Username: "bachoseven",
|
||||
Name: "Francesco",
|
||||
Surname: "Minnocci",
|
||||
User: User{
|
||||
Username: "bachoseven",
|
||||
Name: "Francesco",
|
||||
Surname: "Minnocci",
|
||||
Email: "bachoseven@example.org",
|
||||
}.WithDefaultFullName(),
|
||||
Password: "234",
|
||||
},
|
||||
},
|
||||
Sessions: map[string]*MemorySession{},
|
||||
Sessions: map[string]*memorySession{},
|
||||
}
|
||||
|
||||
type MemoryUser struct {
|
||||
Username string `json:"username"`
|
||||
Name string `json:"name"`
|
||||
Surname string `json:"surname"`
|
||||
|
||||
type memoryUser struct {
|
||||
User
|
||||
Password string `json:"-"`
|
||||
}
|
||||
|
||||
func (u *MemoryUser) GetUsername() string {
|
||||
return u.Username
|
||||
func (u memoryUser) AsUser() *User {
|
||||
return &User{
|
||||
Username: u.Username,
|
||||
Name: u.Name,
|
||||
Surname: u.Surname,
|
||||
FullName: u.FullName,
|
||||
Email: u.Email,
|
||||
}
|
||||
}
|
||||
|
||||
func (u *MemoryUser) GetName() string {
|
||||
return u.Name
|
||||
}
|
||||
|
||||
func (u *MemoryUser) GetSurname() string {
|
||||
return u.Surname
|
||||
}
|
||||
|
||||
func (u *MemoryUser) GetFullName() string {
|
||||
return u.Name + " " + u.Surname
|
||||
}
|
||||
|
||||
type MemorySession struct {
|
||||
type memorySession struct {
|
||||
Username string
|
||||
Token string
|
||||
}
|
||||
|
||||
func (s *MemorySession) GetUsername() string {
|
||||
return s.Username
|
||||
}
|
||||
|
||||
func (s *MemorySession) GetToken() string {
|
||||
return s.Token
|
||||
func (s memorySession) AsSession() *Session {
|
||||
return &Session{
|
||||
Username: s.Username,
|
||||
Token: s.Token,
|
||||
}
|
||||
}
|
||||
|
||||
type Memory struct {
|
||||
Users map[string]*MemoryUser
|
||||
Sessions map[string]*MemorySession
|
||||
Users map[string]*memoryUser
|
||||
Sessions map[string]*memorySession
|
||||
}
|
||||
|
||||
func (m *Memory) GetUser(username string) (User, error) {
|
||||
func (m *Memory) GetUser(username string) (*User, error) {
|
||||
user, ok := m.Users[username]
|
||||
if !ok {
|
||||
return nil, fmt.Errorf(`no user with that username`)
|
||||
}
|
||||
|
||||
return user, nil
|
||||
return user.AsUser(), nil
|
||||
}
|
||||
|
||||
func (m *Memory) GetUsers() ([]User, error) {
|
||||
users := make([]User, len(m.Users))
|
||||
func (m *Memory) GetUsers() ([]*User, error) {
|
||||
users := make([]*User, len(m.Users))
|
||||
i := 0
|
||||
for _, u := range m.Users {
|
||||
users[i] = u
|
||||
users[i] = u.AsUser()
|
||||
i++
|
||||
}
|
||||
|
||||
return users, nil
|
||||
}
|
||||
|
||||
func (m *Memory) GetSession(token string) (Session, error) {
|
||||
func (m *Memory) GetSession(token string) (*Session, error) {
|
||||
session, ok := m.Sessions[token]
|
||||
if !ok {
|
||||
return nil, ErrInvalidSession
|
||||
}
|
||||
|
||||
return session, nil
|
||||
return session.AsSession(), nil
|
||||
}
|
||||
|
||||
func (m *Memory) Login(username string, password string) (Session, error) {
|
||||
user, err := m.GetUser(username)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
func (m *Memory) Login(username string, password string) (*Session, error) {
|
||||
user, ok := m.Users[username]
|
||||
if !ok {
|
||||
return nil, fmt.Errorf(`no user with that username`)
|
||||
}
|
||||
|
||||
memUser := user.(*MemoryUser)
|
||||
|
||||
if memUser.Password != password {
|
||||
if user.Password != password {
|
||||
return nil, fmt.Errorf(`invalid credentials`)
|
||||
}
|
||||
|
||||
session := &MemorySession{username, util.GenerateRandomString(15)}
|
||||
session := &memorySession{username, util.GenerateRandomString(15)}
|
||||
m.Sessions[session.Token] = session
|
||||
|
||||
return session, nil
|
||||
return session.AsSession(), nil
|
||||
}
|
||||
|
||||
+4
-8
@@ -1,14 +1,10 @@
|
||||
|
||||
JS_SOURCES = src/utenti.js
|
||||
JS_BUNDLES = $(patsubst src/%.js, dist/%.min.js, $(JS_SOURCES))
|
||||
JS_SOURCES = src/utenti.js src/profilo.js
|
||||
|
||||
.PHONY: all
|
||||
all: $(JS_BUNDLES)
|
||||
|
||||
dist/%.min.js: src/%.js
|
||||
rollup -c rollup.config.js $<
|
||||
all: $(JS_SOURCES)
|
||||
rollup -c
|
||||
|
||||
.PHONY: debug
|
||||
debug:
|
||||
@echo "JS_SOURCES = $(JS_SOURCES)"
|
||||
@echo "JS_BUNDLES = $(JS_BUNDLES)"
|
||||
@echo "JS_SOURCES = $(JS_SOURCES)"
|
||||
@@ -1,6 +1,4 @@
|
||||
import { defineConfig } from 'rollup'
|
||||
|
||||
// import resolve from '@rollup/plugin-node-resolve'
|
||||
import { terser } from 'rollup-plugin-terser'
|
||||
|
||||
export default defineConfig([
|
||||
@@ -16,9 +14,18 @@ export default defineConfig([
|
||||
'fuse.js': 'Fuse',
|
||||
},
|
||||
},
|
||||
plugins: [
|
||||
// resolve(),
|
||||
terser(),
|
||||
],
|
||||
plugins: [terser()],
|
||||
},
|
||||
{
|
||||
input: 'src/profilo.js',
|
||||
external: ['alpinejs'],
|
||||
output: {
|
||||
file: 'dist/profilo.min.js',
|
||||
format: 'iife',
|
||||
globals: {
|
||||
alpinejs: 'Alpine',
|
||||
},
|
||||
},
|
||||
plugins: [terser()],
|
||||
},
|
||||
])
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
import Alpine from 'alpinejs'
|
||||
|
||||
Alpine.data('profilo', () => ({
|
||||
init() {
|
||||
console.log('Profilo!')
|
||||
},
|
||||
}))
|
||||
|
||||
Alpine.data('passwordForm', () => ({
|
||||
password: '',
|
||||
passwordAgain: '',
|
||||
passwordSame: true,
|
||||
onUpdate() {
|
||||
this.passwordSame = this.password === this.passwordAgain
|
||||
},
|
||||
}))
|
||||
@@ -81,6 +81,15 @@ func main() {
|
||||
return c.JSON(utenti)
|
||||
})
|
||||
|
||||
app.Get("/api/profilo", func(c *fiber.Ctx) error {
|
||||
user := c.Locals("user")
|
||||
if user == nil {
|
||||
return fmt.Errorf(`user not logged in`)
|
||||
}
|
||||
|
||||
return c.JSON(user)
|
||||
})
|
||||
|
||||
app.Get("/storia", func(c *fiber.Ctx) error {
|
||||
storia, err := GetStoria()
|
||||
if err != nil {
|
||||
@@ -137,7 +146,7 @@ func main() {
|
||||
c.Cookie(&fiber.Cookie{
|
||||
Name: "session-token",
|
||||
Path: "/",
|
||||
Value: session.GetToken(),
|
||||
Value: session.Token,
|
||||
Expires: inThreeDays,
|
||||
})
|
||||
|
||||
@@ -145,7 +154,7 @@ func main() {
|
||||
})
|
||||
|
||||
app.Get("/profilo", func(c *fiber.Ctx) error {
|
||||
user, ok := c.Locals("user").(auth.User)
|
||||
user, ok := c.Locals("user").(*auth.User)
|
||||
if !ok || user == nil {
|
||||
return fmt.Errorf(`user not logged in`)
|
||||
}
|
||||
|
||||
+42
-2
@@ -29,6 +29,8 @@
|
||||
--shadow-1: 0 0 16px 0 #00000018;
|
||||
|
||||
--text-input-bg: #fff;
|
||||
--text-input-readonly-bg: #e4e4e4;
|
||||
--text-input-readonly-fg: #777;
|
||||
|
||||
--bg-darker-2-1: #c8c8c8;
|
||||
--accent-2-lighter: #5cc969;
|
||||
@@ -401,11 +403,24 @@ li {
|
||||
line-height: 1.8;
|
||||
}
|
||||
|
||||
p + p {
|
||||
padding-top: 0.5rem;
|
||||
}
|
||||
|
||||
ul,
|
||||
ol {
|
||||
padding: 0 0 0 1.5rem;
|
||||
}
|
||||
|
||||
hr {
|
||||
width: 50ch;
|
||||
height: 1px;
|
||||
margin: 0;
|
||||
|
||||
border: none;
|
||||
background-color: var(--bg-darker-2);
|
||||
}
|
||||
|
||||
pre {
|
||||
margin: 0.5rem 0;
|
||||
|
||||
@@ -431,21 +446,27 @@ p.center {
|
||||
|
||||
/* Controls */
|
||||
|
||||
a {
|
||||
a:not(.button) {
|
||||
color: var(--accent-1-fg);
|
||||
font-weight: var(--font-weight-medium);
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
a:hover {
|
||||
a:not(.button):hover {
|
||||
color: var(--accent-1);
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
a.button {
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
/* Buttons */
|
||||
|
||||
button,
|
||||
.button {
|
||||
display: inline-block;
|
||||
|
||||
font-family: var(--font-sf);
|
||||
font-weight: var(--font-weight-medium);
|
||||
font-size: 17px;
|
||||
@@ -544,6 +565,19 @@ input[type='password'] {
|
||||
font-family: caption;
|
||||
}
|
||||
|
||||
input[type='text']:read-only,
|
||||
input[type='password']:read-only {
|
||||
background: var(--text-input-readonly-bg);
|
||||
color: var(--text-input-readonly-fg);
|
||||
box-shadow: 0 0 8px 0 #00000010;
|
||||
}
|
||||
|
||||
input[type='text'].error,
|
||||
input[type='password'].error {
|
||||
background: #faa;
|
||||
color: #311;
|
||||
}
|
||||
|
||||
/* Compound Controls */
|
||||
|
||||
.compound {
|
||||
@@ -617,10 +651,16 @@ form .field-set {
|
||||
padding: 1rem;
|
||||
}
|
||||
|
||||
form .field-set .fill {
|
||||
grid-column: 1 / span 2;
|
||||
}
|
||||
|
||||
form .field-set label {
|
||||
grid-column: 1 / 2;
|
||||
align-self: center;
|
||||
justify-self: end;
|
||||
|
||||
font-weight: var(--font-weight-medium);
|
||||
}
|
||||
|
||||
form .field-set input {
|
||||
|
||||
+19
-4
@@ -1,4 +1,3 @@
|
||||
|
||||
body.dark-mode {
|
||||
--bg: #282828;
|
||||
--fg: #a6cc92;
|
||||
@@ -24,8 +23,10 @@ body.dark-mode {
|
||||
--font-weight-bold: 700;
|
||||
|
||||
--shadow-1: 0 0 16px 0 #16182077;
|
||||
|
||||
|
||||
--text-input-bg: var(--bg-darker);
|
||||
--text-input-readonly-bg: hsl(10, 10%, 22%);
|
||||
--text-input-readonly-fg: hsl(10, 10%, 40%);
|
||||
|
||||
--bg-darker-2-1: #c8c8c8;
|
||||
--accent-2-lighter: #5cc969;
|
||||
@@ -62,6 +63,19 @@ body.dark-mode {
|
||||
background: #4b4342;
|
||||
}
|
||||
|
||||
.dark-mode input[type='text']:read-only,
|
||||
.dark-mode input[type='password']:read-only {
|
||||
background: var(--text-input-readonly-bg);
|
||||
color: var(--text-input-readonly-fg);
|
||||
box-shadow: 0 0 8px 0 #00000010;
|
||||
}
|
||||
|
||||
.dark-mode input[type='text'].error,
|
||||
.dark-mode input[type='password'].error {
|
||||
background: #633;
|
||||
color: #faa;
|
||||
}
|
||||
|
||||
.dark-mode pre {
|
||||
background: var(--bg-darker);
|
||||
border: 1px solid var(--bg-darker-2);
|
||||
@@ -72,6 +86,7 @@ body.dark-mode {
|
||||
filter: invert(1);
|
||||
}
|
||||
|
||||
.dark-mode table td, .dark-mode table th {
|
||||
.dark-mode table td,
|
||||
.dark-mode table th {
|
||||
border-color: var(--fg);
|
||||
}
|
||||
}
|
||||
|
||||
+3
-1
@@ -88,10 +88,12 @@
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<hr>
|
||||
<section>
|
||||
<!-- <h2>Altro...</h2> -->
|
||||
<div class="card">
|
||||
<div class="title">Vuoi diventare un macchinista?</div>
|
||||
<!-- <h3 style="font-weight: 500;">Vuoi diventare un macchinista?</h3> -->
|
||||
<div class="description">
|
||||
<p>
|
||||
Ti interessa (o interesserebbe) smanettare al PC, montare e smontare i cose? Stai spesso in dipartimento? Allora
|
||||
|
||||
+95
-10
@@ -1,20 +1,105 @@
|
||||
{{template "base" .}}
|
||||
|
||||
{{define "title"}}Profilo @{{ .User.Username }} • PHC{{end}}
|
||||
|
||||
{{define "title"}}Profilo di @{{ .User.Username }} • PHC{{end}}
|
||||
{{define "body"}}
|
||||
<section>
|
||||
<script src="https://unpkg.com/alpinejs@3.x.x/dist/cdn.min.js"></script>
|
||||
<script src="/public/js/profilo.min.js"></script>
|
||||
<section x-data="profilo">
|
||||
<h1>Profilo di @{{ .User.Username }}</h1>
|
||||
<h2>Impostazioni</h2>
|
||||
<p>
|
||||
Lorem ipsum dolor sit amet consectetur adipisicing elit. Quae earum amet delectus cumque obcaecati minus quos aliquid fugiat reprehenderit voluptatum?
|
||||
</p>
|
||||
<p class="center">
|
||||
<a href="/logout">Logout</a>
|
||||
<a class="button" href="/logout">Logout</a>
|
||||
</p>
|
||||
</section>
|
||||
<section>
|
||||
<h2>Appunti e Dispense</h2>
|
||||
<p>
|
||||
Per gestire i tuoi appunti e le tue dispense caricate nella sezione <a href="/appunti">Appunti</a> del sito vai
|
||||
<a href="/appunti/condivisi">alla pagina appunti condivisi</a>.
|
||||
</p>
|
||||
</section>
|
||||
<section>
|
||||
<h2>Impostazioni</h2>
|
||||
<div class="card-list">
|
||||
<form class="card" action="/profile/impostazioni" method="POST">
|
||||
<div class="title">
|
||||
Sito PHC
|
||||
</div>
|
||||
<p>
|
||||
Aggiorna i campi relativi al sito del PHC, l'immagine del profilo verrà visualizzata sulla tua pagina utente <a href="#">phc.dm.unipi.it/u/{{ .User.Username }}</a> e nella lista di <a href="/utenti">tutti gli utenti</a>.
|
||||
</p>
|
||||
<div class="field-set">
|
||||
<label for="website-nickname">Nickname</label>
|
||||
<input type="text" name="nickname" id="website-nickname" placeholder="{{ .User.Username }}">
|
||||
<label for="website-profile-picture">Immagine Profilo</label>
|
||||
<input type="file" name="picture" id="website-profile-picture">
|
||||
</div>
|
||||
<p>
|
||||
Puoi anche aggiungere link ad altri tuoi profili su siti esterni (quando riempi l'ultimo campo se ne crea uno nuovo sotto)
|
||||
</p>
|
||||
<div class="field-set">
|
||||
<label for="website-link-1">Link 1</label>
|
||||
<input type="text" name="link" id="website-link-1"
|
||||
placeholder="https://github.com/...">
|
||||
<label for="website-link-2">Link 2</label>
|
||||
<input type="text" name="link" id="website-link-2"
|
||||
placeholder="https://twitter.com/...">
|
||||
<label for="website-link-3">Link 3</label>
|
||||
<input type="text" name="link" id="website-link-3"
|
||||
placeholder="https://news.ycombinator.com/user?id=...">
|
||||
</div>
|
||||
<div class="field">
|
||||
<button class="primary">Aggiorna</button>
|
||||
</div>
|
||||
</form>
|
||||
<form class="card" action="/profile/impostazioni" method="POST">
|
||||
<div class="title">
|
||||
Informazioni Utente
|
||||
</div>
|
||||
<p>
|
||||
Aggiorna i campi modificabili dell'account Poisson
|
||||
</p>
|
||||
<div class="field-set">
|
||||
<label for="user-username">Username</label>
|
||||
<input type="text" readonly name="username" id="user-username" value="{{ .User.Username }}">
|
||||
<label for="user-name">Nome</label>
|
||||
<input type="text" readonly name="name" id="user-name" value="{{ .User.Name }}">
|
||||
<label for="user-surname">Cognome</label>
|
||||
<input type="text" readonly name="surname" id="user-surname" value="{{ .User.Surname }}">
|
||||
<label for="user-email">Email</label>
|
||||
<input type="text" readonly name="email" id="user-email" value="{{ .User.Email }}">
|
||||
</div>
|
||||
<div class="field">
|
||||
<button class="primary">Aggiorna</button>
|
||||
</div>
|
||||
</form>
|
||||
<form x-data="passwordForm" class="card" action="/profile/impostazioni" method="POST">
|
||||
<div class="title">
|
||||
Modifica Password
|
||||
</div>
|
||||
<p>
|
||||
Aggiorna la password di Poisson
|
||||
</p>
|
||||
<div class="field-set">
|
||||
<label for="pass-username">Username</label>
|
||||
<input type="text" readonly name="username" id="pass-username" value="{{ .User.Username }}">
|
||||
<label for="pass-password">Password</label>
|
||||
<input type="password" name="password" id="pass-password" :class="!passwordSame ? 'error' : ''"
|
||||
x-model="password" @input="onUpdate" placeholder="In realtà anche questo non funge...">
|
||||
<label for="pass-password-2">Ripeti Password</label>
|
||||
<input type="password" name="password-2" id="pass-password-2" :class="!passwordSame ? 'error' : ''"
|
||||
x-model="passwordAgain" @input="onUpdate" placeholder="In realtà anche questo non funge...">
|
||||
</div>
|
||||
<div class="field">
|
||||
<button class="primary">Aggiorna Password</button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</section>
|
||||
<section>
|
||||
<h2>Recupero Credenziali Poisson</h2>
|
||||
<p>
|
||||
Per il recupero credenziali vieni direttamente al PHC a parlarne con calma con noi altrimenti puoi inviaci una email all'indirizzo <a href="mailto:{{ .Config.Email }}">{{ .Config.Email }}</a> e poi recuperare le nuove credenziali sul sito <a href="https://credenziali.phc.dm.unipi.it/">credenziali.phc.dm.unipi.it</a>.
|
||||
Per il recupero credenziali vieni direttamente al PHC a parlarne con calma con noi altrimenti puoi inviaci una email
|
||||
all'indirizzo <a href="mailto:{{ .Config.Email }}">{{ .Config.Email }}</a> e poi recuperare le nuove credenziali sul
|
||||
sito <a href="https://credenziali.phc.dm.unipi.it/">credenziali.phc.dm.unipi.it</a>.
|
||||
</p>
|
||||
</section>
|
||||
{{end}}
|
||||
Reference in New Issue
Block a user