Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add RemoteAddress to mirrors #26952

Merged
merged 3 commits into from
Sep 16, 2023
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions models/migrations/migrations.go
Original file line number Diff line number Diff line change
Expand Up @@ -530,6 +530,8 @@ var migrations = []Migration{
NewMigration("Add Action Schedule Table", v1_21.AddActionScheduleTable),
// v274 -> v275
NewMigration("Add Actions artifacts expiration date", v1_21.AddExpiredUnixColumnInActionArtifactTable),
// v275 -> v276
NewMigration("Add RemoteAddress to mirrors", v1_21.AddRemoteAddressToMirrors),
}

// GetCurrentDBVersion returns the current db version
Expand Down
132 changes: 132 additions & 0 deletions models/migrations/v1_21/v275.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,132 @@
// Copyright 2023 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT

package v1_21 //nolint

import (
"context"
"fmt"
"path/filepath"
"strings"

"code.gitea.io/gitea/modules/git"
giturl "code.gitea.io/gitea/modules/git/url"
"code.gitea.io/gitea/modules/setting"

"xorm.io/xorm"
)

func AddRemoteAddressToMirrors(x *xorm.Engine) error {
type Mirror struct {
RemoteAddress string `xorm:"VARCHAR(2048)"`
}

type PushMirror struct {
RemoteAddress string `xorm:"VARCHAR(2048)"`
}

if err := x.Sync(new(Mirror), new(PushMirror)); err != nil {
return err
}

if err := migratePullMirrors(x); err != nil {
return err
}

return migratePushMirrors(x)
}

func migratePullMirrors(x *xorm.Engine) error {
type Mirror struct {
ID int64 `xorm:"pk autoincr"`
RepoID int64 `xorm:"INDEX"`
RemoteAddress string `xorm:"VARCHAR(2048)"`
}

sess := x.NewSession()
defer sess.Close()

if err := sess.Begin(); err != nil {
return err
}

if err := sess.Iterate(new(Mirror), func(_ int, bean any) error {
m := bean.(*Mirror)
remoteAddress, err := getRemoteAddress(sess, m.RepoID, "origin")
if err != nil {
return err
}

m.RemoteAddress = remoteAddress

_, err = sess.ID(m.ID).Cols("remote_address").Update(m)
return err
}); err != nil {
return err
}

return sess.Commit()
}

func migratePushMirrors(x *xorm.Engine) error {
type PushMirror struct {
ID int64 `xorm:"pk autoincr"`
RepoID int64 `xorm:"INDEX"`
RemoteName string
RemoteAddress string `xorm:"VARCHAR(2048)"`
}

sess := x.NewSession()
defer sess.Close()

if err := sess.Begin(); err != nil {
return err
}

if err := sess.Iterate(new(PushMirror), func(_ int, bean any) error {
m := bean.(*PushMirror)
remoteAddress, err := getRemoteAddress(sess, m.RepoID, m.RemoteName)
if err != nil {
return err
}

m.RemoteAddress = remoteAddress

_, err = sess.ID(m.ID).Cols("remote_address").Update(m)
return err
}); err != nil {
return err
}

return sess.Commit()
}

func getRemoteAddress(sess *xorm.Session, repoID int64, remoteName string) (string, error) {
var ownerName string
var repoName string
has, err := sess.
Table("repository").
Cols("owner_name", "lower_name").
Where("id=?", repoID).
Get(&ownerName, &repoName)
if err != nil {
return "", err
} else if !has {
return "", fmt.Errorf("repository [%v] not found", repoID)
}

repoPath := filepath.Join(setting.RepoRootPath, strings.ToLower(ownerName), strings.ToLower(repoName)+".git")

remoteURL, err := git.GetRemoteAddress(context.Background(), repoPath, remoteName)
if err != nil {
return "", err
}

u, err := giturl.Parse(remoteURL)
if err != nil {
return "", err
}
u.User = nil

return u.String(), nil
}
2 changes: 1 addition & 1 deletion models/repo/mirror.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ type Mirror struct {
LFS bool `xorm:"lfs_enabled NOT NULL DEFAULT false"`
LFSEndpoint string `xorm:"lfs_endpoint TEXT"`

Address string `xorm:"-"`
RemoteAddress string `xorm:"VARCHAR(2048)"`
}

func init() {
Expand Down
10 changes: 6 additions & 4 deletions models/repo/pushmirror.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,17 +20,19 @@ var ErrPushMirrorNotExist = util.NewNotExistErrorf("PushMirror does not exist")

// PushMirror represents mirror information of a repository.
type PushMirror struct {
ID int64 `xorm:"pk autoincr"`
RepoID int64 `xorm:"INDEX"`
Repo *Repository `xorm:"-"`
RemoteName string
ID int64 `xorm:"pk autoincr"`
RepoID int64 `xorm:"INDEX"`
Repo *Repository `xorm:"-"`
RemoteName string
RemoteAddress string `xorm:"VARCHAR(2048)"`

SyncOnCommit bool `xorm:"NOT NULL DEFAULT true"`
Interval time.Duration
CreatedUnix timeutil.TimeStamp `xorm:"created"`
LastUpdateUnix timeutil.TimeStamp `xorm:"INDEX last_update"`
LastError string `xorm:"text"`
}

type PushMirrorOptions struct {
ID int64
RepoID int64
Expand Down
8 changes: 2 additions & 6 deletions models/repo/repo.go
Original file line number Diff line number Diff line change
Expand Up @@ -191,12 +191,8 @@ func (repo *Repository) SanitizedOriginalURL() string {
if repo.OriginalURL == "" {
return ""
}
u, err := url.Parse(repo.OriginalURL)
if err != nil {
return ""
}
u.User = nil
return u.String()
u, _ := util.SanitizeURL(repo.OriginalURL)
return u
}

// text representations to be returned in SizeDetail.Name
Expand Down
5 changes: 5 additions & 0 deletions modules/repository/repo.go
Original file line number Diff line number Diff line change
Expand Up @@ -180,12 +180,17 @@ func MigrateRepositoryGitData(ctx context.Context, u *user_model.User,
defer committer.Close()

if opts.Mirror {
remoteAddress, err := util.SanitizeURL(opts.CloneAddr)
if err != nil {
return repo, err
}
mirrorModel := repo_model.Mirror{
RepoID: repo.ID,
Interval: setting.Mirror.DefaultInterval,
EnablePrune: true,
NextUpdateUnix: timeutil.TimeStampNow().AddDuration(setting.Mirror.DefaultInterval),
LFS: opts.LFS,
RemoteAddress: remoteAddress,
}
if opts.LFS {
mirrorModel.LFSEndpoint = opts.LFSEndpoint
Expand Down
9 changes: 9 additions & 0 deletions modules/util/url.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,3 +39,12 @@ func URLJoin(base string, elems ...string) string {
}
return joinedURL
}

func SanitizeURL(s string) (string, error) {
u, err := url.Parse(s)
delvh marked this conversation as resolved.
Show resolved Hide resolved
if err != nil {
return "", err
delvh marked this conversation as resolved.
Show resolved Hide resolved
}
u.User = nil
return u.String(), nil
}
17 changes: 12 additions & 5 deletions routers/api/v1/repo/mirror.go
Original file line number Diff line number Diff line change
Expand Up @@ -343,12 +343,19 @@ func CreatePushMirror(ctx *context.APIContext, mirrorOption *api.CreatePushMirro
return
}

remoteAddress, err := util.SanitizeURL(mirrorOption.RemoteAddress)
if err != nil {
ctx.ServerError("SanitizeURL", err)
return
}

pushMirror := &repo_model.PushMirror{
RepoID: repo.ID,
Repo: repo,
RemoteName: fmt.Sprintf("remote_mirror_%s", remoteSuffix),
Interval: interval,
SyncOnCommit: mirrorOption.SyncOnCommit,
RepoID: repo.ID,
Repo: repo,
RemoteName: fmt.Sprintf("remote_mirror_%s", remoteSuffix),
Interval: interval,
SyncOnCommit: mirrorOption.SyncOnCommit,
RemoteAddress: remoteAddress,
}

if err = repo_model.InsertPushMirror(ctx, pushMirror); err != nil {
Expand Down
24 changes: 19 additions & 5 deletions routers/web/repo/setting/setting.go
Original file line number Diff line number Diff line change
Expand Up @@ -243,6 +243,13 @@ func SettingsPost(ctx *context.Context) {
return
}

remoteAddress, err := util.SanitizeURL(form.MirrorAddress)
if err != nil {
ctx.ServerError("SanitizeURL", err)
return
}
pullMirror.RemoteAddress = remoteAddress

form.LFS = form.LFS && setting.LFS.StartServer

if len(form.LFSEndpoint) > 0 {
Expand Down Expand Up @@ -397,12 +404,19 @@ func SettingsPost(ctx *context.Context) {
return
}

remoteAddress, err := util.SanitizeURL(form.PushMirrorAddress)
if err != nil {
ctx.ServerError("SanitizeURL", err)
return
}

m := &repo_model.PushMirror{
RepoID: repo.ID,
Repo: repo,
RemoteName: fmt.Sprintf("remote_mirror_%s", remoteSuffix),
SyncOnCommit: form.PushMirrorSyncOnCommit,
Interval: interval,
RepoID: repo.ID,
Repo: repo,
RemoteName: fmt.Sprintf("remote_mirror_%s", remoteSuffix),
SyncOnCommit: form.PushMirrorSyncOnCommit,
Interval: interval,
RemoteAddress: remoteAddress,
}
if err := repo_model.InsertPushMirror(ctx, m); err != nil {
ctx.ServerError("InsertPushMirror", err)
Expand Down
11 changes: 1 addition & 10 deletions routers/web/repo/view.go
Original file line number Diff line number Diff line change
Expand Up @@ -627,15 +627,6 @@ func markupRender(ctx *context.Context, renderCtx *markup.RenderContext, input i
return escaped, output, err
}

func safeURL(address string) string {
u, err := url.Parse(address)
if err != nil {
return address
}
u.User = nil
return u.String()
}

func checkHomeCodeViewable(ctx *context.Context) {
if len(ctx.Repo.Units) > 0 {
if ctx.Repo.Repository.IsBeingCreated() {
Expand All @@ -659,7 +650,7 @@ func checkHomeCodeViewable(ctx *context.Context) {

ctx.Data["Repo"] = ctx.Repo
ctx.Data["MigrateTask"] = task
ctx.Data["CloneAddr"] = safeURL(cfg.CloneAddr)
ctx.Data["CloneAddr"], _ = util.SanitizeURL(cfg.CloneAddr)
ctx.Data["Failed"] = task.Status == structs.TaskStatusFailed
ctx.HTML(http.StatusOK, tplMigrating)
return
Expand Down
17 changes: 1 addition & 16 deletions services/convert/mirror.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,35 +5,20 @@ package convert

import (
repo_model "code.gitea.io/gitea/models/repo"
"code.gitea.io/gitea/modules/git"
api "code.gitea.io/gitea/modules/structs"
)

// ToPushMirror convert from repo_model.PushMirror and remoteAddress to api.TopicResponse
func ToPushMirror(pm *repo_model.PushMirror) (*api.PushMirror, error) {
repo := pm.GetRepository()
remoteAddress, err := getRemoteAddress(repo, pm.RemoteName)
if err != nil {
return nil, err
}
return &api.PushMirror{
RepoName: repo.Name,
RemoteName: pm.RemoteName,
RemoteAddress: remoteAddress,
RemoteAddress: pm.RemoteAddress,
CreatedUnix: pm.CreatedUnix.FormatLong(),
LastUpdateUnix: pm.LastUpdateUnix.FormatLong(),
LastError: pm.LastError,
Interval: pm.Interval.String(),
SyncOnCommit: pm.SyncOnCommit,
}, nil
}

func getRemoteAddress(repo *repo_model.Repository, remoteName string) (string, error) {
url, err := git.GetRemoteURL(git.DefaultContext, repo.RepoPath(), remoteName)
if err != nil {
return "", err
}
// remove confidential information
url.User = nil
return url.String(), nil
}
3 changes: 1 addition & 2 deletions templates/repo/header.tmpl
Original file line number Diff line number Diff line change
Expand Up @@ -37,8 +37,7 @@
{{end}}
</div>
{{if $.PullMirror}}
{{$address := MirrorRemoteAddress $.Context . $.PullMirror.GetRemoteName false}}
<div class="fork-flag">{{$.locale.Tr "repo.mirror_from"}} <a target="_blank" rel="noopener noreferrer" href="{{$address.Address}}">{{$address.Address}}</a></div>
<div class="fork-flag">{{$.locale.Tr "repo.mirror_from"}} <a target="_blank" rel="noopener noreferrer" href="{{$.PullMirror.RemoteAddress}}">{{$.PullMirror.RemoteAddress}}</a></div>
{{end}}
{{if .IsFork}}<div class="fork-flag">{{$.locale.Tr "repo.forked_from"}} <a href="{{.BaseRepo.Link}}">{{.BaseRepo.FullName}}</a></div>{{end}}
{{if .IsGenerated}}<div class="fork-flag">{{$.locale.Tr "repo.generated_from"}} <a href="{{.TemplateRepo.Link}}">{{.TemplateRepo.FullName}}</a></div>{{end}}
Expand Down
7 changes: 3 additions & 4 deletions templates/repo/settings/options.tmpl
Original file line number Diff line number Diff line change
Expand Up @@ -123,7 +123,7 @@
{{else if $isWorkingPullMirror}}
<tbody>
<tr>
<td>{{(MirrorRemoteAddress $.Context .Repository .PullMirror.GetRemoteName false).Address}}</td>
<td>{{.PullMirror.RemoteAddress}}</td>
<td>{{$.locale.Tr "repo.settings.mirror_settings.direction.pull"}}</td>
<td>{{DateTime "full" .PullMirror.UpdatedUnix}}</td>
<td class="right aligned">
Expand Down Expand Up @@ -200,8 +200,7 @@
<tbody>
{{range .PushMirrors}}
<tr>
{{$address := MirrorRemoteAddress $.Context $.Repository .GetRemoteName true}}
<td class="gt-word-break">{{$address.Address}}</td>
<td class="gt-word-break">{{.RemoteAddress}}</td>
<td>{{$.locale.Tr "repo.settings.mirror_settings.direction.push"}}</td>
<td>{{if .LastUpdateUnix}}{{DateTime "full" .LastUpdateUnix}}{{else}}{{$.locale.Tr "never"}}{{end}} {{if .LastError}}<div class="ui red label" data-tooltip-content="{{.LastError}}">{{$.locale.Tr "error"}}</div>{{end}}</td>
<td class="right aligned">
Expand All @@ -211,7 +210,7 @@
data-tooltip-content="{{$.locale.Tr "repo.settings.mirror_settings.push_mirror.edit_sync_time"}}"
data-modal-push-mirror-edit-id="{{.ID}}"
data-modal-push-mirror-edit-interval="{{.Interval}}"
data-modal-push-mirror-edit-address="{{$address.Address}}"
data-modal-push-mirror-edit-address="{{.RemoteAddress}}"
>
{{svg "octicon-pencil" 14}}
</button>
Expand Down