Further tests with oauth and sqlite

This commit is contained in:
Thomas Schwery 2017-01-28 17:29:48 +01:00
parent e5936b3c64
commit b838c8e2cb

220
main.go
View file

@ -1,39 +1,225 @@
package main
import (
"encoding/json"
"golang.org/x/oauth2"
"io/ioutil"
"net/http"
"fmt"
"log"
"github.com/go-openapi/strfmt"
apiclient "client"
skillsclient "client/skills"
httptransport "github.com/go-openapi/runtime/client"
"database/sql"
_ "github.com/mattn/go-sqlite3"
)
type Character struct {
CharacterID int32
CharacterName string
ExpiresOn string
}
const htmlIndex = `<html><body>
<a href="/login">Log in</a>
</body></html>
`
var (
googleOauthConfig = &oauth2.Config{
RedirectURL: "http://localhost:3000/callback",
ClientID: "CLIENTKEY",
ClientSecret: "SECRETKEY",
Scopes: []string{
"esi-skills.read_skillqueue.v1",
"esi-skills.read_skills.v1",
},
Endpoint: oauth2.Endpoint{
AuthURL: "https://login.eveonline.com/oauth/authorize/",
TokenURL: "https://login.eveonline.com/oauth/token/",
},
}
// Some random string, random for each request
oauthStateString = "random"
)
func main() {
db, err := sql.Open("sqlite3", "./foo.db")
if err != nil {
log.Fatal(err)
}
defer db.Close()
_, _ = db.Exec("CREATE TABLE IF NOT EXISTS properties (id integer NOT NULL PRIMARY KEY, name TEXT);")
tx, err := db.Begin()
if err != nil {
log.Fatal(err)
}
stmt, err := tx.Prepare("insert into foo(id, name) values(?, ?)")
if err != nil {
log.Fatal(err)
}
defer stmt.Close()
for i := 0; i < 100; i++ {
_, err = stmt.Exec(i, fmt.Sprintf("こんにちわ世界%03d", i))
if err != nil {
log.Fatal(err)
}
}
tx.Commit()
rows, err := db.Query("select id, name from foo")
if err != nil {
log.Fatal(err)
}
defer rows.Close()
for rows.Next() {
var id int
var name string
err = rows.Scan(&id, &name)
if err != nil {
log.Fatal(err)
}
fmt.Println(id, name)
}
err = rows.Err()
if err != nil {
log.Fatal(err)
}
stmt, err = db.Prepare("select name from foo where id = ?")
if err != nil {
log.Fatal(err)
}
defer stmt.Close()
var name string
err = stmt.QueryRow("3").Scan(&name)
if err != nil {
log.Fatal(err)
}
fmt.Println(name)
_, err = db.Exec("delete from foo")
if err != nil {
log.Fatal(err)
}
_, err = db.Exec("insert into foo(id, name) values(1, 'foo'), (2, 'bar'), (3, 'baz')")
if err != nil {
log.Fatal(err)
}
rows, err = db.Query("select id, name from foo")
if err != nil {
log.Fatal(err)
}
defer rows.Close()
for rows.Next() {
var id int
var name string
err = rows.Scan(&id, &name)
if err != nil {
log.Fatal(err)
}
fmt.Println(id, name)
}
err = rows.Err()
if err != nil {
log.Fatal(err)
}
http.HandleFunc("/", handleMain)
http.HandleFunc("/login", handleGoogleLogin)
http.HandleFunc("/callback", handleGoogleCallback)
fmt.Println(http.ListenAndServe(":3000", nil))
}
func handleMain(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, htmlIndex)
}
func handleGoogleLogin(w http.ResponseWriter, r *http.Request) {
url := googleOauthConfig.AuthCodeURL(oauthStateString)
// https://eveonline-third-party-documentation.readthedocs.io/en/latest/sso/authentication.html
// response_type: Must be set to “code”.
url = url + "&response_type=code"
http.Redirect(w, r, url, http.StatusTemporaryRedirect)
}
func handleGoogleCallback(w http.ResponseWriter, r *http.Request) {
state := r.FormValue("state")
if state != oauthStateString {
fmt.Printf("invalid oauth state, expected '%s', got '%s'\n", oauthStateString, state)
http.Redirect(w, r, "/", http.StatusTemporaryRedirect)
return
}
code := r.FormValue("code")
token, err := googleOauthConfig.Exchange(oauth2.NoContext, code)
if err != nil {
fmt.Printf("Code exchange failed with '%s'\n", err)
http.Redirect(w, r, "/", http.StatusTemporaryRedirect)
return
}
//fmt.Println("Access token: " + token.AccessToken)
//fmt.Println("Refresh token: " + token.RefreshToken)
client := &http.Client{}
req, err := http.NewRequest("GET", "https://login.eveonline.com/oauth/verify", nil)
req.Header.Add("Authorization", "Bearer "+token.AccessToken)
response, _ := client.Do(req)
defer response.Body.Close()
contents, _ := ioutil.ReadAll(response.Body)
var m Character
errJson := json.Unmarshal(contents, &m)
if errJson != nil {
fmt.Printf("JSON read error with '%s'\n", errJson)
http.Redirect(w, r, "/", http.StatusTemporaryRedirect)
return
}
fmt.Fprintf(w, "Name: %s\n", m.CharacterName)
fmt.Fprintf(w, "Id: %d\n", m.CharacterID)
fmt.Fprintf(w, "Token: %s\n\n", token.AccessToken)
bearerToken := httptransport.BearerToken(token.AccessToken)
// create the transport
transport := httptransport.New("esi.tech.ccp.is", "/latest", []string{"https"})
// create the API client, with the transport
client := apiclient.New(transport, strfmt.Default)
swaggerclient := apiclient.New(transport, strfmt.Default)
// to override the host for the default client
// apiclient.Default.SetTransport(transport)
charIDSkilqueue := skillsclient.NewGetCharactersCharacterIDSkillqueueParams().WithCharacterID(m.CharacterID)
skillqueueresp, _ := swaggerclient.Skills.GetCharactersCharacterIDSkillqueue(charIDSkilqueue, bearerToken)
// make the request to get all items
resp, err := client.Universe.GetUniverseRaces(nil)
if err != nil {
log.Fatal(err)
skillqueue := skillqueueresp.Payload
for _, skill := range skillqueue {
// element is the element from someSlice for where we are
name := "UNK"
level := skill.FinishedLevel
id := skill.SkillID
startDate := skill.StartDate
endDate := skill.FinishDate
fmt.Fprintf(w, "%s: %d\n %d - %s to %s\n\n", name, id, level, startDate, endDate)
}
races := resp.Payload
for _,race := range races {
// element is the element from someSlice for where we are
name := race.Name
description := race.Description
fmt.Printf("%s:\n%s\n\n", *name, *description)
}
}