Skip to content

Commit

Permalink
Merge pull request ernoaapa#16 from arnested/deploy-key
Browse files Browse the repository at this point in the history
Add `--deploy-key` parameter
  • Loading branch information
ernoaapa authored Nov 13, 2018
2 parents 88a1a31 + cf3b80b commit 545b209
Show file tree
Hide file tree
Showing 4 changed files with 80 additions and 9 deletions.
8 changes: 7 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,9 @@ fetch-ssh-keys github --organization my-awesome-company --team my-lovely-team --

# Fetch 'ernoaapa' and 'arnested' public keys
fetch-ssh-keys github --user ernoaapa --user arnested --token YOUR-TOKEN-HERE ./the-keys

# Fetch 'ernoaapa/fetch-ssh-keys' deploy keys (requires a Github token with the `repo` or `public_repo` scope)
fetch-ssh-keys github --deploy-key ernoaapa/fetch-ssh-keys --token YOUR-TOKEN-HERE ./the-keys
```

Tool can be used for example to automatically update `.ssh/authorized_keys` file by giving path to `.ssh/authorized_keys` as last argument and adding the script to cron job.
Expand All @@ -40,10 +43,13 @@ Tool can be used for example to automatically update `.ssh/authorized_keys` file
| --organization | Name of the organization which members keys to pick |
| --team | Name or slug of the team which members keys to pick |
| --user | Name of the user which keys to pick |
| --deploy-key | Name of the owner/repo which deploy keys to pick |
| --token | GitHub API token to use for communication. Without token you get only public members of the organization. |
| --public-only | Return only members what are publicly members of the given organization |

You can give `--organisation` (optionally combined with `--team` flag) and/or one or more `--user` flags.
You can give `--organisation` (optionally combined with `--team` flag) and/or one or more `--user` or `--deploy-key` flags.

The `--deploy-key` parameter requires a Github token with the `repo` or `public_repo` scope.

## Development
### Get dependencies
Expand Down
33 changes: 31 additions & 2 deletions fetch/github.go
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@ func GitHubUsers(usernames []string, token string) (map[string][]string, error)
return fetchUserKeys(client, usernames, token)
}

// GitHubDeployKeys fetches repositories' SSH keys from GitHub
func GitHubDeployKeys(ownerRepos []string, token string) (map[string][]string, error) {
client := getClient(token)
return fetchDeployKeys(client, ownerRepos, token)
}

func getClient(token string) *github.Client {
if len(token) > 0 {
ts := oauth2.StaticTokenSource(
Expand All @@ -61,7 +67,7 @@ func fetchUsers(client *github.Client, organizationName string, params GithubFet
return []*github.User{}, err
}

teamUsers, _, err := client.Organizations.ListTeamMembers(ctx, teamID, &github.OrganizationListTeamMembersOptions{})
teamUsers, _, err := client.Teams.ListTeamMembers(ctx, teamID, &github.TeamListTeamMembersOptions{})
if err != nil {
return []*github.User{}, err
}
Expand All @@ -81,7 +87,7 @@ func fetchUsers(client *github.Client, organizationName string, params GithubFet
func resolveTeamID(client *github.Client, organizationName, teamName string) (int64, error) {
ctx := context.Background()

teams, _, err := client.Organizations.ListTeams(ctx, organizationName, &github.ListOptions{})
teams, _, err := client.Teams.ListTeams(ctx, organizationName, &github.ListOptions{})
if err != nil {
return -1, err
}
Expand Down Expand Up @@ -114,3 +120,26 @@ func fetchUserKeys(client *github.Client, usernames []string, token string) (map

return result, nil
}

func fetchDeployKeys(client *github.Client, ownerRepos []string, token string) (map[string][]string, error) {
ctx := context.Background()

result := map[string][]string{}
for _, ownerRepo := range ownerRepos {
ownerRepoSplit := strings.SplitN(ownerRepo, "/", 2)
owner := ownerRepoSplit[0]
repo := ownerRepoSplit[1]
keys, _, err := client.Repositories.ListKeys(ctx, owner, repo, &github.ListOptions{})
if err != nil {
return map[string][]string{}, err
}

result[ownerRepo] = make([]string, len(keys))

for index, key := range keys {
result[ownerRepo][index] = *key.Key
}
}

return result, nil
}
23 changes: 23 additions & 0 deletions fetch/github_deploy_key_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
// +build deploy_key

package fetch

import (
"os"
"testing"

log "github.com/Sirupsen/logrus"

"github.com/stretchr/testify/assert"
)

func TestFetchDeployKeys(t *testing.T) {
log.SetLevel(log.DebugLevel)

keys, err := GitHubDeployKeys([]string{"arnested/fetch-ssh-keys"}, os.Getenv("GITHUB_TOKEN"))

assert.NoError(t, err, "Fetch GitHub keys returned error")
assert.Equal(t, 1, len(keys), "should return SSH keys for 'arnested/fetch-ssh-keys'")
assert.True(t, len(keys["arnested/fetch-ssh-keys"]) > 0, "should return 'arnested/fetch-ssh-keys' deploy SSH key")
assert.True(t, len(keys["arnested/fetch-ssh-keys"][0]) > 0, "should not return empty key for 'arnested/fetch-ssh-keys'")
}
25 changes: 19 additions & 6 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,11 @@ func main() {
},
cli.StringSliceFlag{
Name: "user",
Usage: "Return given user public ssh keys (this option can be used multiple times for multiple users)",
Usage: "Return given `USER` public ssh keys (this option can be used multiple times for multiple users)",
},
cli.StringSliceFlag{
Name: "deploy-key",
Usage: "Return given `OWNER/REPO` deploy ssh keys (this option can be used multiple times for multiple repositories)",
},
},
Action: func(c *cli.Context) error {
Expand All @@ -73,10 +77,12 @@ func main() {
organisation = c.String("organization")
teams = c.StringSlice("team")
users = c.StringSlice("user")
ownerRepos = c.StringSlice("deploy-key")
publicOnly = c.Bool("public-only")

orgKeys map[string][]string
userKeys map[string][]string
deployKeys map[string][]string
orgKeys map[string][]string
userKeys map[string][]string

target = c.Args().Get(0)
fileMode = os.FileMode(c.GlobalInt("file-mode"))
Expand All @@ -86,8 +92,8 @@ func main() {
err error
)

if organisation == "" && len(users) == 0 {
return fmt.Errorf("You must give either --organisation or --user parameter")
if organisation == "" && len(users) == 0 && len(ownerRepos) == 0 {
return fmt.Errorf("You must give either --organisation or --user or --deploy-key parameter")
}

if c.IsSet("organization") {
Expand All @@ -108,7 +114,14 @@ func main() {
}
}

return output.Write(format, target, fileMode, utils.MergeKeys(orgKeys, userKeys), comment)
if c.IsSet("deploy-key") {
deployKeys, err = fetch.GitHubDeployKeys(ownerRepos, token)
if err != nil {
return errors.Wrap(err, "Failed to fetch GitHub repositories' deploy keys")
}
}

return output.Write(format, target, fileMode, utils.MergeKeys(orgKeys, userKeys, deployKeys), comment)
},
},
}
Expand Down

0 comments on commit 545b209

Please sign in to comment.