93 lines
2.7 KiB
Go
93 lines
2.7 KiB
Go
package github
|
|
|
|
import (
|
|
"net/url"
|
|
"strings"
|
|
)
|
|
|
|
const httpsScheme = "https"
|
|
|
|
// httpsCloneURLFromRepositoryURL converts GitHub GraphQL's Repository.url
|
|
// field into the HTTPS clone identity used by task repository consumers. The
|
|
// GraphQL schema exposes url, while cloneUrl is a gh CLI JSON field and is not
|
|
// valid on Repository. An absent or malformed URL remains absent so nullable
|
|
// head repository data is never replaced with an invented identity.
|
|
func httpsCloneURLFromRepositoryURL(repositoryURL string) string {
|
|
parsed, err := url.Parse(strings.TrimSpace(repositoryURL))
|
|
if err != nil || parsed.Host == "" || strings.Trim(parsed.Path, "/") == "" ||
|
|
(parsed.Scheme != "http" && parsed.Scheme != httpsScheme) {
|
|
return ""
|
|
}
|
|
parsed.Scheme = httpsScheme
|
|
parsed.RawQuery = ""
|
|
parsed.Fragment = ""
|
|
parsed.Path = strings.TrimRight(parsed.Path, "/")
|
|
if !strings.HasSuffix(parsed.Path, ".git") {
|
|
parsed.Path += ".git"
|
|
}
|
|
parsed.RawPath = ""
|
|
return parsed.String()
|
|
}
|
|
|
|
// githubRepositoryResponse is the shared subset returned by GET and POST
|
|
// repository endpoints. Keep the provider response private so only the
|
|
// credential-free projection crosses service boundaries.
|
|
type githubRepositoryResponse struct {
|
|
ID int64 `json:"id"`
|
|
NodeID string `json:"node_id"`
|
|
FullName string `json:"full_name"`
|
|
Name string `json:"name"`
|
|
CloneURL string `json:"clone_url"`
|
|
HTMLURL string `json:"html_url"`
|
|
DefaultBranch string `json:"default_branch"`
|
|
Fork bool `json:"fork"`
|
|
Owner struct {
|
|
Login string `json:"login"`
|
|
} `json:"owner"`
|
|
Parent *struct {
|
|
ID int64 `json:"id"`
|
|
FullName string `json:"full_name"`
|
|
} `json:"parent"`
|
|
Permissions struct {
|
|
Push bool `json:"push"`
|
|
Admin bool `json:"admin"`
|
|
} `json:"permissions"`
|
|
}
|
|
|
|
func projectGitHubRepository(raw githubRepositoryResponse) *GitHubRepository {
|
|
repository := &GitHubRepository{
|
|
ID: raw.ID,
|
|
NodeID: raw.NodeID,
|
|
FullName: raw.FullName,
|
|
Owner: raw.Owner.Login,
|
|
Name: raw.Name,
|
|
CloneURL: raw.CloneURL,
|
|
HTMLURL: raw.HTMLURL,
|
|
DefaultBranch: raw.DefaultBranch,
|
|
Fork: raw.Fork,
|
|
PushAccess: raw.Permissions.Push,
|
|
AdminAccess: raw.Permissions.Admin,
|
|
}
|
|
if raw.Parent != nil {
|
|
repository.ParentID = raw.Parent.ID
|
|
repository.ParentFullName = raw.Parent.FullName
|
|
}
|
|
return repository
|
|
}
|
|
|
|
func copyGitHubRepository(repository *GitHubRepository) *GitHubRepository {
|
|
if repository == nil {
|
|
return nil
|
|
}
|
|
copy := *repository
|
|
return ©
|
|
}
|
|
|
|
func repositoryKeyFromFullName(fullName string) repoKey {
|
|
parts := strings.SplitN(strings.TrimSpace(fullName), "/", 2)
|
|
if len(parts) != 2 {
|
|
return repoKey{Owner: fullName}
|
|
}
|
|
return repoKey{Owner: parts[0], Repo: parts[1]}
|
|
}
|