Merge pull request #560 from evolvedlight/master
First cut of fork repo
This commit is contained in:
		
						commit
						d7d167ac63
					
				|  | @ -20,7 +20,6 @@ import ( | |||
| var ( | ||||
| 	x      *xorm.Engine | ||||
| 	tables []interface{} | ||||
| 
 | ||||
| 	HasEngine bool | ||||
| 
 | ||||
| 	DbCfg struct { | ||||
|  |  | |||
							
								
								
									
										148
									
								
								models/repo.go
								
								
								
								
							
							
						
						
									
										148
									
								
								models/repo.go
								
								
								
								
							|  | @ -177,6 +177,14 @@ func (repo *Repository) GetMirror() (err error) { | |||
| 	return err | ||||
| } | ||||
| 
 | ||||
| func (repo *Repository) GetPath() string { | ||||
|         return RepoPath(repo.Owner.Name, repo.Name) | ||||
| } | ||||
| 
 | ||||
| func (repo *Repository) IsOwnedBy(u *User) bool { | ||||
|         return repo.OwnerId == u.Id | ||||
| } | ||||
| 
 | ||||
| func (repo *Repository) HasAccess(uname string) bool { | ||||
| 	if err := repo.GetOwner(); err != nil { | ||||
| 		return false | ||||
|  | @ -939,6 +947,13 @@ func DeleteRepository(uid, repoId int64, userName string) error { | |||
| 		sess.Rollback() | ||||
| 		return err | ||||
| 	} | ||||
| 	 | ||||
| 	if repo.IsFork { | ||||
|                 if _, err = sess.Exec("UPDATE `repository` SET num_forks = num_forks - 1 WHERE id = ?", repo.ForkId); err != nil { | ||||
|                     sess.Rollback() | ||||
|                     return err | ||||
|                 } | ||||
| 	} | ||||
| 
 | ||||
| 	if _, err = sess.Exec("UPDATE `user` SET num_repos = num_repos - 1 WHERE id = ?", uid); err != nil { | ||||
| 		sess.Rollback() | ||||
|  | @ -1240,6 +1255,137 @@ func IsStaring(uid, repoId int64) bool { | |||
| 	return has | ||||
| } | ||||
| 
 | ||||
| func ForkRepository(repoName string, uid int64) { | ||||
| func ForkRepository(u *User, oldRepo *Repository) (*Repository, error) { | ||||
|         isExist, err := IsRepositoryExist(u, oldRepo.Name) | ||||
|         if err != nil { | ||||
|             return nil, err | ||||
|         } else if isExist { | ||||
|             return nil, ErrRepoAlreadyExist | ||||
|         } | ||||
|      | ||||
|         sess := x.NewSession() | ||||
|         defer sess.Close() | ||||
|         if err = sess.Begin(); err != nil { | ||||
|             return nil, err | ||||
|         } | ||||
|      | ||||
|         repo := &Repository{ | ||||
|             OwnerId:     u.Id, | ||||
|             Owner:       u, | ||||
|             Name:        oldRepo.Name, | ||||
|             LowerName:   oldRepo.LowerName, | ||||
|             Description: oldRepo.Description, | ||||
|             IsPrivate:   oldRepo.IsPrivate, | ||||
|             IsFork:      true, | ||||
|             ForkId:      oldRepo.Id, | ||||
|         } | ||||
|      | ||||
|         if _, err = sess.Insert(repo); err != nil { | ||||
|             sess.Rollback() | ||||
|             return nil, err | ||||
|         } | ||||
|      | ||||
|         var t *Team // Owner team.
 | ||||
|      | ||||
|         mode := WRITABLE | ||||
|          | ||||
|         access := &Access{ | ||||
|             UserName: u.LowerName, | ||||
|             RepoName: path.Join(u.LowerName, repo.LowerName), | ||||
|             Mode:     mode, | ||||
|         } | ||||
|         // Give access to all members in owner team.
 | ||||
|         if u.IsOrganization() { | ||||
|             t, err = u.GetOwnerTeam() | ||||
|             if err != nil { | ||||
|                 sess.Rollback() | ||||
|                 return nil, err | ||||
|             } | ||||
|             if err = t.GetMembers(); err != nil { | ||||
|                 sess.Rollback() | ||||
|                 return nil, err | ||||
|             } | ||||
|             for _, u := range t.Members { | ||||
|                 access.Id = 0 | ||||
|                 access.UserName = u.LowerName | ||||
|                 if _, err = sess.Insert(access); err != nil { | ||||
|                     sess.Rollback() | ||||
|                     return nil, err | ||||
|                 } | ||||
|             } | ||||
|         } else { | ||||
|             if _, err = sess.Insert(access); err != nil { | ||||
|                 sess.Rollback() | ||||
|                 return nil, err | ||||
|             } | ||||
|         } | ||||
|      | ||||
|         if _, err = sess.Exec( | ||||
|             "UPDATE `user` SET num_repos = num_repos + 1 WHERE id = ?", u.Id); err != nil { | ||||
|             sess.Rollback() | ||||
|             return nil, err | ||||
|         } | ||||
|      | ||||
|         // Update owner team info and count.
 | ||||
|         if u.IsOrganization() { | ||||
|             t.RepoIds += "$" + com.ToStr(repo.Id) + "|" | ||||
|             t.NumRepos++ | ||||
|             if _, err = sess.Id(t.Id).AllCols().Update(t); err != nil { | ||||
|                 sess.Rollback() | ||||
|                 return nil, err | ||||
|             } | ||||
|         } | ||||
|      | ||||
|          | ||||
|      | ||||
|         if u.IsOrganization() { | ||||
|             t, err := u.GetOwnerTeam() | ||||
|             if err != nil { | ||||
|                 log.Error(4, "GetOwnerTeam: %v", err) | ||||
|             } else { | ||||
|                 if err = t.GetMembers(); err != nil { | ||||
|                     log.Error(4, "GetMembers: %v", err) | ||||
|                 } else { | ||||
|                     for _, u := range t.Members { | ||||
|                         if err = WatchRepo(u.Id, repo.Id, true); err != nil { | ||||
|                             log.Error(4, "WatchRepo2: %v", err) | ||||
|                         } | ||||
|                     } | ||||
|                 } | ||||
|             } | ||||
|         } else { | ||||
|             if err = WatchRepo(u.Id, repo.Id, true); err != nil { | ||||
|                 log.Error(4, "WatchRepo3: %v", err) | ||||
|             } | ||||
|         } | ||||
|      | ||||
|         if err = NewRepoAction(u, repo); err != nil { | ||||
|             log.Error(4, "NewRepoAction: %v", err) | ||||
|         } | ||||
|          | ||||
|         if _, err = sess.Exec( | ||||
|             "UPDATE `repository` SET num_forks = num_forks + 1 WHERE id = ?", oldRepo.Id); err != nil { | ||||
|             sess.Rollback() | ||||
|             return nil, err | ||||
|         } | ||||
|          | ||||
|         if err = sess.Commit(); err != nil { | ||||
|             return nil, err | ||||
|         } | ||||
|      | ||||
|         repoPath := RepoPath(u.Name, repo.Name) | ||||
|         _, stderr, err := process.ExecTimeout(10*time.Minute, | ||||
|                 fmt.Sprintf("ForkRepository: %s/%s", u.Name, repo.Name), | ||||
|                 "git", "clone", oldRepo.GetPath(), repoPath) | ||||
|      | ||||
|         _, stderr, err = process.ExecDir(-1, | ||||
|             repoPath, fmt.Sprintf("CreateRepository(git update-server-info): %s", repoPath), | ||||
|             "git", "update-server-info") | ||||
|         if err != nil { | ||||
|             return nil, errors.New("CreateRepository(git update-server-info): " + stderr) | ||||
|         } | ||||
|      | ||||
|         return repo, nil | ||||
|     | ||||
| 
 | ||||
| } | ||||
|  |  | |||
|  | @ -217,6 +217,21 @@ func Action(ctx *middleware.Context) { | |||
| 		err = models.StarRepo(ctx.User.Id, ctx.Repo.Repository.Id, true) | ||||
| 	case "unstar": | ||||
| 		err = models.StarRepo(ctx.User.Id, ctx.Repo.Repository.Id, false) | ||||
|         case "fork": | ||||
|                 repo, error := models.ForkRepository(ctx.User, ctx.Repo.Repository) | ||||
|                 if error != nil { | ||||
|                     log.Error(4, "Action(%s): %v", ctx.Params(":action"), error) | ||||
|                     ctx.JSON(200, map[string]interface{}{ | ||||
|                         "ok":  false, | ||||
|                         "err": error.Error(), | ||||
|                     }) | ||||
|                     return | ||||
|                 } | ||||
|                 if error == nil { | ||||
|                         ctx.Redirect(setting.AppSubUrl + "/" + repo.Owner.Name + "/" + repo.Name) | ||||
|                          | ||||
|                         return | ||||
|                 } | ||||
| 	case "desc": | ||||
| 		if !ctx.Repo.IsOwner { | ||||
| 			ctx.Error(404) | ||||
|  |  | |||
|  | @ -101,6 +101,7 @@ | |||
|                 <table> | ||||
|                     <tbody> | ||||
|                         {{range .Sections}} | ||||
|                         Test: {{ .NumLines}} | ||||
|                         {{range .Lines}} | ||||
|                         <tr class="{{DiffLineTypeToStr .Type}}-code nl-1 ol-1"> | ||||
|                             <td class="lines-num lines-num-old"> | ||||
|  | @ -109,6 +110,7 @@ | |||
|                             <td class="lines-num lines-num-new"> | ||||
|                                 <span rel="L1">{{if .RightIdx}}{{.RightIdx}}{{end}}</span> | ||||
|                             </td> | ||||
|                              | ||||
|                             <td class="lines-code"> | ||||
|                                 <pre>{{ToUtf8 .Content}}</pre> | ||||
|                             </td> | ||||
|  |  | |||
|  | @ -44,14 +44,15 @@ | |||
|                     </button> | ||||
|                 </a> | ||||
|             </li> | ||||
|             <!-- <li id="repo-header-fork"> | ||||
|                 <a id="repo-header-fork-btn" href="{{.RepoLink}}/action/fork"> | ||||
|             <li id="repo-header-fork"> | ||||
|                 <a id="repo-header-fork-btn" {{if not .IsRepositoryOwner}} href="{{.RepoLink}}/action/fork"{{end}}> | ||||
|                     <button class="btn btn-gray text-bold btn-radius"> | ||||
|                         <i class="octicon octicon-repo-forked"></i>{{.i18n.Tr "repo.fork"}} | ||||
|                         <span class="num">{{.Repository.NumForks}}</span> | ||||
|                     </button> | ||||
|                 </a> | ||||
|             </li> --> | ||||
|              | ||||
|             </li> | ||||
|         </ul> | ||||
|     </div> | ||||
| </div> | ||||
		Loading…
	
		Reference in New Issue