]> source.dussan.org Git - gitea.git/commitdiff
Allow Organisations to have a E-Mail (#25082)
authorJakobDev <jakobdev@gmx.de>
Tue, 25 Jul 2023 08:26:27 +0000 (10:26 +0200)
committerGitHub <noreply@github.com>
Tue, 25 Jul 2023 08:26:27 +0000 (08:26 +0000)
Resolves #25057

This adds a E-Mail field to Organisations. The E-Mail is just shown on
the Profile when it is visited by a logged in User. The E-mail is not
used for something else.

**Screenshots:**

![grafik](https://github.com/go-gitea/gitea/assets/15185051/a8d622b3-7278-4c08-984b-9c5ebfdb5471)

![grafik](https://github.com/go-gitea/gitea/assets/15185051/6dcb1dd7-d04b-49eb-bc96-6582cfe9757b)

---------

Co-authored-by: Denys Konovalov <kontakt@denyskon.de>
Co-authored-by: Denys Konovalov <privat@denyskon.de>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: Giteabot <teabot@gitea.io>
modules/structs/org.go
options/locale/locale_en-US.ini
routers/api/v1/org/org.go
routers/web/org/setting.go
services/convert/convert.go
services/forms/org.go
templates/org/home.tmpl
templates/org/settings/options.tmpl
templates/swagger/v1_json.tmpl
tests/integration/api_user_orgs_test.go
web_src/css/org.css

index 7c83dcdee7e4da3dd494cae8a55ddd18fc531635..c0a545ac1c3fa1ddc46826dca6438533d7c61284 100644 (file)
@@ -8,6 +8,7 @@ type Organization struct {
        ID                        int64  `json:"id"`
        Name                      string `json:"name"`
        FullName                  string `json:"full_name"`
+       Email                     string `json:"email"`
        AvatarURL                 string `json:"avatar_url"`
        Description               string `json:"description"`
        Website                   string `json:"website"`
@@ -32,6 +33,7 @@ type CreateOrgOption struct {
        // required: true
        UserName    string `json:"username" binding:"Required;Username;MaxSize(40)"`
        FullName    string `json:"full_name" binding:"MaxSize(100)"`
+       Email       string `json:"email" binding:"MaxSize(255)"`
        Description string `json:"description" binding:"MaxSize(255)"`
        Website     string `json:"website" binding:"ValidUrl;MaxSize(255)"`
        Location    string `json:"location" binding:"MaxSize(50)"`
@@ -46,6 +48,7 @@ type CreateOrgOption struct {
 // EditOrgOption options for editing an organization
 type EditOrgOption struct {
        FullName    string `json:"full_name" binding:"MaxSize(100)"`
+       Email       string `json:"email" binding:"MaxSize(255)"`
        Description string `json:"description" binding:"MaxSize(255)"`
        Website     string `json:"website" binding:"ValidUrl;MaxSize(255)"`
        Location    string `json:"location" binding:"MaxSize(50)"`
index 8784ab6878feb82903c05b0cb479b08e0b3aa35d..4eb60e5c9b6e78927c027deb9881051961225f40 100644 (file)
@@ -2532,6 +2532,7 @@ form.create_org_not_allowed = You are not allowed to create an organization.
 settings = Settings
 settings.options = Organization
 settings.full_name = Full Name
+settings.email = Contact Email
 settings.website = Website
 settings.location = Location
 settings.permission = Permissions
index 4e30ad17620f3e2f8b32f386bb6f8d53921ce0f0..b0666c87f89cee6e47d4219d6eda691c98c8904e 100644 (file)
@@ -255,6 +255,7 @@ func Create(ctx *context.APIContext) {
        org := &organization.Organization{
                Name:                      form.UserName,
                FullName:                  form.FullName,
+               Email:                     form.Email,
                Description:               form.Description,
                Website:                   form.Website,
                Location:                  form.Location,
@@ -299,7 +300,15 @@ func Get(ctx *context.APIContext) {
                ctx.NotFound("HasOrgOrUserVisible", nil)
                return
        }
-       ctx.JSON(http.StatusOK, convert.ToOrganization(ctx, ctx.Org.Organization))
+
+       org := convert.ToOrganization(ctx, ctx.Org.Organization)
+
+       // Don't show Mail, when User is not logged in
+       if ctx.Doer == nil {
+               org.Email = ""
+       }
+
+       ctx.JSON(http.StatusOK, org)
 }
 
 // Edit change an organization's information
@@ -328,6 +337,7 @@ func Edit(ctx *context.APIContext) {
        form := web.GetForm(ctx).(*api.EditOrgOption)
        org := ctx.Org.Organization
        org.FullName = form.FullName
+       org.Email = form.Email
        org.Description = form.Description
        org.Website = form.Website
        org.Location = form.Location
index bd558f78b89a11990b32844fb335a03aa733699e..f63b2e9f064e051bb3b46bb9f5265f1c39c98bc4 100644 (file)
@@ -100,6 +100,7 @@ func SettingsPost(ctx *context.Context) {
        }
 
        org.FullName = form.FullName
+       org.Email = form.Email
        org.Description = form.Description
        org.Website = form.Website
        org.Location = form.Location
index cb246a8b4b79c88c335b24283c235e1d00b70f5a..a7a777e8bd6ba6792bcb2d530c2cbf92774269b1 100644 (file)
@@ -289,6 +289,7 @@ func ToOrganization(ctx context.Context, org *organization.Organization) *api.Or
                Name:                      org.Name,
                UserName:                  org.Name,
                FullName:                  org.FullName,
+               Email:                     org.Email,
                Description:               org.Description,
                Website:                   org.Website,
                Location:                  org.Location,
index c333bead316dd7b01c1b86d45d83ec05a0b5c2e7..6e2d787516d26132727f86601b37a8eb6a6f41f3 100644 (file)
@@ -38,6 +38,7 @@ func (f *CreateOrgForm) Validate(req *http.Request, errs binding.Errors) binding
 type UpdateOrgSettingForm struct {
        Name                      string `binding:"Required;Username;MaxSize(40)" locale:"org.org_name_holder"`
        FullName                  string `binding:"MaxSize(100)"`
+       Email                     string `binding:"MaxSize(255)"`
        Description               string `binding:"MaxSize(255)"`
        Website                   string `binding:"ValidUrl;MaxSize(255)"`
        Location                  string `binding:"MaxSize(50)"`
index 967b31e7a8f5eaada04bf74ae936cdddde65f4b9..445df520a9f32b4e791253501eed1e7f629c7150 100644 (file)
                        </div>
                        {{if $.RenderedDescription}}<div class="render-content markup">{{$.RenderedDescription|Str2html}}</div>{{end}}
                        <div class="text grey meta">
-                               {{if .Org.Location}}<div class="item">{{svg "octicon-location"}} <span>{{.Org.Location}}</span></div>{{end}}
-                               {{if .Org.Website}}<div class="item">{{svg "octicon-link"}} <a target="_blank" rel="noopener noreferrer me" href="{{.Org.Website}}">{{.Org.Website}}</a></div>{{end}}
+                               {{if .Org.Location}}<div class="flex-text-block">{{svg "octicon-location"}} <span>{{.Org.Location}}</span></div>{{end}}
+                               {{if .Org.Website}}<div class="flex-text-block">{{svg "octicon-link"}} <a target="_blank" rel="noopener noreferrer me" href="{{.Org.Website}}">{{.Org.Website}}</a></div>{{end}}
+                               {{if $.IsSigned}}
+                                       {{if .Org.Email}}<div class="flex-text-block">{{svg "octicon-mail"}} <a class="muted" href="mailto:{{.Org.Email}}">{{.Org.Email}}</a></div>{{end}}
+                               {{end}}
                        </div>
                </div>
                <div class="right menu">
index 846ebaee1adae44c033e9987ac13b115670d0792..683b88646770fc6bfbd84667c2a282f02c8467d5 100644 (file)
                                                        <label for="full_name">{{.locale.Tr "org.org_full_name_holder"}}</label>
                                                        <input id="full_name" name="full_name" value="{{.Org.FullName}}" maxlength="100">
                                                </div>
+                                               <div class="field {{if .Err_Email}}error{{end}}">
+                                                       <label for="email">{{.locale.Tr "org.settings.email"}}</label>
+                                                       <input id="email" name="email" type="email" value="{{.Org.Email}}" maxlength="255">
+                                               </div>
                                                <div class="field {{if .Err_Description}}error{{end}}">
                                                        <label for="description">{{$.locale.Tr "org.org_desc"}}</label>
                                                        <textarea id="description" name="description" rows="2" maxlength="255">{{.Org.Description}}</textarea>
index 69874bdc75f043de4bb99317d37f068dda56c8e5..7cb9bac95d38d14ed0e0e87c70607c59d6b014b8 100644 (file)
           "type": "string",
           "x-go-name": "Description"
         },
+        "email": {
+          "type": "string",
+          "x-go-name": "Email"
+        },
         "full_name": {
           "type": "string",
           "x-go-name": "FullName"
           "type": "string",
           "x-go-name": "Description"
         },
+        "email": {
+          "type": "string",
+          "x-go-name": "Email"
+        },
         "full_name": {
           "type": "string",
           "x-go-name": "FullName"
           "type": "string",
           "x-go-name": "Description"
         },
+        "email": {
+          "type": "string",
+          "x-go-name": "Email"
+        },
         "full_name": {
           "type": "string",
           "x-go-name": "FullName"
index 323facaf48ed9d833993a5fa0ec58856bed5f569..f76c61f818f5ec56cf2060cf2a60f1e82c925042 100644 (file)
@@ -36,6 +36,7 @@ func TestUserOrgs(t *testing.T) {
                        Name:        user17.Name,
                        UserName:    user17.Name,
                        FullName:    user17.FullName,
+                       Email:       user17.Email,
                        AvatarURL:   user17.AvatarLink(db.DefaultContext),
                        Description: "",
                        Website:     "",
@@ -47,6 +48,7 @@ func TestUserOrgs(t *testing.T) {
                        Name:        user3.Name,
                        UserName:    user3.Name,
                        FullName:    user3.FullName,
+                       Email:       user3.Email,
                        AvatarURL:   user3.AvatarLink(db.DefaultContext),
                        Description: "",
                        Website:     "",
@@ -106,6 +108,7 @@ func TestMyOrgs(t *testing.T) {
                        Name:        user17.Name,
                        UserName:    user17.Name,
                        FullName:    user17.FullName,
+                       Email:       user17.Email,
                        AvatarURL:   user17.AvatarLink(db.DefaultContext),
                        Description: "",
                        Website:     "",
@@ -117,6 +120,7 @@ func TestMyOrgs(t *testing.T) {
                        Name:        user3.Name,
                        UserName:    user3.Name,
                        FullName:    user3.FullName,
+                       Email:       user3.Email,
                        AvatarURL:   user3.AvatarLink(db.DefaultContext),
                        Description: "",
                        Website:     "",
index d579443ce14abce87b9085b504eda79309f1f11a..9e1fa38941f31e3af7bf9044a1d5ec5bd3f6b489 100644 (file)
   margin-bottom: 10px;
 }
 
-.organization.profile #org-info .meta .item {
-  display: inline-block;
-  margin-right: 10px;
-}
-
-.organization.profile #org-info .meta .item .icon {
-  margin-right: 5px;
+.organization.profile #org-info .meta {
+  display: flex;
+  align-items: center;
+  flex-wrap: wrap;
+  gap: 8px;
 }
 
 .organization.profile .ui.top.header .ui.right {