mirror of https://github.com/gogits/gogs.git
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
170 lines
3.8 KiB
170 lines
3.8 KiB
12 years ago
|
// Copyright (c) 2013 GPMGo Members. All rights reserved.
|
||
|
// Use of this source code is governed by a MIT-style
|
||
|
// license that can be found in the LICENSE file.
|
||
|
|
||
|
package main
|
||
|
|
||
|
import (
|
||
|
"fmt"
|
||
|
"net/http"
|
||
|
"os/exec"
|
||
|
"regexp"
|
||
|
"strings"
|
||
|
|
||
|
"github.com/GPMGo/gpm/doc"
|
||
|
"github.com/GPMGo/gpm/models"
|
||
|
"github.com/GPMGo/gpm/utils"
|
||
|
)
|
||
|
|
||
|
var (
|
||
|
isHasGit, isHasHg bool
|
||
|
)
|
||
|
|
||
|
var cmdInstall = &Command{
|
||
|
UsageLine: "install [install flags] <packages|hash>",
|
||
|
}
|
||
|
|
||
|
func init() {
|
||
|
cmdInstall.Run = runInstall
|
||
|
cmdInstall.Flags = map[string]bool{
|
||
|
"-p": false,
|
||
|
"-d": false,
|
||
|
"-u": false,
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func runInstall(cmd *Command, args []string) {
|
||
|
// Check if has flags.
|
||
|
num := 0
|
||
|
for i, f := range args {
|
||
|
if strings.Index(f, "-") > -1 {
|
||
|
// Deal with flags.
|
||
|
if _, ok := cmdInstall.Flags[f]; ok {
|
||
|
cmdInstall.Flags[f] = true
|
||
|
printPrompt(f)
|
||
|
} else {
|
||
|
fmt.Printf("Unknown flag: %s.\n", f)
|
||
|
return
|
||
|
}
|
||
|
num = i + 1
|
||
|
}
|
||
|
}
|
||
|
// Cut out flag.
|
||
|
args = args[num:]
|
||
|
|
||
|
// Check length of arguments.
|
||
|
if len(args) < 1 {
|
||
|
fmt.Printf("Please list at least one package.\n")
|
||
|
return
|
||
|
}
|
||
|
|
||
|
// Check version control tools.
|
||
|
_, err := exec.LookPath("git")
|
||
|
if err == nil {
|
||
|
isHasGit = true
|
||
|
}
|
||
|
_, err = exec.LookPath("hg")
|
||
|
if err == nil {
|
||
|
isHasHg = true
|
||
|
}
|
||
|
|
||
|
// Install package(s).
|
||
|
for _, p := range args {
|
||
|
// Check if it is a hash string.
|
||
|
// TODO
|
||
|
|
||
|
// Check if it is vaild remote path.
|
||
|
if !utils.IsValidRemotePath(p) {
|
||
|
fmt.Printf("Invalid remote path: %s.\n", p)
|
||
|
} else {
|
||
|
downloadPackage(p, "")
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func printPrompt(flag string) {
|
||
|
switch flag {
|
||
|
case "-p":
|
||
|
fmt.Println("You enabled pure download.")
|
||
|
case "-d":
|
||
|
fmt.Println("You enabled download without installing.")
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// downloadPackage download package either use version control tools or not.
|
||
|
func downloadPackage(path, commit string) {
|
||
|
// Check if use version control tools.
|
||
|
switch {
|
||
|
case !cmdInstall.Flags["-p"] &&
|
||
|
((path[0] == 'g' && isHasGit) || (path[0] == 'c' && isHasHg)): // github.com, code.google.com
|
||
|
args := checkGoGetFlags()
|
||
|
args = append(args, path)
|
||
|
fmt.Printf("Installing package: %s.\n", path)
|
||
|
executeGoCommand(args)
|
||
|
default: // Pure download.
|
||
|
if !cmdInstall.Flags["-p"] {
|
||
|
fmt.Printf("No version control tool available, pure download enabled!\n")
|
||
|
}
|
||
|
|
||
|
fmt.Printf("Downloading package: %s.\n", path)
|
||
|
_, err := pureDownload(path, commit)
|
||
|
if err != nil {
|
||
|
fmt.Printf("Fail to download package(%s) with error: %s.\n", path, err)
|
||
|
} else {
|
||
|
fmt.Printf("Installing package: %s.\n", path)
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func checkGoGetFlags() (args []string) {
|
||
|
args = append(args, "get")
|
||
|
switch {
|
||
|
case cmdInstall.Flags["-d"]:
|
||
|
args = append(args, "-d")
|
||
|
fallthrough
|
||
|
case cmdInstall.Flags["-u"]:
|
||
|
args = append(args, "-u")
|
||
|
}
|
||
|
|
||
|
return args
|
||
|
}
|
||
|
|
||
|
// service represents a source code control service.
|
||
|
type service struct {
|
||
|
pattern *regexp.Regexp
|
||
|
prefix string
|
||
|
get func(*http.Client, map[string]string, string) (*models.PkgInfo, error)
|
||
|
}
|
||
|
|
||
|
// services is the list of source code control services handled by gopkgdoc.
|
||
|
var services = []*service{
|
||
|
{doc.GithubPattern, "github.com/", doc.GetGithubDoc},
|
||
|
//{googlePattern, "code.google.com/", getGoogleDoc},
|
||
|
//{bitbucketPattern, "bitbucket.org/", getBitbucketDoc},
|
||
|
//{launchpadPattern, "launchpad.net/", getLaunchpadDoc},
|
||
|
}
|
||
|
|
||
|
// pureDownload downloads package without control control.
|
||
|
func pureDownload(path, commit string) (pinfo *models.PkgInfo, err error) {
|
||
|
for _, s := range services {
|
||
|
if s.get == nil || !strings.HasPrefix(path, s.prefix) {
|
||
|
continue
|
||
|
}
|
||
|
m := s.pattern.FindStringSubmatch(path)
|
||
|
if m == nil {
|
||
|
if s.prefix != "" {
|
||
|
return nil, doc.NotFoundError{"Import path prefix matches known service, but regexp does not."}
|
||
|
}
|
||
|
continue
|
||
|
}
|
||
|
match := map[string]string{"importPath": path}
|
||
|
for i, n := range s.pattern.SubexpNames() {
|
||
|
if n != "" {
|
||
|
match[n] = m[i]
|
||
|
}
|
||
|
}
|
||
|
return s.get(doc.HttpClient, match, commit)
|
||
|
}
|
||
|
return nil, doc.ErrNoMatch
|
||
|
}
|