#1193 Make organization emails non-mandatory
This commit is contained in:
parent
aa67de910a
commit
80701d45bb
11 changed files with 135 additions and 164 deletions
|
@ -630,7 +630,6 @@ release.tag_name_already_exist = Release with this tag name has already existed.
|
||||||
[org]
|
[org]
|
||||||
org_name_holder = Organization Name
|
org_name_holder = Organization Name
|
||||||
org_name_helper = Great organization names are short and memorable.
|
org_name_helper = Great organization names are short and memorable.
|
||||||
org_email_helper = Organization's E-mail receives all notifications and confirmations.
|
|
||||||
create_org = Create Organization
|
create_org = Create Organization
|
||||||
repo_updated = Updated
|
repo_updated = Updated
|
||||||
people = People
|
people = People
|
||||||
|
|
|
@ -9,8 +9,6 @@ import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
"github.com/gogits/gogs/modules/base"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
|
@ -93,17 +91,6 @@ func (org *User) RemoveOrgRepo(repoID int64) error {
|
||||||
return org.removeOrgRepo(x, repoID)
|
return org.removeOrgRepo(x, repoID)
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsOrgEmailUsed returns true if the e-mail has been used in organization account.
|
|
||||||
func IsOrgEmailUsed(email string) (bool, error) {
|
|
||||||
if len(email) == 0 {
|
|
||||||
return false, nil
|
|
||||||
}
|
|
||||||
return x.Get(&User{
|
|
||||||
Email: email,
|
|
||||||
Type: ORGANIZATION,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
// CreateOrganization creates record of a new organization.
|
// CreateOrganization creates record of a new organization.
|
||||||
func CreateOrganization(org, owner *User) (err error) {
|
func CreateOrganization(org, owner *User) (err error) {
|
||||||
if err = IsUsableName(org.Name); err != nil {
|
if err = IsUsableName(org.Name); err != nil {
|
||||||
|
@ -117,18 +104,9 @@ func CreateOrganization(org, owner *User) (err error) {
|
||||||
return ErrUserAlreadyExist{org.Name}
|
return ErrUserAlreadyExist{org.Name}
|
||||||
}
|
}
|
||||||
|
|
||||||
isExist, err = IsOrgEmailUsed(org.Email)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
} else if isExist {
|
|
||||||
return ErrEmailAlreadyUsed{org.Email}
|
|
||||||
}
|
|
||||||
|
|
||||||
org.LowerName = strings.ToLower(org.Name)
|
org.LowerName = strings.ToLower(org.Name)
|
||||||
org.FullName = org.Name
|
org.FullName = org.Name
|
||||||
org.Avatar = base.EncodeMd5(org.Email)
|
org.UseCustomAvatar = true
|
||||||
org.AvatarEmail = org.Email
|
|
||||||
// No password for organization.
|
|
||||||
org.NumTeams = 1
|
org.NumTeams = 1
|
||||||
org.NumMembers = 1
|
org.NumMembers = 1
|
||||||
|
|
||||||
|
@ -141,6 +119,17 @@ func CreateOrganization(org, owner *User) (err error) {
|
||||||
if _, err = sess.Insert(org); err != nil {
|
if _, err = sess.Insert(org); err != nil {
|
||||||
return fmt.Errorf("insert organization: %v", err)
|
return fmt.Errorf("insert organization: %v", err)
|
||||||
}
|
}
|
||||||
|
org.GenerateRandomAvatar()
|
||||||
|
|
||||||
|
// Add initial creator to organization and owner team.
|
||||||
|
if _, err = sess.Insert(&OrgUser{
|
||||||
|
Uid: owner.Id,
|
||||||
|
OrgID: org.Id,
|
||||||
|
IsOwner: true,
|
||||||
|
NumTeams: 1,
|
||||||
|
}); err != nil {
|
||||||
|
return fmt.Errorf("insert org-user relation: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
// Create default owner team.
|
// Create default owner team.
|
||||||
t := &Team{
|
t := &Team{
|
||||||
|
@ -154,23 +143,11 @@ func CreateOrganization(org, owner *User) (err error) {
|
||||||
return fmt.Errorf("insert owner team: %v", err)
|
return fmt.Errorf("insert owner team: %v", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add initial creator to organization and owner team.
|
if _, err = sess.Insert(&TeamUser{
|
||||||
ou := &OrgUser{
|
|
||||||
Uid: owner.Id,
|
|
||||||
OrgID: org.Id,
|
|
||||||
IsOwner: true,
|
|
||||||
NumTeams: 1,
|
|
||||||
}
|
|
||||||
if _, err = sess.Insert(ou); err != nil {
|
|
||||||
return fmt.Errorf("insert org-user relation: %v", err)
|
|
||||||
}
|
|
||||||
|
|
||||||
tu := &TeamUser{
|
|
||||||
Uid: owner.Id,
|
Uid: owner.Id,
|
||||||
OrgID: org.Id,
|
OrgID: org.Id,
|
||||||
TeamID: t.ID,
|
TeamID: t.ID,
|
||||||
}
|
}); err != nil {
|
||||||
if _, err = sess.Insert(tu); err != nil {
|
|
||||||
return fmt.Errorf("insert team-user relation: %v", err)
|
return fmt.Errorf("insert team-user relation: %v", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -55,12 +55,12 @@ type User struct {
|
||||||
Name string `xorm:"UNIQUE NOT NULL"`
|
Name string `xorm:"UNIQUE NOT NULL"`
|
||||||
FullName string
|
FullName string
|
||||||
// Email is the primary email address (to be used for communication).
|
// Email is the primary email address (to be used for communication).
|
||||||
Email string `xorm:"UNIQUE(s) NOT NULL"`
|
Email string `xorm:"NOT NULL"`
|
||||||
Passwd string `xorm:"NOT NULL"`
|
Passwd string `xorm:"NOT NULL"`
|
||||||
LoginType LoginType
|
LoginType LoginType
|
||||||
LoginSource int64 `xorm:"NOT NULL DEFAULT 0"`
|
LoginSource int64 `xorm:"NOT NULL DEFAULT 0"`
|
||||||
LoginName string
|
LoginName string
|
||||||
Type UserType `xorm:"UNIQUE(s)"`
|
Type UserType
|
||||||
Orgs []*User `xorm:"-"`
|
Orgs []*User `xorm:"-"`
|
||||||
Repos []*Repository `xorm:"-"`
|
Repos []*Repository `xorm:"-"`
|
||||||
Location string
|
Location string
|
||||||
|
@ -132,42 +132,56 @@ func (u *User) HomeLink() string {
|
||||||
return setting.AppSubUrl + "/" + u.Name
|
return setting.AppSubUrl + "/" + u.Name
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// CustomAvatarPath returns user custom avatar file path.
|
||||||
|
func (u *User) CustomAvatarPath() string {
|
||||||
|
return filepath.Join(setting.AvatarUploadPath, com.ToStr(u.Id))
|
||||||
|
}
|
||||||
|
|
||||||
|
// GenerateRandomAvatar generates a random avatar for user.
|
||||||
|
func (u *User) GenerateRandomAvatar() error {
|
||||||
|
seed := u.Email
|
||||||
|
if len(seed) == 0 {
|
||||||
|
seed = u.Name
|
||||||
|
}
|
||||||
|
|
||||||
|
img, err := avatar.RandomImage([]byte(seed))
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("RandomImage: %v", err)
|
||||||
|
}
|
||||||
|
if err = os.MkdirAll(path.Dir(u.CustomAvatarPath()), os.ModePerm); err != nil {
|
||||||
|
return fmt.Errorf("MkdirAll: %v", err)
|
||||||
|
}
|
||||||
|
fw, err := os.Create(u.CustomAvatarPath())
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("Create: %v", err)
|
||||||
|
}
|
||||||
|
defer fw.Close()
|
||||||
|
|
||||||
|
if err = jpeg.Encode(fw, img, nil); err != nil {
|
||||||
|
return fmt.Errorf("Encode: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
log.Info("New random avatar created: %d", u.Id)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
func (u *User) RelAvatarLink() string {
|
func (u *User) RelAvatarLink() string {
|
||||||
defaultImgUrl := "/img/avatar_default.jpg"
|
defaultImgUrl := "/img/avatar_default.jpg"
|
||||||
if u.Id == -1 {
|
if u.Id == -1 {
|
||||||
return defaultImgUrl
|
return defaultImgUrl
|
||||||
}
|
}
|
||||||
|
|
||||||
imgPath := path.Join(setting.AvatarUploadPath, com.ToStr(u.Id))
|
|
||||||
switch {
|
switch {
|
||||||
case u.UseCustomAvatar:
|
case u.UseCustomAvatar:
|
||||||
if !com.IsExist(imgPath) {
|
if !com.IsExist(u.CustomAvatarPath()) {
|
||||||
return defaultImgUrl
|
return defaultImgUrl
|
||||||
}
|
}
|
||||||
return "/avatars/" + com.ToStr(u.Id)
|
return "/avatars/" + com.ToStr(u.Id)
|
||||||
case setting.DisableGravatar, setting.OfflineMode:
|
case setting.DisableGravatar, setting.OfflineMode:
|
||||||
if !com.IsExist(imgPath) {
|
if !com.IsExist(u.CustomAvatarPath()) {
|
||||||
img, err := avatar.RandomImage([]byte(u.Email))
|
if err := u.GenerateRandomAvatar(); err != nil {
|
||||||
if err != nil {
|
log.Error(3, "GenerateRandomAvatar: %v", err)
|
||||||
log.Error(3, "RandomImage: %v", err)
|
|
||||||
return defaultImgUrl
|
|
||||||
}
|
}
|
||||||
if err = os.MkdirAll(path.Dir(imgPath), os.ModePerm); err != nil {
|
|
||||||
log.Error(3, "MkdirAll: %v", err)
|
|
||||||
return defaultImgUrl
|
|
||||||
}
|
|
||||||
fw, err := os.Create(imgPath)
|
|
||||||
if err != nil {
|
|
||||||
log.Error(3, "Create: %v", err)
|
|
||||||
return defaultImgUrl
|
|
||||||
}
|
|
||||||
defer fw.Close()
|
|
||||||
|
|
||||||
if err = jpeg.Encode(fw, img, nil); err != nil {
|
|
||||||
log.Error(3, "Encode: %v", err)
|
|
||||||
return defaultImgUrl
|
|
||||||
}
|
|
||||||
log.Info("New random avatar created: %d", u.Id)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return "/avatars/" + com.ToStr(u.Id)
|
return "/avatars/" + com.ToStr(u.Id)
|
||||||
|
@ -208,11 +222,6 @@ func (u *User) ValidatePassword(passwd string) bool {
|
||||||
return u.Passwd == newUser.Passwd
|
return u.Passwd == newUser.Passwd
|
||||||
}
|
}
|
||||||
|
|
||||||
// CustomAvatarPath returns user custom avatar file path.
|
|
||||||
func (u *User) CustomAvatarPath() string {
|
|
||||||
return filepath.Join(setting.AvatarUploadPath, com.ToStr(u.Id))
|
|
||||||
}
|
|
||||||
|
|
||||||
// UploadAvatar saves custom avatar for user.
|
// UploadAvatar saves custom avatar for user.
|
||||||
// FIXME: split uploads to different subdirs in case we have massive users.
|
// FIXME: split uploads to different subdirs in case we have massive users.
|
||||||
func (u *User) UploadAvatar(data []byte) error {
|
func (u *User) UploadAvatar(data []byte) error {
|
||||||
|
@ -494,6 +503,8 @@ func ChangeUserName(u *User, newUserName string) (err error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func updateUser(e Engine, u *User) error {
|
func updateUser(e Engine, u *User) error {
|
||||||
|
// Organization does not need e-mail.
|
||||||
|
if !u.IsOrganization() {
|
||||||
u.Email = strings.ToLower(u.Email)
|
u.Email = strings.ToLower(u.Email)
|
||||||
has, err := e.Where("id!=?", u.Id).And("type=?", u.Type).And("email=?", u.Email).Get(new(User))
|
has, err := e.Where("id!=?", u.Id).And("type=?", u.Type).And("email=?", u.Email).Get(new(User))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -502,6 +513,12 @@ func updateUser(e Engine, u *User) error {
|
||||||
return ErrEmailAlreadyUsed{u.Email}
|
return ErrEmailAlreadyUsed{u.Email}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if len(u.AvatarEmail) == 0 {
|
||||||
|
u.AvatarEmail = u.Email
|
||||||
|
}
|
||||||
|
u.Avatar = avatar.HashEmail(u.AvatarEmail)
|
||||||
|
}
|
||||||
|
|
||||||
u.LowerName = strings.ToLower(u.Name)
|
u.LowerName = strings.ToLower(u.Name)
|
||||||
|
|
||||||
if len(u.Location) > 255 {
|
if len(u.Location) > 255 {
|
||||||
|
@ -514,13 +531,8 @@ func updateUser(e Engine, u *User) error {
|
||||||
u.Description = u.Description[:255]
|
u.Description = u.Description[:255]
|
||||||
}
|
}
|
||||||
|
|
||||||
if u.AvatarEmail == "" {
|
|
||||||
u.AvatarEmail = u.Email
|
|
||||||
}
|
|
||||||
u.Avatar = avatar.HashEmail(u.AvatarEmail)
|
|
||||||
|
|
||||||
u.FullName = base.Sanitizer.Sanitize(u.FullName)
|
u.FullName = base.Sanitizer.Sanitize(u.FullName)
|
||||||
_, err = e.Id(u.Id).AllCols().Update(u)
|
_, err := e.Id(u.Id).AllCols().Update(u)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -17,8 +17,7 @@ import (
|
||||||
// \/ /_____/ \/ \/ \/ \/ \/
|
// \/ /_____/ \/ \/ \/ \/ \/
|
||||||
|
|
||||||
type CreateOrgForm struct {
|
type CreateOrgForm struct {
|
||||||
OrgName string `form:"org_name" binding:"Required;AlphaDashDot;MaxSize(30)"`
|
OrgName string `binding:"Required;AlphaDashDot;MaxSize(30)"`
|
||||||
Email string `form:"email" binding:"Required;Email;MaxSize(50)"`
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (f *CreateOrgForm) Validate(ctx *macaron.Context, errs binding.Errors) binding.Errors {
|
func (f *CreateOrgForm) Validate(ctx *macaron.Context, errs binding.Errors) binding.Errors {
|
||||||
|
@ -28,11 +27,9 @@ func (f *CreateOrgForm) Validate(ctx *macaron.Context, errs binding.Errors) bind
|
||||||
type UpdateOrgSettingForm struct {
|
type UpdateOrgSettingForm struct {
|
||||||
OrgUserName string `form:"uname" binding:"Required;AlphaDashDot;MaxSize(30)" locale:"org.org_name_holder"`
|
OrgUserName string `form:"uname" binding:"Required;AlphaDashDot;MaxSize(30)" locale:"org.org_name_holder"`
|
||||||
OrgFullName string `form:"fullname" binding:"MaxSize(100)"`
|
OrgFullName string `form:"fullname" binding:"MaxSize(100)"`
|
||||||
Email string `form:"email" binding:"Required;Email;MaxSize(50)"`
|
|
||||||
Description string `form:"desc" binding:"MaxSize(255)"`
|
Description string `form:"desc" binding:"MaxSize(255)"`
|
||||||
Website string `form:"website" binding:"Url;MaxSize(100)"`
|
Website string `form:"website" binding:"Url;MaxSize(100)"`
|
||||||
Location string `form:"location" binding:"MaxSize(50)"`
|
Location string `form:"location" binding:"MaxSize(50)"`
|
||||||
Avatar string `form:"avatar" binding:"Required;Email;MaxSize(50)"`
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (f *UpdateOrgSettingForm) Validate(ctx *macaron.Context, errs binding.Errors) binding.Errors {
|
func (f *UpdateOrgSettingForm) Validate(ctx *macaron.Context, errs binding.Errors) binding.Errors {
|
||||||
|
|
2
public/css/gogs.min.css
vendored
2
public/css/gogs.min.css
vendored
File diff suppressed because one or more lines are too long
|
@ -17,11 +17,8 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.repository {
|
@create-page-form-input-padding: 250px !important;
|
||||||
@input-padding: 250px !important;
|
#create-page-form {
|
||||||
&.new.repo,
|
|
||||||
&.new.migrate,
|
|
||||||
&.new.fork {
|
|
||||||
form {
|
form {
|
||||||
margin: auto;
|
margin: auto;
|
||||||
width: 800px!important;
|
width: 800px!important;
|
||||||
|
@ -29,16 +26,32 @@
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
.header {
|
.header {
|
||||||
padding-left: @input-padding+30px;
|
padding-left: @create-page-form-input-padding+30px;
|
||||||
}
|
}
|
||||||
.inline.field > label {
|
.inline.field > label {
|
||||||
text-align: right;
|
text-align: right;
|
||||||
width: @input-padding;
|
width: @create-page-form-input-padding;
|
||||||
word-wrap: break-word;
|
word-wrap: break-word;
|
||||||
}
|
}
|
||||||
.help {
|
.help {
|
||||||
margin-left: @input-padding+15px;
|
margin-left: @create-page-form-input-padding+15px;
|
||||||
}
|
}
|
||||||
|
.optional .title {
|
||||||
|
margin-left: @create-page-form-input-padding;
|
||||||
|
}
|
||||||
|
input,
|
||||||
|
textarea {
|
||||||
|
width: 50%!important;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.repository {
|
||||||
|
&.new.repo,
|
||||||
|
&.new.migrate,
|
||||||
|
&.new.fork {
|
||||||
|
#create-page-form;
|
||||||
|
form {
|
||||||
.dropdown {
|
.dropdown {
|
||||||
.dropdown.icon {
|
.dropdown.icon {
|
||||||
margin-top: -7px!important;
|
margin-top: -7px!important;
|
||||||
|
@ -50,13 +63,6 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.optional .title {
|
|
||||||
margin-left: @input-padding;
|
|
||||||
}
|
|
||||||
input,
|
|
||||||
textarea {
|
|
||||||
width: 50%!important;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -66,7 +72,7 @@
|
||||||
width: 50%!important;
|
width: 50%!important;
|
||||||
}
|
}
|
||||||
#auto-init {
|
#auto-init {
|
||||||
margin-left: @input-padding+15px;
|
margin-left: @create-page-form-input-padding+15px;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -14,4 +14,8 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
&.new.org {
|
||||||
|
#create-page-form;
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -59,25 +59,18 @@ func CreatePost(ctx *middleware.Context, form auth.CreateOrgForm) {
|
||||||
|
|
||||||
org := &models.User{
|
org := &models.User{
|
||||||
Name: form.OrgName,
|
Name: form.OrgName,
|
||||||
Email: form.Email,
|
|
||||||
IsActive: true,
|
IsActive: true,
|
||||||
Type: models.ORGANIZATION,
|
Type: models.ORGANIZATION,
|
||||||
}
|
}
|
||||||
|
|
||||||
var err error
|
if err := models.CreateOrganization(org, ctx.User); err != nil {
|
||||||
if err = models.CreateOrganization(org, ctx.User); err != nil {
|
ctx.Data["Err_OrgName"] = true
|
||||||
switch {
|
switch {
|
||||||
case models.IsErrUserAlreadyExist(err):
|
case models.IsErrUserAlreadyExist(err):
|
||||||
ctx.Data["Err_OrgName"] = true
|
|
||||||
ctx.RenderWithErr(ctx.Tr("form.org_name_been_taken"), CREATE, &form)
|
ctx.RenderWithErr(ctx.Tr("form.org_name_been_taken"), CREATE, &form)
|
||||||
case models.IsErrEmailAlreadyUsed(err):
|
|
||||||
ctx.Data["Err_Email"] = true
|
|
||||||
ctx.RenderWithErr(ctx.Tr("form.email_been_used"), CREATE, &form)
|
|
||||||
case models.IsErrNameReserved(err):
|
case models.IsErrNameReserved(err):
|
||||||
ctx.Data["Err_OrgName"] = true
|
|
||||||
ctx.RenderWithErr(ctx.Tr("org.form.name_reserved", err.(models.ErrNameReserved).Name), CREATE, &form)
|
ctx.RenderWithErr(ctx.Tr("org.form.name_reserved", err.(models.ErrNameReserved).Name), CREATE, &form)
|
||||||
case models.IsErrNamePatternNotAllowed(err):
|
case models.IsErrNamePatternNotAllowed(err):
|
||||||
ctx.Data["Err_OrgName"] = true
|
|
||||||
ctx.RenderWithErr(ctx.Tr("org.form.name_pattern_not_allowed", err.(models.ErrNamePatternNotAllowed).Pattern), CREATE, &form)
|
ctx.RenderWithErr(ctx.Tr("org.form.name_pattern_not_allowed", err.(models.ErrNamePatternNotAllowed).Pattern), CREATE, &form)
|
||||||
default:
|
default:
|
||||||
ctx.Handle(500, "CreateOrganization", err)
|
ctx.Handle(500, "CreateOrganization", err)
|
||||||
|
|
|
@ -61,19 +61,11 @@ func SettingsPost(ctx *middleware.Context, form auth.UpdateOrgSettingForm) {
|
||||||
}
|
}
|
||||||
|
|
||||||
org.FullName = form.OrgFullName
|
org.FullName = form.OrgFullName
|
||||||
org.Email = form.Email
|
|
||||||
org.Description = form.Description
|
org.Description = form.Description
|
||||||
org.Website = form.Website
|
org.Website = form.Website
|
||||||
org.Location = form.Location
|
org.Location = form.Location
|
||||||
org.Avatar = base.EncodeMd5(form.Avatar)
|
|
||||||
org.AvatarEmail = form.Avatar
|
|
||||||
if err := models.UpdateUser(org); err != nil {
|
if err := models.UpdateUser(org); err != nil {
|
||||||
if models.IsErrEmailAlreadyUsed(err) {
|
|
||||||
ctx.Data["Err_Email"] = true
|
|
||||||
ctx.RenderWithErr(ctx.Tr("form.email_been_used"), SETTINGS_OPTIONS, &form)
|
|
||||||
} else {
|
|
||||||
ctx.Handle(500, "UpdateUser", err)
|
ctx.Handle(500, "UpdateUser", err)
|
||||||
}
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
log.Trace("Organization setting updated: %s", org.Name)
|
log.Trace("Organization setting updated: %s", org.Name)
|
||||||
|
|
|
@ -1,31 +1,30 @@
|
||||||
{{template "ng/base/head" .}}
|
{{template "base/head" .}}
|
||||||
{{template "ng/base/header" .}}
|
<div class="organization new org">
|
||||||
<div id="sign-wrapper">
|
<div class="ui middle very relaxed page grid">
|
||||||
<form class="form-align form panel sign-panel sign-form container panel-radius" id="sign-up-form" action="{{AppSubUrl}}/org/create" method="post">
|
<div class="column">
|
||||||
|
<form class="ui form" action="{{.Link}}" method="post">
|
||||||
{{.CsrfTokenHtml}}
|
{{.CsrfTokenHtml}}
|
||||||
<div class="panel-header">
|
<h3 class="ui top attached header">
|
||||||
<h2>{{.i18n.Tr "new_org"}}</h2>
|
{{.i18n.Tr "new_org"}}
|
||||||
</div>
|
</h3>
|
||||||
<div class="panel-content">
|
<div class="ui attached segment">
|
||||||
{{template "ng/base/alert" .}}
|
{{template "base/alert" .}}
|
||||||
<div class="field">
|
<div class="inline required field {{if .Err_OrgName}}error{{end}}">
|
||||||
<label class="req" for="org_name">{{.i18n.Tr "org.org_name_holder"}}</label>
|
<label for="org_name">{{.i18n.Tr "org.org_name_holder"}}</label>
|
||||||
<input class="ipt ipt-large ipt-radius {{if .Err_OrgName}}ipt-error{{end}}" id="org_name" name="org_name" type="text" value="{{.org_name}}" required/>
|
<input id="org_name" name="org_name" value="{{.org_name}}" autofocus required>
|
||||||
<label></label>
|
|
||||||
<span class="help">{{.i18n.Tr "org.org_name_helper"}}</span>
|
<span class="help">{{.i18n.Tr "org.org_name_helper"}}</span>
|
||||||
</div>
|
</div>
|
||||||
<div class="field">
|
|
||||||
<label class="req" for="email">{{.i18n.Tr "email"}}</label>
|
<div class="inline field">
|
||||||
<input class="ipt ipt-large ipt-radius {{if .Err_Email}}ipt-error{{end}}" id="email" name="email" type="email" value="{{.email}}" required/>
|
|
||||||
<label></label>
|
<label></label>
|
||||||
<span class="help">{{.i18n.Tr "org.org_email_helper"}}</span>
|
<button class="ui green button">
|
||||||
</div>
|
{{.i18n.Tr "org.create_org"}}
|
||||||
<div class="field">
|
</button>
|
||||||
<span class="form-label"></span>
|
<a class="ui button" href="{{AppSubUrl}}/">{{.i18n.Tr "cancel"}}</a>
|
||||||
<button class="btn btn-large btn-blue btn-radius">{{.i18n.Tr "org.create_org"}}</button>
|
|
||||||
<a class="btn btn-small btn-gray btn-radius" id="repo-create-cancel" href="{{AppSubUrl}}/"><strong>{{.i18n.Tr "cancel"}}</strong></a>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{template "ng/base/footer" .}}
|
{{template "base/footer" .}}
|
|
@ -30,10 +30,6 @@
|
||||||
<label for="full-name">{{.i18n.Tr "org.settings.full_name"}}</label>
|
<label for="full-name">{{.i18n.Tr "org.settings.full_name"}}</label>
|
||||||
<input class="ipt ipt-large ipt-radius {{if .Err_FullName}}ipt-error{{end}}" id="full-name" name="fullname" value="{{.Org.FullName}}" />
|
<input class="ipt ipt-large ipt-radius {{if .Err_FullName}}ipt-error{{end}}" id="full-name" name="fullname" value="{{.Org.FullName}}" />
|
||||||
</div>
|
</div>
|
||||||
<div class="field">
|
|
||||||
<label class="req" for="email">{{.i18n.Tr "email"}}</label>
|
|
||||||
<input class="ipt ipt-large ipt-radius {{if .Err_Email}}ipt-error{{end}}" id="email" name="email" type="email" value="{{.Org.Email}}" required />
|
|
||||||
</div>
|
|
||||||
<div class="field clear">
|
<div class="field clear">
|
||||||
<label class="left" for="desc">{{.i18n.Tr "org.org_desc"}}</label>
|
<label class="left" for="desc">{{.i18n.Tr "org.org_desc"}}</label>
|
||||||
<textarea class="ipt ipt-large ipt-radius {{if .Err_Description}}ipt-error{{end}}" id="desc" name="desc">{{.Org.Description}}</textarea>
|
<textarea class="ipt ipt-large ipt-radius {{if .Err_Description}}ipt-error{{end}}" id="desc" name="desc">{{.Org.Description}}</textarea>
|
||||||
|
@ -46,10 +42,6 @@
|
||||||
<label for="location">{{.i18n.Tr "org.settings.location"}}</label>
|
<label for="location">{{.i18n.Tr "org.settings.location"}}</label>
|
||||||
<input class="ipt ipt-large ipt-radius {{if .Err_Location}}ipt-error{{end}}" id="location" name="location" type="text" value="{{.Org.Location}}" />
|
<input class="ipt ipt-large ipt-radius {{if .Err_Location}}ipt-error{{end}}" id="location" name="location" type="text" value="{{.Org.Location}}" />
|
||||||
</div>
|
</div>
|
||||||
<div class="field {{if DisableGravatar}}hide{{end}}">
|
|
||||||
<label class="req" for="gravatar-email">Gravatar {{.i18n.Tr "email"}}</label>
|
|
||||||
<input class="ipt ipt-large ipt-radius {{if .Err_Avatar}}ipt-error{{end}}" id="gravatar-email" name="avatar" type="text" value="{{.Org.AvatarEmail}}" />
|
|
||||||
</div>
|
|
||||||
<div class="field">
|
<div class="field">
|
||||||
<span class="form-label"></span>
|
<span class="form-label"></span>
|
||||||
<button class="btn btn-green btn-large btn-radius" id="change-orgname-btn" href="#change-orgname-modal">{{.i18n.Tr "org.settings.update_settings"}}</button>
|
<button class="btn btn-green btn-large btn-radius" id="change-orgname-btn" href="#change-orgname-modal">{{.i18n.Tr "org.settings.update_settings"}}</button>
|
||||||
|
|
Reference in a new issue