123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146 |
- package libamuse
- import (
- "notabug.org/apiote/amuse/accounts"
- "notabug.org/apiote/amuse/db"
- "notabug.org/apiote/amuse/network"
- "crypto/sha256"
- "encoding/base64"
- "errors"
- "net/http"
- "notabug.org/apiote/gott"
- )
- type Avatar struct {
- Data []byte
- Mimetype string
- Etag string
- }
- func getUser(args ...interface{}) (interface{}, error) {
- request := args[0].(*RequestData)
- result := args[1].(*Result)
- user, err := db.GetUser(request.id)
- result.result = user
- return gott.Tuple(args), err
- }
- func getAvatar(args ...interface{}) (interface{}, error) {
- result := args[1].(*Result)
- small := args[2].(bool)
- user := result.result.(*db.User)
- if small {
- if string(user.AvatarSmall) == "" {
- return gott.Tuple(args), errors.New("No avatar")
- } else {
- result.result = user.AvatarSmall
- }
- } else {
- if string(user.Avatar) == "" {
- return gott.Tuple(args), errors.New("No avatar")
- } else {
- result.result = user.Avatar
- }
- }
- result.result2 = "image/webp"
- return gott.Tuple(args), nil
- }
- func checkEtag(args ...interface{}) (interface{}, error) {
- request := args[0].(*RequestData)
- result := args[1].(*Result)
- h := sha256.New()
- _, err := h.Write([]byte(result.page))
- if err != nil {
- return gott.Tuple(args), err
- }
- etag := base64.StdEncoding.EncodeToString(h.Sum(nil))
- if etag == request.etag {
- result.result = []byte{}
- }
- result.page = etag
- return gott.Tuple(args), nil
- }
- func createPlaceholderRequest(args ...interface{}) (interface{}, error) {
- request := args[0].(*network.Request)
- result := args[1].(*network.Result)
- small := args[2].(bool)
- result.Client = &http.Client{}
- size := "512"
- if small {
- size = "40"
- }
- httpRequest, err := http.NewRequest("GET", "https://api.adorable.io/avatars/"+size+"/"+request.Id+".png", nil)
- result.Request = httpRequest
- return gott.Tuple(args), err
- }
- func unmarshalPlaceholder(args ...interface{}) interface{} {
- result := args[1].(*network.Result)
- result.Result = result.Body
- return gott.Tuple(args)
- }
- func recovery(args ...interface{}) (interface{}, error) {
- err := args[3].(error)
- switch err.Error() {
- case "No avatar":
- return getPlaceholder(args...)
- default:
- return gott.Tuple(args), err
- }
- }
- func getPlaceholder(args ...interface{}) (interface{}, error) {
- request := args[0].(*RequestData)
- result := args[1].(*Result)
- small := args[2].(bool)
- r, err := gott.
- NewResult(gott.Tuple{&network.Request{Id: request.id, Etag: request.etag}, &network.Result{}, small}).
- Bind(createPlaceholderRequest).
- Map(network.AddHeaders).
- Bind(network.DoRequest).
- Bind(network.HandleRequestError).
- Bind(network.ReadResponse).
- Map(unmarshalPlaceholder).
- // todo get etag
- Finish()
- if err != nil {
- return gott.Tuple(args), err
- }
- result.result = r.(gott.Tuple)[1].(*network.Result).Result.([]byte)
- result.result2 = "image/png"
- return gott.Tuple(args), nil
- }
- func ShowUserAvatar(username, etagReq string, auth accounts.Authentication, small bool) (Avatar, error) {
- auth.Necessary = true
- avatar := Avatar{}
- r, err := gott.
- NewResult(gott.Tuple{&RequestData{id: username, etag: etagReq, auth: auth, username: username}, &Result{}, small}).
- Bind(verifyToken).
- Bind(verifyUser).
- Bind(getUser).
- Bind(getAvatar).
- Bind(checkEtag).
- Recover(recovery).
- Finish()
- if err != nil {
- return avatar, err
- }
- r = r.(gott.Tuple)[1]
- avatar.Data = r.(*Result).result.([]byte)
- avatar.Mimetype = r.(*Result).result2.(string)
- avatar.Etag = r.(*Result).page
- return avatar, nil
- }
|