diff --git a/db/common.go b/db/common.go index 6c7ac08..f6514ab 100644 --- a/db/common.go +++ b/db/common.go @@ -14,6 +14,6 @@ var ( func Connect(params string) (err error) { conn, err = sqlx.Connect("mysql", params) - conn.Mappper = reflectx.NewMapperFunc("json", strings.ToLower) + conn.Mapper = reflectx.NewMapperFunc("json", strings.ToLower) return } diff --git a/server/auth.go b/server/auth.go index cb603ba..8580820 100644 --- a/server/auth.go +++ b/server/auth.go @@ -6,8 +6,7 @@ import ( "net/url" "github.com/localhots/empact/config" - "github.com/localhots/empact/db" - "github.com/localhots/empact/job" + "github.com/localhots/empact/task" ) @@ -31,17 +30,10 @@ func authCallbackHandler(w http.ResponseWriter, r *http.Request) { code := r.FormValue("code") fmt.Println("Got code: ", code) - res := make(chan string) - job.Enqueue(&task.FetchAccessTokenTask{ - Code: code, - Result: res, - Task: &db.Task{}, - }) - - if login, ok := <-res; ok { + if _, login, err := task.Authenticate(code); err == nil { authorize(r, login) } else { - panic("Failed to access token or user info") + panic(err) } } } diff --git a/task/access_token.go b/task/access_token.go deleted file mode 100644 index 829e058..0000000 --- a/task/access_token.go +++ /dev/null @@ -1,67 +0,0 @@ -package task - -import ( - "bytes" - "encoding/json" - "fmt" - "io/ioutil" - "net/http" - "net/url" - - "github.com/localhots/empact/config" - "github.com/localhots/empact/db" -) - -func FetchAccessToken(code string, result chan string) { - payload := url.Values{} - payload.Set("client_id", config.C().ClientID) - payload.Set("client_secret", config.C().ClientSecret) - payload.Set("code", code) - payload.Set("redirect_uri", config.C().RedirectURI) - - buf := bytes.NewBuffer([]byte(payload.Encode())) - fmt.Println("Requesting token") - resp, err := http.Post(config.C().AccessTokenURL, "application/x-www-form-urlencoded", buf) - if err != nil { - panic(err) - } - - defer resp.Body.Close() - body, err := ioutil.ReadAll(resp.Body) - if err != nil { - panic(err) - } - - fmt.Println(string(body)) - - pairs, _ := url.ParseQuery(string(body)) - token := pairs.Get("access_token") - fmt.Println("Got token: " + token) - - fmt.Println("Requesting info") - resp, err = http.Get("https://api.github.com/user?access_token=" + token) - if err != nil { - panic(err) - } - - defer resp.Body.Close() - body, err = ioutil.ReadAll(resp.Body) - if err != nil { - panic(err) - } - fmt.Println(string(body)) - - user := &db.User{} - json.Unmarshal(body, &user) - user.Save() - fmt.Println("Saving user", user) - - tok := &db.Token{ - User: user.Login, - Token: token, - } - fmt.Println("Saving token", tok) - tok.Save() - - result <- user.Login -} diff --git a/task/auth.go b/task/auth.go new file mode 100644 index 0000000..572779c --- /dev/null +++ b/task/auth.go @@ -0,0 +1,82 @@ +package task + +import ( + "bytes" + "encoding/json" + "fmt" + "io/ioutil" + "net/http" + "net/url" + + "github.com/localhots/empact/config" + "github.com/localhots/empact/db" +) + +func Authenticate(code string) (token, login string, err error) { + if token, err = FetchAccessToken(code); err != nil { + return + } + fmt.Println("Got token: " + token) + + var user *db.User + if user, err = FetchUserInfoWithToken(token); err != nil { + return + } + login = user.Login + fmt.Println("Saving user", user) + user.Save() + + tok := &db.Token{ + User: login, + Token: token, + } + fmt.Println("Saving token", tok) + tok.Save() + + return +} + +func FetchAccessToken(code string) (token string, err error) { + payload := url.Values{} + payload.Set("client_id", config.C().ClientID) + payload.Set("client_secret", config.C().ClientSecret) + payload.Set("code", code) + payload.Set("redirect_uri", config.C().RedirectURI) + + fmt.Println("Requesting token") + buf := bytes.NewBuffer([]byte(payload.Encode())) + var resp *http.Response + if resp, err = http.Post(config.C().AccessTokenURL, "application/x-www-form-urlencoded", buf); err != nil { + return + } + + defer resp.Body.Close() + var body []byte + if body, err = ioutil.ReadAll(resp.Body); err != nil { + return + } + + pairs, _ := url.ParseQuery(string(body)) + if token = pairs.Get("access_token"); token == "" { + err = fmt.Errorf("Failed to fetch access token usign code %q: %s", code, pairs.Get("error_description")) + } + return +} + +func FetchUserInfoWithToken(token string) (u *db.User, err error) { + var resp *http.Response + if resp, err = http.Get("https://api.github.com/user?access_token=" + token); err != nil { + return + } + + defer resp.Body.Close() + var body []byte + if body, err = ioutil.ReadAll(resp.Body); err != nil { + return + } + + u = &db.User{} + err = json.Unmarshal(body, &u) + + return +} diff --git a/task/common.go b/task/common.go index ac4b64b..a171c9b 100644 --- a/task/common.go +++ b/task/common.go @@ -19,8 +19,8 @@ func saveResponseMeta(token string, res *github.Response) { } tok := &db.Token{ Token: token, - Limit: res.Limit, - Remaining: res.Remaining, + Quota: int64(res.Limit), + Remaining: int64(res.Remaining), ResetAt: res.Reset.Time, } tok.Save() diff --git a/task/sync.go b/task/sync.go new file mode 100644 index 0000000..f20f487 --- /dev/null +++ b/task/sync.go @@ -0,0 +1,63 @@ +package task + +import ( + "github.com/google/go-github/github" + "github.com/localhots/empact/db" +) + +func SyncRepos(token, owner string) { + client := newGithubClient(token) + opt := &github.RepositoryListByOrgOptions{ + ListOptions: github.ListOptions{}, + } + + for { + opt.Page++ + repos, resp, err := client.Repositories.ListByOrg(owner, opt) + saveResponseMeta(token, resp) + if err != nil { + panic(err) + } + for _, repo := range repos { + r := &db.Repo{ + Owner: owner, + Name: *repo.Name, + } + r.Save() + } + if len(repos) < 30 { + break + } + } +} + +func SyncContrib(token, owner, repo string) { + client := newGithubClient(token) + contribs, resp, err := client.Repositories.ListContributorsStats(owner, repo) + saveResponseMeta(token, resp) + if err != nil { + if err.Error() == "EOF" { + return // Empty repository, not an actual error + } + panic(err) + } + + for _, c := range contribs { + for _, week := range c.Weeks { + if *week.Commits == 0 { + continue + } + + contrib := &db.Contrib{ + Week: week.Week.Time.Unix(), + Author: *c.Author.Login, + Owner: owner, + Repo: repo, + Commits: int64(*week.Commits), + Additions: int64(*week.Additions), + Deletions: int64(*week.Deletions), + } + contrib.Save() + } + } +} diff --git a/task/sync_contrib.go b/task/sync_contrib.go deleted file mode 100644 index d895d0f..0000000 --- a/task/sync_contrib.go +++ /dev/null @@ -1,36 +0,0 @@ -package task - -import ( - "github.com/localhots/empact/db" -) - -func SyncContrib(token, owner, repo string) { - client := newGithubClient(token) - contribs, resp, err := client.Repositories.ListContributorsStats(owner, repo) - saveResponseMeta(token, resp) - if err != nil { - if err.Error() == "EOF" { - return // Empty repository, not an actual error - } - panic(err) - } - - for _, c := range contribs { - for _, week := range c.Weeks { - if *week.Commits == 0 { - continue - } - - contrib := &db.Contrib{ - Week: week.Week.Time.Unix(), - Author: *c.Author.Login, - Owner: t.Owner, - Repo: t.Repo, - Commits: *week.Commits, - Additions: *week.Additions, - Deletions: *week.Deletions, - } - contrib.Save() - } - } -} diff --git a/task/sync_repos.go b/task/sync_repos.go deleted file mode 100644 index cfb6c10..0000000 --- a/task/sync_repos.go +++ /dev/null @@ -1,32 +0,0 @@ -package task - -import ( - "github.com/google/go-github/github" - "github.com/localhots/empact/db" -) - -func SyncRepos(token, owner string) { - client := newGithubClient(token) - opt := &github.RepositoryListByOrgOptions{ - ListOptions: github.ListOptions{}, - } - - for { - opt.Page++ - repos, resp, err := client.Repositories.ListByOrg(owner, opt) - saveResponseMeta(token, resp) - if err != nil { - panic(err) - } - for _, repo := range repos { - r := &db.Repo{ - Owner: owner, - Name: *repo.Name, - } - r.Save() - } - if len(repos) < 30 { - break - } - } -}