Start working on diff page
This commit is contained in:
		
							parent
							
								
									c1a3d4fefb
								
							
						
					
					
						commit
						87de66561c
					
				
					 7 changed files with 591 additions and 430 deletions
				
			
		|  | @ -5,7 +5,7 @@ Gogs(Go Git Service) is a Self Hosted Git Service in the Go Programming Language | |||
| 
 | ||||
|  | ||||
| 
 | ||||
| ##### Current version: 0.1.7 Alpha | ||||
| ##### Current version: 0.1.8 Alpha | ||||
| 
 | ||||
| #### Other language version | ||||
| 
 | ||||
|  |  | |||
|  | @ -5,7 +5,7 @@ Gogs(Go Git Service) 是一个由 Go 语言编写的自助 Git 托管服务。 | |||
| 
 | ||||
|  | ||||
| 
 | ||||
| ##### 当前版本:0.1.7 Alpha | ||||
| ##### 当前版本:0.1.8 Alpha | ||||
| 
 | ||||
| ## 开发目的 | ||||
| 
 | ||||
|  | @ -16,7 +16,7 @@ Gogs 完全使用 Go 语言来实现对 Git 数据的操作,实现 **零** 依 | |||
| ## 项目概览 | ||||
| 
 | ||||
| - 有关项目设计、开发说明、变更日志和路线图,请通过  [Wiki](https://github.com/gogits/gogs/wiki) 查看。 | ||||
| - 您可以到 [Trello Broad](https://trello.com/b/uxAoeLUl/gogs-go-git-service) 跟随开发团队的脚步。 | ||||
| - 您可以到 [Trello Board](https://trello.com/b/uxAoeLUl/gogs-go-git-service) 跟随开发团队的脚步。 | ||||
| - 想要先睹为快?通过 [在线体验](http://try.gogits.org/Unknown/gogs) 或查看 **安装部署 -> 二进制安装** 小节。 | ||||
| - 使用过程中遇到问题?尝试从 [故障排查](https://github.com/gogits/gogs/wiki/Troubleshooting) 页面获取帮助。 | ||||
| 
 | ||||
|  |  | |||
							
								
								
									
										137
									
								
								diff.txt
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										137
									
								
								diff.txt
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,137 @@ | |||
| commit c1a3d4fefbbbf332cd1cedda66e93bf40cc9713d | ||||
| Author: Unknown <joe2010xtmf@163.com> | ||||
| Date:   Tue Mar 25 21:37:18 2014 -0400 | ||||
| 
 | ||||
|     Add mail notify for creating issue | ||||
| 
 | ||||
| diff --git a/gogs.go b/gogs.go | ||||
| index b62580f..f5a328a 100644 | ||||
| --- a/gogs.go | ||||
| +++ b/gogs.go | ||||
| @@ -19,7 +19,7 @@ import ( | ||||
|  // Test that go1.2 tag above is included in builds. main.go refers to this definition. | ||||
|  const go12tag = true | ||||
|   | ||||
| -const APP_VER = "0.1.7.0325" | ||||
| +const APP_VER = "0.1.8.0325" | ||||
|   | ||||
|  func init() { | ||||
|  	base.AppVer = APP_VER | ||||
| diff --git a/models/issue.go b/models/issue.go | ||||
| index 2bdd083..2de6568 100644 | ||||
| --- a/models/issue.go | ||||
| +++ b/models/issue.go | ||||
| @@ -59,7 +59,6 @@ func CreateIssue(userId, repoId, milestoneId, assigneeId int64, name, labels, co | ||||
|  		Content:     content, | ||||
|  	} | ||||
|  	_, err = orm.Insert(issue) | ||||
| -	// TODO: newIssueAction | ||||
|  	return issue, err | ||||
|  } | ||||
|   | ||||
| diff --git a/modules/mailer/mail.go b/modules/mailer/mail.go | ||||
| index 92acd20..d0decbe 100644 | ||||
| --- a/modules/mailer/mail.go | ||||
| +++ b/modules/mailer/mail.go | ||||
| @@ -6,6 +6,7 @@ package mailer | ||||
|   | ||||
|  import ( | ||||
|  	"encoding/hex" | ||||
| +	"errors" | ||||
|  	"fmt" | ||||
|   | ||||
|  	"github.com/gogits/gogs/models" | ||||
| @@ -15,12 +16,17 @@ import ( | ||||
|  ) | ||||
|   | ||||
|  // Create New mail message use MailFrom and MailUser | ||||
| -func NewMailMessage(To []string, subject, body string) Message { | ||||
| -	msg := NewHtmlMessage(To, base.MailService.User, subject, body) | ||||
| +func NewMailMessageFrom(To []string, from, subject, body string) Message { | ||||
| +	msg := NewHtmlMessage(To, from, subject, body) | ||||
|  	msg.User = base.MailService.User | ||||
|  	return msg | ||||
|  } | ||||
|   | ||||
| +// Create New mail message use MailFrom and MailUser | ||||
| +func NewMailMessage(To []string, subject, body string) Message { | ||||
| +	return NewMailMessageFrom(To, base.MailService.User, subject, body) | ||||
| +} | ||||
| + | ||||
|  func GetMailTmplData(user *models.User) map[interface{}]interface{} { | ||||
|  	data := make(map[interface{}]interface{}, 10) | ||||
|  	data["AppName"] = base.AppName | ||||
| @@ -84,3 +90,33 @@ func SendActiveMail(r *middleware.Render, user *models.User) { | ||||
|   | ||||
|  	SendAsync(&msg) | ||||
|  } | ||||
| + | ||||
| +// SendNotifyMail sends mail notification of all watchers. | ||||
| +func SendNotifyMail(userId, repoId int64, userName, repoName, subject, content string) error { | ||||
| +	watches, err := models.GetWatches(repoId) | ||||
| +	if err != nil { | ||||
| +		return errors.New("mail.NotifyWatchers(get watches): " + err.Error()) | ||||
| +	} | ||||
| + | ||||
| +	tos := make([]string, 0, len(watches)) | ||||
| +	for i := range watches { | ||||
| +		uid := watches[i].UserId | ||||
| +		if userId == uid { | ||||
| +			continue | ||||
| +		} | ||||
| +		u, err := models.GetUserById(uid) | ||||
| +		if err != nil { | ||||
| +			return errors.New("mail.NotifyWatchers(get user): " + err.Error()) | ||||
| +		} | ||||
| +		tos = append(tos, u.Email) | ||||
| +	} | ||||
| + | ||||
| +	if len(tos) == 0 { | ||||
| +		return nil | ||||
| +	} | ||||
| + | ||||
| +	msg := NewMailMessageFrom(tos, userName, subject, content) | ||||
| +	msg.Info = fmt.Sprintf("Subject: %s, send notify emails", subject) | ||||
| +	SendAsync(&msg) | ||||
| +	return nil | ||||
| +} | ||||
| diff --git a/modules/mailer/mailer.go b/modules/mailer/mailer.go | ||||
| index da63e01..63861d8 100644 | ||||
| --- a/modules/mailer/mailer.go | ||||
| +++ b/modules/mailer/mailer.go | ||||
| @@ -33,7 +33,7 @@ func (m Message) Content() string { | ||||
|  	} | ||||
|   | ||||
|  	// create mail content | ||||
| -	content := "From: " + m.User + "<" + m.From + | ||||
| +	content := "From: " + m.From + "<" + m.User + | ||||
|  		">\r\nSubject: " + m.Subject + "\r\nContent-Type: " + contentType + "\r\n\r\n" + m.Body | ||||
|  	return content | ||||
|  } | ||||
| diff --git a/routers/repo/issue.go b/routers/repo/issue.go | ||||
| index fc5bb98..242593f 100644 | ||||
| --- a/routers/repo/issue.go | ||||
| +++ b/routers/repo/issue.go | ||||
| @@ -13,6 +13,7 @@ import ( | ||||
|  	"github.com/gogits/gogs/modules/auth" | ||||
|  	"github.com/gogits/gogs/modules/base" | ||||
|  	"github.com/gogits/gogs/modules/log" | ||||
| +	"github.com/gogits/gogs/modules/mailer" | ||||
|  	"github.com/gogits/gogs/modules/middleware" | ||||
|  ) | ||||
|   | ||||
| @@ -86,6 +87,14 @@ func CreateIssue(ctx *middleware.Context, params martini.Params, form auth.Creat | ||||
|  		return | ||||
|  	} | ||||
|   | ||||
| +	// Mail watchers. | ||||
| +	if base.Service.NotifyMail { | ||||
| +		if err = mailer.SendNotifyMail(ctx.User.Id, ctx.Repo.Repository.Id, ctx.User.Name, ctx.Repo.Repository.Name, issue.Name, issue.Content); err != nil { | ||||
| +			ctx.Handle(200, "issue.CreateIssue", err) | ||||
| +			return | ||||
| +		} | ||||
| +	} | ||||
| + | ||||
|  	log.Trace("%d Issue created: %d", ctx.Repo.Repository.Id, issue.Id) | ||||
|  	ctx.Redirect(fmt.Sprintf("/%s/%s/issues/%d", params["username"], params["reponame"], issue.Index)) | ||||
|  } | ||||
							
								
								
									
										272
									
								
								models/git.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										272
									
								
								models/git.go
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,272 @@ | |||
| // Copyright 2014 The Gogs Authors. All rights reserved.
 | ||||
| // Use of this source code is governed by a MIT-style
 | ||||
| // license that can be found in the LICENSE file.
 | ||||
| 
 | ||||
| package models | ||||
| 
 | ||||
| import ( | ||||
| 	"container/list" | ||||
| 	"fmt" | ||||
| 	"path" | ||||
| 	"strings" | ||||
| 
 | ||||
| 	"github.com/Unknwon/com" | ||||
| 
 | ||||
| 	"github.com/gogits/git" | ||||
| ) | ||||
| 
 | ||||
| // RepoFile represents a file object in git repository.
 | ||||
| type RepoFile struct { | ||||
| 	*git.TreeEntry | ||||
| 	Path   string | ||||
| 	Size   int64 | ||||
| 	Repo   *git.Repository | ||||
| 	Commit *git.Commit | ||||
| } | ||||
| 
 | ||||
| // LookupBlob returns the content of an object.
 | ||||
| func (file *RepoFile) LookupBlob() (*git.Blob, error) { | ||||
| 	if file.Repo == nil { | ||||
| 		return nil, ErrRepoFileNotLoaded | ||||
| 	} | ||||
| 
 | ||||
| 	return file.Repo.LookupBlob(file.Id) | ||||
| } | ||||
| 
 | ||||
| // GetBranches returns all branches of given repository.
 | ||||
| func GetBranches(userName, reposName string) ([]string, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	refs, err := repo.AllReferences() | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	brs := make([]string, len(refs)) | ||||
| 	for i, ref := range refs { | ||||
| 		brs[i] = ref.Name | ||||
| 	} | ||||
| 	return brs, nil | ||||
| } | ||||
| 
 | ||||
| func GetTargetFile(userName, reposName, branchName, commitId, rpath string) (*RepoFile, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	commit, err := repo.GetCommit(branchName, commitId) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	parts := strings.Split(path.Clean(rpath), "/") | ||||
| 
 | ||||
| 	var entry *git.TreeEntry | ||||
| 	tree := commit.Tree | ||||
| 	for i, part := range parts { | ||||
| 		if i == len(parts)-1 { | ||||
| 			entry = tree.EntryByName(part) | ||||
| 			if entry == nil { | ||||
| 				return nil, ErrRepoFileNotExist | ||||
| 			} | ||||
| 		} else { | ||||
| 			tree, err = repo.SubTree(tree, part) | ||||
| 			if err != nil { | ||||
| 				return nil, err | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	size, err := repo.ObjectSize(entry.Id) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	repoFile := &RepoFile{ | ||||
| 		entry, | ||||
| 		rpath, | ||||
| 		size, | ||||
| 		repo, | ||||
| 		commit, | ||||
| 	} | ||||
| 
 | ||||
| 	return repoFile, nil | ||||
| } | ||||
| 
 | ||||
| // GetReposFiles returns a list of file object in given directory of repository.
 | ||||
| func GetReposFiles(userName, reposName, branchName, commitId, rpath string) ([]*RepoFile, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	commit, err := repo.GetCommit(branchName, commitId) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	var repodirs []*RepoFile | ||||
| 	var repofiles []*RepoFile | ||||
| 	commit.Tree.Walk(func(dirname string, entry *git.TreeEntry) int { | ||||
| 		if dirname == rpath { | ||||
| 			// TODO: size get method shoule be improved
 | ||||
| 			size, err := repo.ObjectSize(entry.Id) | ||||
| 			if err != nil { | ||||
| 				return 0 | ||||
| 			} | ||||
| 
 | ||||
| 			var cm = commit | ||||
| 			var i int | ||||
| 			for { | ||||
| 				i = i + 1 | ||||
| 				//fmt.Println(".....", i, cm.Id(), cm.ParentCount())
 | ||||
| 				if cm.ParentCount() == 0 { | ||||
| 					break | ||||
| 				} else if cm.ParentCount() == 1 { | ||||
| 					pt, _ := repo.SubTree(cm.Parent(0).Tree, dirname) | ||||
| 					if pt == nil { | ||||
| 						break | ||||
| 					} | ||||
| 					pEntry := pt.EntryByName(entry.Name) | ||||
| 					if pEntry == nil || !pEntry.Id.Equal(entry.Id) { | ||||
| 						break | ||||
| 					} else { | ||||
| 						cm = cm.Parent(0) | ||||
| 					} | ||||
| 				} else { | ||||
| 					var emptyCnt = 0 | ||||
| 					var sameIdcnt = 0 | ||||
| 					var lastSameCm *git.Commit | ||||
| 					//fmt.Println(".....", cm.ParentCount())
 | ||||
| 					for i := 0; i < cm.ParentCount(); i++ { | ||||
| 						//fmt.Println("parent", i, cm.Parent(i).Id())
 | ||||
| 						p := cm.Parent(i) | ||||
| 						pt, _ := repo.SubTree(p.Tree, dirname) | ||||
| 						var pEntry *git.TreeEntry | ||||
| 						if pt != nil { | ||||
| 							pEntry = pt.EntryByName(entry.Name) | ||||
| 						} | ||||
| 
 | ||||
| 						//fmt.Println("pEntry", pEntry)
 | ||||
| 
 | ||||
| 						if pEntry == nil { | ||||
| 							emptyCnt = emptyCnt + 1 | ||||
| 							if emptyCnt+sameIdcnt == cm.ParentCount() { | ||||
| 								if lastSameCm == nil { | ||||
| 									goto loop | ||||
| 								} else { | ||||
| 									cm = lastSameCm | ||||
| 									break | ||||
| 								} | ||||
| 							} | ||||
| 						} else { | ||||
| 							//fmt.Println(i, "pEntry", pEntry.Id, "entry", entry.Id)
 | ||||
| 							if !pEntry.Id.Equal(entry.Id) { | ||||
| 								goto loop | ||||
| 							} else { | ||||
| 								lastSameCm = cm.Parent(i) | ||||
| 								sameIdcnt = sameIdcnt + 1 | ||||
| 								if emptyCnt+sameIdcnt == cm.ParentCount() { | ||||
| 									// TODO: now follow the first parent commit?
 | ||||
| 									cm = lastSameCm | ||||
| 									//fmt.Println("sameId...")
 | ||||
| 									break | ||||
| 								} | ||||
| 							} | ||||
| 						} | ||||
| 					} | ||||
| 				} | ||||
| 			} | ||||
| 
 | ||||
| 		loop: | ||||
| 
 | ||||
| 			rp := &RepoFile{ | ||||
| 				entry, | ||||
| 				path.Join(dirname, entry.Name), | ||||
| 				size, | ||||
| 				repo, | ||||
| 				cm, | ||||
| 			} | ||||
| 
 | ||||
| 			if entry.IsFile() { | ||||
| 				repofiles = append(repofiles, rp) | ||||
| 			} else if entry.IsDir() { | ||||
| 				repodirs = append(repodirs, rp) | ||||
| 			} | ||||
| 		} | ||||
| 		return 0 | ||||
| 	}) | ||||
| 
 | ||||
| 	return append(repodirs, repofiles...), nil | ||||
| } | ||||
| 
 | ||||
| func GetCommit(userName, repoName, branchname, commitid string) (*git.Commit, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, repoName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	return repo.GetCommit(branchname, commitid) | ||||
| } | ||||
| 
 | ||||
| // GetCommits returns all commits of given branch of repository.
 | ||||
| func GetCommits(userName, reposName, branchname string) (*list.List, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 	r, err := repo.LookupReference(fmt.Sprintf("refs/heads/%s", branchname)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 	return r.AllCommits() | ||||
| } | ||||
| 
 | ||||
| type DiffFile struct { | ||||
| 	Name               string | ||||
| 	Addition, Deletion int | ||||
| 	Type               string | ||||
| 	Content            []string | ||||
| } | ||||
| 
 | ||||
| type Diff struct { | ||||
| 	NumFiles                     int // Number of file has been changed.
 | ||||
| 	TotalAddition, TotalDeletion int | ||||
| 	Files                        []*DiffFile | ||||
| } | ||||
| 
 | ||||
| func GetDiff(repoPath, commitid string) (*Diff, error) { | ||||
| 	stdout, _, err := com.ExecCmdDir(repoPath, "git", "show", commitid) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	// Sperate parts by file.
 | ||||
| 	parts := strings.Split(stdout, "diff --git ") | ||||
| 
 | ||||
| 	// First part is commit information.
 | ||||
| 	// Check if it's a merge.
 | ||||
| 	mergeIndex := strings.Index(parts[0], "merge") | ||||
| 	if mergeIndex > -1 { | ||||
| 		mergeCommit := strings.SplitN(strings.Split(parts[0], "\n")[1], "", 3)[2] | ||||
| 		return GetDiff(repoPath, mergeCommit) | ||||
| 	} | ||||
| 
 | ||||
| 	diff := &Diff{NumFiles: len(parts[1:])} | ||||
| 	diff.Files = make([]*DiffFile, 0, diff.NumFiles) | ||||
| 	for _, part := range parts[1:] { | ||||
| 		infos := strings.SplitN(part, "\n", 6) | ||||
| 		infos[5] = strings.TrimSuffix(strings.TrimSuffix(infos[5], "\n"), "\n\\ No newline at end of file") | ||||
| 
 | ||||
| 		file := &DiffFile{ | ||||
| 			Name:    strings.TrimPrefix(strings.Split(infos[0], " ")[0], "a/"), | ||||
| 			Content: strings.Split(infos[5], "\n"), | ||||
| 		} | ||||
| 		diff.Files = append(diff.Files, file) | ||||
| 	} | ||||
| 	return diff, nil | ||||
| } | ||||
							
								
								
									
										242
									
								
								models/repo.go
									
									
									
									
									
								
							
							
						
						
									
										242
									
								
								models/repo.go
									
									
									
									
									
								
							|  | @ -5,17 +5,14 @@ | |||
| package models | ||||
| 
 | ||||
| import ( | ||||
| 	"container/list" | ||||
| 	"errors" | ||||
| 	"fmt" | ||||
| 	"io/ioutil" | ||||
| 	"os" | ||||
| 	"os/exec" | ||||
| 	"path" | ||||
| 	"path/filepath" | ||||
| 	"regexp" | ||||
| 	"strings" | ||||
| 	"sync" | ||||
| 	"time" | ||||
| 	"unicode/utf8" | ||||
| 
 | ||||
|  | @ -36,8 +33,6 @@ var ( | |||
| 	ErrRepoFileNotLoaded = fmt.Errorf("repo file not loaded") | ||||
| ) | ||||
| 
 | ||||
| var gitInitLocker = sync.Mutex{} | ||||
| 
 | ||||
| var ( | ||||
| 	LanguageIgns, Licenses []string | ||||
| ) | ||||
|  | @ -222,33 +217,21 @@ func extractGitBareZip(repoPath string) error { | |||
| } | ||||
| 
 | ||||
| // initRepoCommit temporarily changes with work directory.
 | ||||
| func initRepoCommit(tmpPath string, sig *git.Signature) error { | ||||
| 	gitInitLocker.Lock() | ||||
| 	defer gitInitLocker.Unlock() | ||||
| 
 | ||||
| 	// Change work directory.
 | ||||
| 	curPath, err := os.Getwd() | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} else if err = os.Chdir(tmpPath); err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 	defer os.Chdir(curPath) | ||||
| 
 | ||||
| func initRepoCommit(tmpPath string, sig *git.Signature) (err error) { | ||||
| 	var stderr string | ||||
| 	if _, stderr, err = com.ExecCmd("git", "add", "--all"); err != nil { | ||||
| 	if _, stderr, err = com.ExecCmdDir(tmpPath, "git", "add", "--all"); err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 	log.Info("stderr(1): %s", stderr) | ||||
| 	if _, stderr, err = com.ExecCmd("git", "commit", fmt.Sprintf("--author='%s <%s>'", sig.Name, sig.Email), | ||||
| 	log.Trace("stderr(1): %s", stderr) | ||||
| 	if _, stderr, err = com.ExecCmdDir(tmpPath, "git", "commit", fmt.Sprintf("--author='%s <%s>'", sig.Name, sig.Email), | ||||
| 		"-m", "Init commit"); err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 	log.Info("stderr(2): %s", stderr) | ||||
| 	if _, stderr, err = com.ExecCmd("git", "push", "origin", "master"); err != nil { | ||||
| 	log.Trace("stderr(2): %s", stderr) | ||||
| 	if _, stderr, err = com.ExecCmdDir(tmpPath, "git", "push", "origin", "master"); err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 	log.Info("stderr(3): %s", stderr) | ||||
| 	log.Trace("stderr(3): %s", stderr) | ||||
| 	return nil | ||||
| } | ||||
| 
 | ||||
|  | @ -562,214 +545,3 @@ func UnWatchRepository() { | |||
| func ForkRepository(reposName string, userId int64) { | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| // RepoFile represents a file object in git repository.
 | ||||
| type RepoFile struct { | ||||
| 	*git.TreeEntry | ||||
| 	Path   string | ||||
| 	Size   int64 | ||||
| 	Repo   *git.Repository | ||||
| 	Commit *git.Commit | ||||
| } | ||||
| 
 | ||||
| // LookupBlob returns the content of an object.
 | ||||
| func (file *RepoFile) LookupBlob() (*git.Blob, error) { | ||||
| 	if file.Repo == nil { | ||||
| 		return nil, ErrRepoFileNotLoaded | ||||
| 	} | ||||
| 
 | ||||
| 	return file.Repo.LookupBlob(file.Id) | ||||
| } | ||||
| 
 | ||||
| // GetBranches returns all branches of given repository.
 | ||||
| func GetBranches(userName, reposName string) ([]string, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	refs, err := repo.AllReferences() | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	brs := make([]string, len(refs)) | ||||
| 	for i, ref := range refs { | ||||
| 		brs[i] = ref.Name | ||||
| 	} | ||||
| 	return brs, nil | ||||
| } | ||||
| 
 | ||||
| func GetTargetFile(userName, reposName, branchName, commitId, rpath string) (*RepoFile, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	commit, err := repo.GetCommit(branchName, commitId) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	parts := strings.Split(path.Clean(rpath), "/") | ||||
| 
 | ||||
| 	var entry *git.TreeEntry | ||||
| 	tree := commit.Tree | ||||
| 	for i, part := range parts { | ||||
| 		if i == len(parts)-1 { | ||||
| 			entry = tree.EntryByName(part) | ||||
| 			if entry == nil { | ||||
| 				return nil, ErrRepoFileNotExist | ||||
| 			} | ||||
| 		} else { | ||||
| 			tree, err = repo.SubTree(tree, part) | ||||
| 			if err != nil { | ||||
| 				return nil, err | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	size, err := repo.ObjectSize(entry.Id) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	repoFile := &RepoFile{ | ||||
| 		entry, | ||||
| 		rpath, | ||||
| 		size, | ||||
| 		repo, | ||||
| 		commit, | ||||
| 	} | ||||
| 
 | ||||
| 	return repoFile, nil | ||||
| } | ||||
| 
 | ||||
| // GetReposFiles returns a list of file object in given directory of repository.
 | ||||
| func GetReposFiles(userName, reposName, branchName, commitId, rpath string) ([]*RepoFile, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	commit, err := repo.GetCommit(branchName, commitId) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	var repodirs []*RepoFile | ||||
| 	var repofiles []*RepoFile | ||||
| 	commit.Tree.Walk(func(dirname string, entry *git.TreeEntry) int { | ||||
| 		if dirname == rpath { | ||||
| 			// TODO: size get method shoule be improved
 | ||||
| 			size, err := repo.ObjectSize(entry.Id) | ||||
| 			if err != nil { | ||||
| 				return 0 | ||||
| 			} | ||||
| 
 | ||||
| 			var cm = commit | ||||
| 			var i int | ||||
| 			for { | ||||
| 				i = i + 1 | ||||
| 				//fmt.Println(".....", i, cm.Id(), cm.ParentCount())
 | ||||
| 				if cm.ParentCount() == 0 { | ||||
| 					break | ||||
| 				} else if cm.ParentCount() == 1 { | ||||
| 					pt, _ := repo.SubTree(cm.Parent(0).Tree, dirname) | ||||
| 					if pt == nil { | ||||
| 						break | ||||
| 					} | ||||
| 					pEntry := pt.EntryByName(entry.Name) | ||||
| 					if pEntry == nil || !pEntry.Id.Equal(entry.Id) { | ||||
| 						break | ||||
| 					} else { | ||||
| 						cm = cm.Parent(0) | ||||
| 					} | ||||
| 				} else { | ||||
| 					var emptyCnt = 0 | ||||
| 					var sameIdcnt = 0 | ||||
| 					var lastSameCm *git.Commit | ||||
| 					//fmt.Println(".....", cm.ParentCount())
 | ||||
| 					for i := 0; i < cm.ParentCount(); i++ { | ||||
| 						//fmt.Println("parent", i, cm.Parent(i).Id())
 | ||||
| 						p := cm.Parent(i) | ||||
| 						pt, _ := repo.SubTree(p.Tree, dirname) | ||||
| 						var pEntry *git.TreeEntry | ||||
| 						if pt != nil { | ||||
| 							pEntry = pt.EntryByName(entry.Name) | ||||
| 						} | ||||
| 
 | ||||
| 						//fmt.Println("pEntry", pEntry)
 | ||||
| 
 | ||||
| 						if pEntry == nil { | ||||
| 							emptyCnt = emptyCnt + 1 | ||||
| 							if emptyCnt+sameIdcnt == cm.ParentCount() { | ||||
| 								if lastSameCm == nil { | ||||
| 									goto loop | ||||
| 								} else { | ||||
| 									cm = lastSameCm | ||||
| 									break | ||||
| 								} | ||||
| 							} | ||||
| 						} else { | ||||
| 							//fmt.Println(i, "pEntry", pEntry.Id, "entry", entry.Id)
 | ||||
| 							if !pEntry.Id.Equal(entry.Id) { | ||||
| 								goto loop | ||||
| 							} else { | ||||
| 								lastSameCm = cm.Parent(i) | ||||
| 								sameIdcnt = sameIdcnt + 1 | ||||
| 								if emptyCnt+sameIdcnt == cm.ParentCount() { | ||||
| 									// TODO: now follow the first parent commit?
 | ||||
| 									cm = lastSameCm | ||||
| 									//fmt.Println("sameId...")
 | ||||
| 									break | ||||
| 								} | ||||
| 							} | ||||
| 						} | ||||
| 					} | ||||
| 				} | ||||
| 			} | ||||
| 
 | ||||
| 		loop: | ||||
| 
 | ||||
| 			rp := &RepoFile{ | ||||
| 				entry, | ||||
| 				path.Join(dirname, entry.Name), | ||||
| 				size, | ||||
| 				repo, | ||||
| 				cm, | ||||
| 			} | ||||
| 
 | ||||
| 			if entry.IsFile() { | ||||
| 				repofiles = append(repofiles, rp) | ||||
| 			} else if entry.IsDir() { | ||||
| 				repodirs = append(repodirs, rp) | ||||
| 			} | ||||
| 		} | ||||
| 		return 0 | ||||
| 	}) | ||||
| 
 | ||||
| 	return append(repodirs, repofiles...), nil | ||||
| } | ||||
| 
 | ||||
| func GetCommit(userName, repoName, branchname, commitid string) (*git.Commit, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, repoName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 
 | ||||
| 	return repo.GetCommit(branchname, commitid) | ||||
| } | ||||
| 
 | ||||
| // GetCommits returns all commits of given branch of repository.
 | ||||
| func GetCommits(userName, reposName, branchname string) (*list.List, error) { | ||||
| 	repo, err := git.OpenRepository(RepoPath(userName, reposName)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 	r, err := repo.LookupReference(fmt.Sprintf("refs/heads/%s", branchname)) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 	return r.AllCommits() | ||||
| } | ||||
|  |  | |||
|  | @ -34,8 +34,24 @@ func Commits(ctx *middleware.Context, params martini.Params) { | |||
| 	ctx.HTML(200, "repo/commits") | ||||
| } | ||||
| 
 | ||||
| func Diff(ctx *middleware.Context,params martini.Params){ | ||||
| 	ctx.Data["Title"] = "commit-sha" | ||||
| func Diff(ctx *middleware.Context, params martini.Params) { | ||||
| 	commit, err := models.GetCommit(params["username"], params["reponame"], params["branchname"], params["commitid"]) | ||||
| 	if err != nil { | ||||
| 		ctx.Handle(404, "repo.Diff", err) | ||||
| 		return | ||||
| 	} | ||||
| 
 | ||||
| 	diff, err := models.GetDiff(models.RepoPath(params["username"], params["reponame"]), params["commitid"]) | ||||
| 	if err != nil { | ||||
| 		ctx.Handle(404, "repo.Diff", err) | ||||
| 		return | ||||
| 	} | ||||
| 
 | ||||
| 	shortSha := params["commitid"][:7] | ||||
| 	ctx.Data["Title"] = commit.Message() + " · " + shortSha | ||||
| 	ctx.Data["Commit"] = commit | ||||
| 	ctx.Data["ShortSha"] = shortSha | ||||
| 	ctx.Data["Diff"] = diff | ||||
| 	ctx.Data["IsRepoToolbarCommits"] = true | ||||
| 	ctx.HTML(200,"repo/diff") | ||||
| 	ctx.HTML(200, "repo/diff") | ||||
| } | ||||
|  |  | |||
|  | @ -7,239 +7,203 @@ | |||
|         <div class="panel panel-info diff-box diff-head-box"> | ||||
|             <div class="panel-heading"> | ||||
|                 <a class="pull-right btn btn-primary btn-sm" href="#commit-source">Browse Source</a> | ||||
|                 <h4>bsongen: support for custom tags</h4> | ||||
|                 <h4>{{.Commit.Message}}</h4> | ||||
|             </div> | ||||
|             <div class="panel-body"> | ||||
|                 <span class="pull-right"> | ||||
|                     commit <span class="label label-default sha">commit-sha</span> | ||||
|                     commit <span class="label label-default sha">{{.ShortSha}}</span> | ||||
|                 </span> | ||||
|                 <p class="author"> | ||||
|                     <img class="avatar" src="#" alt=""/> | ||||
|                     <a class="name" href="#"><strong>author-name</strong></a> | ||||
|                     <span class="time">times-ago</span> | ||||
|                     <img class="avatar" src="{{AvatarLink .Commit.Author.Email}}" alt=""/> | ||||
|                     <a class="name" href="#"><strong>{{.Commit.Author.Name}}</strong></a> | ||||
|                     <span class="time">{{TimeSince .Commit.Author.When}}</span> | ||||
|                 </p> | ||||
|             </div> | ||||
|         </div> | ||||
| 
 | ||||
|         <div class="diff-detail-box diff-box"> | ||||
|             <a class="pull-right btn btn-default" data-toggle="collapse" data-target="#diff-files">Show Diff Files</a> | ||||
|             <a class="pull-right btn btn-default" data-toggle="collapse" data-target="#diff-files">Show Diff Stats</a> | ||||
|             <p class="showing"> | ||||
|                 <i class="fa fa-retweet"></i> | ||||
|                 <strong> 5 changed files</strong> with <strong>25 additions</strong> and <strong>9 deletions</strong>. | ||||
|                 <strong> {{.Diff.NumFiles}} changed files</strong> with <strong>{{.Diff.TotalAddition}} additions</strong> and <strong>{{.Diff.TotalDeletion}} deletions</strong>. | ||||
|             </p> | ||||
|             <ol class="detail-files collapse" id="diff-files"> | ||||
|                 {{range .Diff.Files}} | ||||
|                 <li> | ||||
|                     <div class="diff-counter count pull-right"> | ||||
|                         <span class="add" data-line="2">2</span> | ||||
|                         <span class="add" data-line="{{.Addition}}">{{.Addition}}</span> | ||||
|                         <span class="bar"> | ||||
|                             <span class="pull-left add"></span> | ||||
|                             <span class="pull-left del"></span> | ||||
|                         </span> | ||||
|                         <span class="del" data-line="4">4</span> | ||||
|                         <span class="del" data-line="{{.Deletion}}">{{.Deletion}}</span> | ||||
|                     </div> | ||||
|                     <!-- todo finish all file status, now modify, add, delete and rename --> | ||||
|                     <span class="status modify" data-toggle="tooltip" data-placement="right" title="modify"> </span> | ||||
|                     <a class="file" href="#diff-1">gopmweb.go</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <div class="diff-counter count pull-right"> | ||||
|                         <span class="add" data-line="666">666</span> | ||||
|                         <span class="bar"> | ||||
|                             <span class="pull-left add"></span> | ||||
|                             <span class="pull-left del"></span> | ||||
|                         </span> | ||||
|                         <span class="del" data-line="44">44</span> | ||||
|                     </div> | ||||
|                     <span class="status add" data-toggle="tooltip" data-placement="right" title="add"> </span> | ||||
|                     <a class="file" href="#diff-2">static/img/favicon.png</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <span class="status del" data-toggle="tooltip" data-placement="right" title="delete"> </span> | ||||
|                     <a class="file" href="#diff-2">static/img/favicon.png</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <span class="status rename" data-toggle="tooltip" data-placement="right" title="rename"> </span> | ||||
|                     <a class="file" href="#diff-2">static/img/favicon.png</a> | ||||
|                     <a class="file" href="#diff-1">{{.Name}}</a> | ||||
|                 </li> | ||||
|                 {{end}} | ||||
|             </ol> | ||||
|         </div> | ||||
| 
 | ||||
|         <div class="panel panel-default diff-file-box diff-box file-content" id="diff-1"> | ||||
|             <div class="panel-heading"> | ||||
|                 <div class="diff-counter count pull-left"> | ||||
|                     <span class="add" data-line="1">BIN</span> | ||||
|                     <span class="bar"> | ||||
|                         <span class="pull-left add"></span> | ||||
|                         <span class="pull-left del"></span> | ||||
|                     </span> | ||||
|                     <span class="del" data-line="0"></span> | ||||
|                 </div> | ||||
|                 <a class="btn btn-default btn-sm pull-right" href="#">View File</a> | ||||
|                <span class="file">data/test/bson_test/simple_type.png</span> | ||||
|             </div> | ||||
|             <div class="panel-body file-body file-code code-view code-bin"> | ||||
|                 <table> | ||||
|                     <tbody> | ||||
|                         <tr class="text-center"><td><img src="http://1.gravatar.com/avatar/f72f7454ce9d710baa506394f68f4132?s=200" alt=""/></td></tr> | ||||
|                     </tbody> | ||||
|                 </table> | ||||
|             </div> | ||||
|         </div> | ||||
| 
 | ||||
|         {{range .Diff.Files}} | ||||
|         <div class="panel panel-default diff-file-box diff-box file-content" id="diff-2"> | ||||
|             <div class="panel-heading"> | ||||
|                 <div class="diff-counter count pull-left"> | ||||
|                     <span class="add" data-line="30">+ 30</span> | ||||
|                     <span class="add" data-line="{{.Addition}}">+ {{.Addition}}</span> | ||||
|                     <span class="bar"> | ||||
|                         <span class="pull-left add"></span> | ||||
|                         <span class="pull-left del"></span> | ||||
|                     </span> | ||||
|                     <span class="del" data-line="4">- 4</span> | ||||
|                     <span class="del" data-line="{{.Deletion}}">- {{.Deletion}}</span> | ||||
|                 </div> | ||||
|                 <a class="btn btn-default btn-sm pull-right" href="#">View File</a> | ||||
|                 <span class="file">data/test/bson_test/simple_type.go</span> | ||||
|                 <span class="file">{{.Name}}</span> | ||||
|             </div> | ||||
|             <div class="panel-body file-body file-code code-view code-diff"> | ||||
|                 <table> | ||||
|                     <tbody> | ||||
|                     <tr class="same-code nl-1 ol-1"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L1">1</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L1">1</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="same-code nl-2 ol-2"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L1">2</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L1">2</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="same-code nl-3 ol-3"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L3">3</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L3">3</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="add-code nl-4 ol-0"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="add">+</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L4">4</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="add-code nl-5 ol-0"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="add">+</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L5">5</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="del-code nl-0 ol-4"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L4">4</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="del">-</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="del-code nl-0 ol-5"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L5">5</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="del">-</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="del-code nl-0 ol-6"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L6">6</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="del">-</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="del-code nl-0 ol-7"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L7">7</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="del">-</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="same-code nl-6 ol-8"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L8">8</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L6">6</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="same-code nl-7 ol-9"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L1">9</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L1">7</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                     <tr class="same-code nl-8 ol-10"> | ||||
|                         <td class="lines-num lines-num-old"> | ||||
|                             <span rel="L1">10</span> | ||||
|                         </td> | ||||
|                         <td class="lines-num lines-num-new"> | ||||
|                             <span rel="L1">8</span> | ||||
|                         </td> | ||||
|                         <td class="lines-code"> | ||||
|                             <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                         </td> | ||||
|                     </tr> | ||||
|                         {{range .Content}} | ||||
|                         <tr class="same-code nl-1 ol-1"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L1"></span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L1"></span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>{{.}}</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         {{end}} | ||||
|                        <!--  <tr class="same-code nl-2 ol-2"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L1">2</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L1">2</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="same-code nl-3 ol-3"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L3">3</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L3">3</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="add-code nl-4 ol-0"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="add">+</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L4">4</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="add-code nl-5 ol-0"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="add">+</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L5">5</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="del-code nl-0 ol-4"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L4">4</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="del">-</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="del-code nl-0 ol-5"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L5">5</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="del">-</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="del-code nl-0 ol-6"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L6">6</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="del">-</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="del-code nl-0 ol-7"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L7">7</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="del">-</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="same-code nl-6 ol-8"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L8">8</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L6">6</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="same-code nl-7 ol-9"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L1">9</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L1">7</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> | ||||
|                         <tr class="same-code nl-8 ol-10"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|                                 <span rel="L1">10</span> | ||||
|                             </td> | ||||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L1">8</span> | ||||
|                             </td> | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>	"github.com/youtube/vitess/go/bson"</pre> | ||||
|                             </td> | ||||
|                         </tr> --> | ||||
|                     </tbody> | ||||
|                 </table> | ||||
|             </div> | ||||
|         </div> | ||||
|         {{end}} | ||||
| 
 | ||||
|         <div class="panel panel-default diff-file-box diff-box file-content"> | ||||
|         <!-- <div class="panel panel-default diff-file-box diff-box file-content"> | ||||
|             <div class="panel-heading"> | ||||
|                 <div class="diff-counter count pull-left"> | ||||
|                     <span class="add" data-line="2">+ 2</span> | ||||
|  | @ -442,7 +406,7 @@ | |||
|                     </tbody> | ||||
|                 </table> | ||||
|             </div> | ||||
|         </div> | ||||
|         </div> --> | ||||
|     </div> | ||||
| </div> | ||||
| {{template "base/footer" .}} | ||||
		Loading…
	
		Reference in a new issue