diff options
| author | İbrahim Serdar Açıkgöz <serdaracikgoz86@gmail.com> | 2018-11-27 18:31:26 +0300 |
|---|---|---|
| committer | İbrahim Serdar Açıkgöz <serdaracikgoz86@gmail.com> | 2018-11-27 18:31:26 +0300 |
| commit | c93bef2e140634d68b3bf37ed55cebb6fd16b2c8 (patch) | |
| tree | 551977ba882bff9d4a6904330b6f4cbf68ab2b3b | |
| parent | performance improvement and modal initiation (diff) | |
| download | gitbatch-c93bef2e140634d68b3bf37ed55cebb6fd16b2c8.tar.gz | |
change remote branch to hierarchical structure and intiate job mechanism.
| -rw-r--r-- | pkg/git/remote.go | 49 | ||||
| -rw-r--r-- | pkg/git/remotebranch.go | 66 | ||||
| -rw-r--r-- | pkg/git/repository.go | 24 | ||||
| -rw-r--r-- | pkg/gui/execview.go | 37 | ||||
| -rw-r--r-- | pkg/gui/gui-util.go | 6 | ||||
| -rw-r--r-- | pkg/gui/gui.go | 28 | ||||
| -rw-r--r-- | pkg/gui/keybindings.go | 8 | ||||
| -rw-r--r-- | pkg/gui/mainview.go | 15 | ||||
| -rw-r--r-- | pkg/gui/remotebranchview.go | 50 | ||||
| -rw-r--r-- | pkg/gui/remotesview.go | 28 | ||||
| -rw-r--r-- | pkg/gui/scheduleview.go | 41 | ||||
| -rw-r--r-- | pkg/job/job.go | 80 | ||||
| -rw-r--r-- | pkg/utils/utils.go | 53 |
13 files changed, 370 insertions, 115 deletions
diff --git a/pkg/git/remote.go b/pkg/git/remote.go index 1651cc2..ec61fd7 100644 --- a/pkg/git/remote.go +++ b/pkg/git/remote.go @@ -1,19 +1,19 @@ package git import ( - "gopkg.in/src-d/go-git.v4/plumbing" - "gopkg.in/src-d/go-git.v4/plumbing/storer" ) type Remote struct { Name string - Reference *plumbing.Reference + URL []string + Branch *RemoteBranch + Branches []*RemoteBranch } func (entity *RepoEntity) NextRemote() error { currentRemoteIndex := 0 for i, remote := range entity.Remotes { - if remote.Reference.Hash() == entity.Remote.Reference.Hash() { + if remote.Name == entity.Remote.Name { currentRemoteIndex = i } } @@ -27,37 +27,26 @@ func (entity *RepoEntity) NextRemote() error { return nil } -func (entity *RepoEntity) loadRemoteBranches() error { +func (entity *RepoEntity) loadRemotes() error { r := entity.Repository entity.Remotes = make([]*Remote, 0) - bs, err := remoteBranchesIter(r.Storer) - if err != nil { - return err + + remotes, err := r.Remotes() + for _, rm := range remotes { + + remote := &Remote{ + Name: rm.Config().Name, + URL: rm.Config().URLs, + } + remote.loadRemoteBranches(&r) + if len(remote.Branches) > 0 { + remote.Branch = remote.Branches[0] + } + entity.Remotes = append(entity.Remotes, remote) + } - defer bs.Close() - err = bs.ForEach(func(b *plumbing.Reference) error { - entity.Remotes = append(entity.Remotes, &Remote{ - Name: b.Name().Short(), - Reference: b, - }) - return nil - }) if err != nil { return err } return err -} - -func remoteBranchesIter(s storer.ReferenceStorer) (storer.ReferenceIter, error) { - refs, err := s.IterReferences() - if err != nil { - return nil, err - } - - return storer.NewReferenceFilteredIter(func(ref *plumbing.Reference) bool { - if ref.Type() == plumbing.HashReference { - return ref.Name().IsRemote() - } - return false - }, refs), nil }
\ No newline at end of file diff --git a/pkg/git/remotebranch.go b/pkg/git/remotebranch.go new file mode 100644 index 0000000..8ccca53 --- /dev/null +++ b/pkg/git/remotebranch.go @@ -0,0 +1,66 @@ +package git + +import ( + "gopkg.in/src-d/go-git.v4" + "gopkg.in/src-d/go-git.v4/plumbing" + "gopkg.in/src-d/go-git.v4/plumbing/storer" + "strings" +) + +type RemoteBranch struct { + Name string + Reference *plumbing.Reference +} + +func (remote *Remote) NextRemoteBranch() error { + currentRemoteIndex := 0 + for i, rb := range remote.Branches { + if rb.Reference.Hash() == remote.Branch.Reference.Hash() { + currentRemoteIndex = i + } + } + // WARNING: DIDN'T CHECK THE LIFE CYCLE + if currentRemoteIndex == len(remote.Branches)-1 { + remote.Branch = remote.Branches[0] + } else { + remote.Branch = remote.Branches[currentRemoteIndex+1] + } + + return nil +} + +func (remote *Remote) loadRemoteBranches(r *git.Repository) error { + remote.Branches = make([]*RemoteBranch, 0) + bs, err := remoteBranchesIter(r.Storer) + if err != nil { + return err + } + defer bs.Close() + err = bs.ForEach(func(b *plumbing.Reference) error { + if strings.Split(b.Name().Short(), "/")[0] == remote.Name { + remote.Branches = append(remote.Branches, &RemoteBranch{ + Name: b.Name().Short(), + Reference: b, + }) + } + return nil + }) + if err != nil { + return err + } + return err +} + +func remoteBranchesIter(s storer.ReferenceStorer) (storer.ReferenceIter, error) { + refs, err := s.IterReferences() + if err != nil { + return nil, err + } + + return storer.NewReferenceFilteredIter(func(ref *plumbing.Reference) bool { + if ref.Type() == plumbing.HashReference { + return ref.Name().IsRemote() + } + return false + }, refs), nil +}
\ No newline at end of file diff --git a/pkg/git/repository.go b/pkg/git/repository.go index 9ecb973..630f4cb 100644 --- a/pkg/git/repository.go +++ b/pkg/git/repository.go @@ -2,13 +2,14 @@ package git import ( "gopkg.in/src-d/go-git.v4" + "github.com/isacikgoz/gitbatch/pkg/utils" "os" "time" - "strings" "errors" ) type RepoEntity struct { + RepoID string Name string AbsPath string Repository git.Repository @@ -34,7 +35,8 @@ func InitializeRepository(directory string) (entity *RepoEntity, err error) { if err != nil { return nil, err } - entity = &RepoEntity{Name: fileInfo.Name(), + entity = &RepoEntity{RepoID: utils.NewHash(), + Name: fileInfo.Name(), AbsPath: directory, Repository: *r, Marked: false, @@ -46,7 +48,7 @@ func InitializeRepository(directory string) (entity *RepoEntity, err error) { } else { return entity, errors.New("There is no commit for this repository: " + directory) } - entity.loadRemoteBranches() + entity.loadRemotes() entity.Branch = entity.GetActiveBranch() if len(entity.Remotes) > 0 { // TODO: tend to take origin/master as default @@ -68,12 +70,13 @@ func (entity *RepoEntity) Unmark() { func (entity *RepoEntity) Pull() error { // TODO: Migrate this code to src-d/go-git // 2018-11-25: tried but it fails, will investigate. - rm := entity.Remote.Reference.Name().Short() - remote := strings.Split(rm, "/")[0] - if err := entity.FetchWithGit(remote); err != nil { + rm := entity.Remote.Name + if err := entity.FetchWithGit(rm); err != nil { return err } - if err := entity.MergeWithGit(rm); err != nil { + entity.Checkout(entity.Branch) + if err := entity.MergeWithGit(entity.Remote.Branch.Name); err != nil { + entity.Refresh() return err } entity.Refresh() @@ -87,9 +90,8 @@ func (entity *RepoEntity) PullTest() error { } func (entity *RepoEntity) Fetch() error { - rm := entity.Remote.Reference.Name().Short() - remote := strings.Split(rm, "/")[0] - if err := entity.FetchWithGit(remote); err != nil { + rm := entity.Remote.Name + if err := entity.FetchWithGit(rm); err != nil { return err } entity.Refresh() @@ -114,7 +116,7 @@ func (entity *RepoEntity) Refresh() error { if err := entity.loadCommits(); err != nil { return err } - if err := entity.loadRemoteBranches(); err != nil { + if err := entity.loadRemotes(); err != nil { return err } return nil diff --git a/pkg/gui/execview.go b/pkg/gui/execview.go index 39a46cb..6371e0e 100644 --- a/pkg/gui/execview.go +++ b/pkg/gui/execview.go @@ -9,8 +9,15 @@ import ( func (gui *Gui) openExecConfirmationView(g *gocui.Gui, v *gocui.View) error { maxX, maxY := g.Size() + err := gui.State.Queue.StartNext() + if err != nil { + return err + } + if mrs,_ := gui.getMarkedEntities(); len(mrs) < 1 { + return nil + } - v, err := g.SetView(execViewFeature.Name, maxX/2-35, maxY/2-5, maxX/2+35, maxY/2+5) + v, err = g.SetView(execViewFeature.Name, maxX/2-35, maxY/2-5, maxX/2+35, maxY/2+5) if err != nil { if err != gocui.ErrUnknownView { return err @@ -35,14 +42,21 @@ func (gui *Gui) openExecConfirmationView(g *gocui.Gui, v *gocui.View) error { } func (gui *Gui) closeExecView(g *gocui.Gui, v *gocui.View) error { - + go g.Update(func(g *gocui.Gui) error { + mainView,_ := g.View(mainViewFeature.Name) + entity, err := gui.getSelectedRepository(g, mainView) + if err != nil { + return err + } + gui.updateCommits(g, entity) + return nil + }) if err := g.DeleteView(v.Name()); err != nil { return nil } if _, err := g.SetCurrentView(mainViewFeature.Name); err != nil { return err } - gui.refreshMain(g) gui.updateKeyBindingsView(g, mainViewFeature.Name) return nil } @@ -62,13 +76,24 @@ func (gui *Gui) execute(g *gocui.Gui, v *gocui.View) error { // here we will be waiting switch mode := gui.State.Mode.ModeID; mode { case FetchMode: - mr.Fetch() + err := mr.Fetch() + if err != nil { + cv, _ := g.View(execViewFeature.Name) + gui.closeExecView(g, cv) + gui.openErrorView(g, err.Error(), "An error occured, manual resolving reuqired") + return nil + } case PullMode: - mr.Pull() + err := mr.Pull() + if err != nil { + cv, _ := g.View(execViewFeature.Name) + gui.closeExecView(g, cv) + gui.openErrorView(g, err.Error(), "It maybe a conflict, manual resolving reuqired") + return nil + } default: return errors.New("No mode is selected") } - gui.refreshViews(g, mr) mr.Unmark() gui.refreshMain(g) } diff --git a/pkg/gui/gui-util.go b/pkg/gui/gui-util.go index 5dd0c0c..2b65e97 100644 --- a/pkg/gui/gui-util.go +++ b/pkg/gui/gui-util.go @@ -24,10 +24,10 @@ func (gui *Gui) refreshViews(g *gocui.Gui, entity *git.RepoEntity) error { if err := gui.updateBranch(g, entity); err != nil { return err } - if err := gui.updateCommits(g, entity); err != nil { - return err + if err := gui.updateRemoteBranches(g, entity); err != nil { + return err } - if err := gui.updateSchedule(g, entity); err != nil { + if err := gui.updateCommits(g, entity); err != nil { return err } return nil diff --git a/pkg/gui/gui.go b/pkg/gui/gui.go index 569e9ce..c171397 100644 --- a/pkg/gui/gui.go +++ b/pkg/gui/gui.go @@ -2,6 +2,7 @@ package gui import ( "github.com/isacikgoz/gitbatch/pkg/git" + "github.com/isacikgoz/gitbatch/pkg/job" "github.com/jroimartin/gocui" "fmt" ) @@ -16,6 +17,7 @@ type guiState struct { Repositories []*git.RepoEntity Directories []string Mode mode + Queue *job.JobQueue } type viewFeature struct { @@ -40,8 +42,9 @@ const ( var ( mainViewFeature = viewFeature{Name: "main", Title: " Matched Repositories "} loadingViewFeature = viewFeature{Name: "loading", Title: " Loading in Progress "} - branchViewFeature = viewFeature{Name: "branch", Title: " Branches "} + branchViewFeature = viewFeature{Name: "branch", Title: " Local Branches "} remoteViewFeature = viewFeature{Name: "remotes", Title: " Remotes "} + remoteBranchViewFeature = viewFeature{Name: "remotebranches", Title: " Remote Branches "} commitViewFeature = viewFeature{Name: "commits", Title: " Commits "} scheduleViewFeature = viewFeature{Name: "schedule", Title: " Schedule "} keybindingsViewFeature = viewFeature{Name: "keybindings", Title: " Keybindings "} @@ -58,6 +61,7 @@ func NewGui(directoies []string) (*Gui, error) { initialState := guiState{ Directories: directoies, Mode: fetchMode, + Queue: job.CreateJobQueue(), } gui := &Gui{ State: initialState, @@ -118,37 +122,37 @@ func (gui *Gui) layout(g *gocui.Gui) error { v.SelFgColor = gocui.ColorBlack v.Overwrite = true } - if v, err := g.SetView(branchViewFeature.Name, int(0.55*float32(maxX)), 0, maxX-1, int(0.20*float32(maxY))-1); err != nil { + if v, err := g.SetView(remoteViewFeature.Name, int(0.55*float32(maxX)), 0, maxX-1, int(0.10*float32(maxY))); err != nil { if err != gocui.ErrUnknownView { return err } - v.Title = branchViewFeature.Title + v.Title = remoteViewFeature.Title v.Wrap = false v.Autoscroll = false } - if v, err := g.SetView(remoteViewFeature.Name, int(0.55*float32(maxX)), int(0.20*float32(maxY)), maxX-1, int(0.40*float32(maxY))); err != nil { + if v, err := g.SetView(remoteBranchViewFeature.Name, int(0.55*float32(maxX)), int(0.10*float32(maxY))+1, maxX-1, int(0.35*float32(maxY))); err != nil { if err != gocui.ErrUnknownView { return err } - v.Title = remoteViewFeature.Title + v.Title = remoteBranchViewFeature.Title v.Wrap = false - v.Overwrite = true + v.Overwrite = false } - if v, err := g.SetView(commitViewFeature.Name, int(0.55*float32(maxX)), int(0.40*float32(maxY))+1, maxX-1, int(0.73*float32(maxY))); err != nil { + if v, err := g.SetView(branchViewFeature.Name, int(0.55*float32(maxX)), int(0.35*float32(maxY))+1, maxX-1, int(0.60*float32(maxY))); err != nil { if err != gocui.ErrUnknownView { return err } - v.Title = commitViewFeature.Title + v.Title = branchViewFeature.Title v.Wrap = false v.Autoscroll = false } - if v, err := g.SetView(scheduleViewFeature.Name, int(0.55*float32(maxX)), int(0.73*float32(maxY))+1, maxX-1, maxY-2); err != nil { + if v, err := g.SetView(commitViewFeature.Name, int(0.55*float32(maxX)), int(0.60*float32(maxY))+1, maxX-1, maxY-2); err != nil { if err != gocui.ErrUnknownView { return err } - v.Title = scheduleViewFeature.Title - v.Wrap = true - v.Autoscroll = true + v.Title = commitViewFeature.Title + v.Wrap = false + v.Autoscroll = false } if v, err := g.SetView(keybindingsViewFeature.Name, -1, maxY-2, maxX, maxY); err != nil { if err != gocui.ErrUnknownView { diff --git a/pkg/gui/keybindings.go b/pkg/gui/keybindings.go index 6605a4d..73f2629 100644 --- a/pkg/gui/keybindings.go +++ b/pkg/gui/keybindings.go @@ -75,6 +75,14 @@ func (gui *Gui) generateKeybindings() error { Vital: false, },{ View: mainViewFeature.Name, + Key: 'z', + Modifier: gocui.ModNone, + Handler: gui.nextRemoteBranch, + Display: "z", + Description: "Iterate over remote branches", + Vital: false, + },{ + View: mainViewFeature.Name, Key: 's', Modifier: gocui.ModNone, Handler: gui.nextCommit, diff --git a/pkg/gui/mainview.go b/pkg/gui/mainview.go index 824fce1..9c69f65 100644 --- a/pkg/gui/mainview.go +++ b/pkg/gui/mainview.go @@ -4,6 +4,7 @@ import ( "fmt" "sync" "github.com/isacikgoz/gitbatch/pkg/git" + "github.com/isacikgoz/gitbatch/pkg/job" "github.com/jroimartin/gocui" "regexp" ) @@ -111,11 +112,23 @@ func (gui *Gui) markRepository(g *gocui.Gui, v *gocui.View) error { } if !r.Marked { r.Mark() + err := gui.State.Queue.AddJob(&job.Job{ + JobType: job.Fetch, + RepoID: r.RepoID, + Name: r.Name, + Args: make([]string, 0), + }) + if err != nil { + return err + } } else { + err := gui.State.Queue.RemoveFromQueue(r.RepoID) + if err != nil { + return err + } r.Unmark() } gui.refreshMain(g) - gui.updateSchedule(g, r) } return nil } diff --git a/pkg/gui/remotebranchview.go b/pkg/gui/remotebranchview.go new file mode 100644 index 0000000..7238f91 --- /dev/null +++ b/pkg/gui/remotebranchview.go @@ -0,0 +1,50 @@ +package gui + +import ( + "github.com/isacikgoz/gitbatch/pkg/git" + "github.com/jroimartin/gocui" + "fmt" +) + +func (gui *Gui) updateRemoteBranches(g *gocui.Gui, entity *git.RepoEntity) error { + var err error + + out, err := g.View(remoteBranchViewFeature.Name) + if err != nil { + return err + } + out.Clear() + currentindex := 0 + trb := len(entity.Remote.Branches) + if trb > 0 { + for i, r := range entity.Remote.Branches { + if r.Name == entity.Remote.Branch.Name { + currentindex = i + fmt.Fprintln(out, selectionIndicator() + r.Name) + continue + } + fmt.Fprintln(out, tab() + r.Name) + } + if err = gui.smartAnchorRelativeToLine(out, currentindex, trb); err != nil { + return err + } + } + return nil +} + +func (gui *Gui) nextRemoteBranch(g *gocui.Gui, v *gocui.View) error { + var err error + entity, err := gui.getSelectedRepository(g, v) + if err != nil { + return err + } + + if err = entity.Remote.NextRemoteBranch(); err != nil { + return err + } + + if err = gui.updateRemoteBranches(g, entity); err != nil { + return err + } + return nil +}
\ No newline at end of file diff --git a/pkg/gui/remotesview.go b/pkg/gui/remotesview.go index e674f43..5d3b924 100644 --- a/pkg/gui/remotesview.go +++ b/pkg/gui/remotesview.go @@ -2,6 +2,7 @@ package gui import ( "github.com/isacikgoz/gitbatch/pkg/git" + "github.com/isacikgoz/gitbatch/pkg/utils" "github.com/jroimartin/gocui" "fmt" ) @@ -17,16 +18,20 @@ func (gui *Gui) updateRemotes(g *gocui.Gui, entity *git.RepoEntity) error { currentindex := 0 totalRemotes := len(entity.Remotes) - for i, r := range entity.Remotes { - if r.Name == entity.Remote.Name { - currentindex = i - fmt.Fprintln(out, selectionIndicator() + r.Name) - continue + if totalRemotes > 0 { + for i, r := range entity.Remotes { + URLtype, shortURL := utils.TrimRemoteURL(r.URL[0]) + suffix := "(" + URLtype + ")" + " " + shortURL + if r.Name == entity.Remote.Name { + currentindex = i + fmt.Fprintln(out, selectionIndicator() + r.Name + ": " + suffix) + continue + } + fmt.Fprintln(out, tab() + r.Name + ": " + suffix) } - fmt.Fprintln(out, tab() + r.Name) - } - if err = gui.smartAnchorRelativeToLine(out, currentindex, totalRemotes); err != nil { - return err + if err = gui.smartAnchorRelativeToLine(out, currentindex, totalRemotes); err != nil { + return err + } } return nil } @@ -37,13 +42,14 @@ func (gui *Gui) nextRemote(g *gocui.Gui, v *gocui.View) error { if err != nil { return err } - if err = entity.NextRemote(); err != nil { return err } - if err = gui.updateRemotes(g, entity); err != nil { return err } + if err = gui.updateRemoteBranches(g, entity); err != nil { + return err + } return nil }
\ No newline at end of file diff --git a/pkg/gui/scheduleview.go b/pkg/gui/scheduleview.go deleted file mode 100644 index 2b83605..0000000 --- a/pkg/gui/scheduleview.go +++ /dev/null @@ -1,41 +0,0 @@ -package gui - -import ( - "github.com/isacikgoz/gitbatch/pkg/git" - "github.com/jroimartin/gocui" - "fmt" - "strings" -) - -func (gui *Gui) updateSchedule(g *gocui.Gui, entity *git.RepoEntity) error { - var err error - - out, err := g.View(scheduleViewFeature.Name) - if err != nil { - return err - } - out.Clear() - if entity.Marked { - - rm := entity.Remote.Reference.Name().Short() - switch mode := gui.State.Mode.ModeID; mode { - case FetchMode: - remote := strings.Split(rm, "/")[0] - s := green.Sprint("$") + " git fetch " + remote - fmt.Fprintln(out, s) - case PullMode: - s := green.Sprint("$") + " git checkout " + entity.Branch.Name + " " + green.Sprint("✓") - fmt.Fprintln(out, s) - remote := strings.Split(rm, "/")[0] - s = green.Sprint("$") + " git fetch " + remote - fmt.Fprintln(out, s) - s = green.Sprint("$") + " git merge " + entity.Remote.Name - fmt.Fprintln(out, s) - default: - fmt.Fprintln(out, "No mode selected") - } - } else { - return nil - } - return nil -}
\ No newline at end of file diff --git a/pkg/job/job.go b/pkg/job/job.go new file mode 100644 index 0000000..6bd5f4d --- /dev/null +++ b/pkg/job/job.go @@ -0,0 +1,80 @@ +package job + +import ( + "fmt" + "errors" +) + +type Job struct { + JobType JobType + RepoID string + Name string + Args []string +} + +type JobQueue struct { + series []*Job +} + +type JobType string + +const ( + Fetch JobType = "FETCH" + Pull JobType = "PULL" +) + +func CreateJob() (j *Job, err error) { + fmt.Println("Job created.") + return j, nil +} + +func (job *Job) start() error { + switch mode := job.JobType; mode { + case Fetch: + fmt.Println("Fetch operation is started") + case Pull: + fmt.Println("Pull operation is started") + default: + return errors.New("Unknown job type") + } + return nil +} + +func CreateJobQueue() (jobQueue *JobQueue) { + s := make([]*Job, 0) + return &JobQueue{ + series: s, + } +} + +func (jobQueue *JobQueue) AddJob(j *Job) error { + for _, job := range jobQueue.series { + if job.RepoID == j.RepoID && job.JobType == j.JobType { + return errors.New("Same job already is in the queue") + } + } + jobQueue.series = append(jobQueue.series, j) + return nil +} + +func (jobQueue *JobQueue) StartNext() error { + lastJob := jobQueue.series[len(jobQueue.series)-1] + if err := lastJob.start(); err != nil { + return err + } + return nil +} + +func (jobQueue *JobQueue) RemoveFromQueue(repoID string) error { + removed := false + for i, job := range jobQueue.series { + if job.RepoID == repoID{ + jobQueue.series = append(jobQueue.series[:i], jobQueue.series[i+1:]...) + removed = true + } + } + if !removed { + return errors.New("There is no job with given repoID") + } + return nil +}
\ No newline at end of file diff --git a/pkg/utils/utils.go b/pkg/utils/utils.go index 6a8b007..4855cbd 100644 --- a/pkg/utils/utils.go +++ b/pkg/utils/utils.go @@ -2,8 +2,16 @@ package utils import ( "strings" + "regexp" + "math/rand" + "time" + "fmt" + "crypto/sha1" ) +var characterRunes = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789") +var src = rand.NewSource(time.Now().UnixNano()) + func TrimTrailingNewline(str string) string { if strings.HasSuffix(str, "\n") { return str[:len(str)-1] @@ -16,4 +24,49 @@ func Min(x, y int) int { return x } return y +} + +func TrimRemoteURL(url string) (urltype string, shorturl string) { + ressh := regexp.MustCompile(`git@`) + rehttp := regexp.MustCompile(`http://`) + rehttps := regexp.MustCompile(`https://`) + + if ressh.MatchString(url) { + shorturl = ressh.Split(url, 5)[1] + urltype = "ssh" + } else if rehttp.MatchString(url) { + shorturl = rehttp.Split(url, 5)[1] + urltype = "http" + } else if rehttps.MatchString(url) { + shorturl = rehttps.Split(url, 5)[1] + urltype = "https" + } + return urltype, shorturl +} + +// RandomString generates a random string of n length +func RandomString(n int) string { + b := make([]rune, n) + for i := range b { + b[i] = characterRunes[rand.Intn(len(characterRunes))] + } + return string(b) +} + +// NewSHA1Hash generates a new SHA1 hash based on +// a random number of characters. +func NewHash(n ...int) string { + noRandomCharacters := 32 + + if len(n) > 0 { + noRandomCharacters = n[0] + } + + randString := RandomString(noRandomCharacters) + + hash := sha1.New() + hash.Write([]byte(randString)) + bs := hash.Sum(nil) + + return fmt.Sprintf("%x", bs) }
\ No newline at end of file |
