3

I'm creating a Go Google App Engine application that will be making HTTP JSON RPC calls to a Bitcoin server. I got my code to work properly on the dev_appserver, but when deployed on GAE, the code seems to not work. I'm using a library available on GitHub, and call it like this:

func GetInfo(id interface{})(map[string]interface{}, os.Error){
    resp, err:=httpjsonrpc.Call("user:pass@111.1.1.1:18332", "getinfo", id, nil)
    if err!=nil{
        log.Println(err)
        return resp, err
    }
    return resp, err
}

Which when called should give:

map[proxy: keypoololdest:1.327368259e+09 blocks:45385 keypoolsize:101 connections:11 version:50200 difficulty:8.88353262 generate:false hashespersec:0 paytxfee:0 balance:0 genproclimit:-1 testnet:true errors:]

But on GAE calling the function seems to be causing an error. What part of the code could be working on dev_appserver, but fail on GAE?

Jonathan Leffler
  • 730,956
  • 141
  • 904
  • 1,278
ThePiachu
  • 8,695
  • 17
  • 65
  • 94

1 Answers1

3

You should make you are using urlfetch.Transport to make HTTP calls in production as described in urlfetch documentation.

Instead of doing:

resp, err := http.Post(address,
    "application/json", strings.NewReader(string(data)))

You should be doing:

client := urlfetch.Client(context)
resp, error := client.Post(address,
    "application/json", strings.NewReader(string(data)))

As you can see in the implementation, urlfetch.Client is just a shortcut to construct an http.Client that uses urlfetch.Transport.

proppy
  • 10,495
  • 5
  • 37
  • 66
  • Hmm, the client.Post seems to be giving an error of "API error 1 (urlfetch: INVALID_URL): ApplicationError: 2 (8, 'nodename nor servname provided, or not known')" – ThePiachu Jan 31 '12 at 16:00
  • What is the value of `address`? – proppy Jan 31 '12 at 18:28
  • It's formatted like "https://user:pass@111.1.1.1:18332", which worked for http.Post. – ThePiachu Jan 31 '12 at 23:25
  • I believe `urlfetch.Transport` doesn't parse auth in the url, you should use `Authorization:` header instead, see http://stackoverflow.com/questions/1341081/using-http-basic-auth-with-google-app-engine-urlfetch-service – proppy Feb 01 '12 at 00:57
  • I guess that was the problem. Had to make a http.Request, then set basic auth, and only then execute it with client.Do. Don't know where to set bodyType to "application/json", but it seems to be working without that, at least on dev server. – ThePiachu Feb 01 '12 at 02:06
  • Tested it on gae, didn't work due to my self-issued certificate. Had to change client.Do to first fetching &urlfetch.Transport, then setting AllowInvalidServerCertificate to true and only then calling transport.RoundTrip(req). Only then did it work properly on dev and gae. Thanks for the help, guess I'll upload my final code to GitHub soon-ish. – ThePiachu Feb 01 '12 at 02:43