I’m trying to implement a method that accesses local trends, based off of this example code found at:
It seems to me that this should be possible if I create a method similar to the search tweets code, which I’ve pasted here:
public JSONObject searchTweets(String q, String access_token, String access_token_secret)
{
JSONObject jsonresponse = new JSONObject();
String oauth_token = access_token;
String oauth_token_secret = access_token_secret;
// generate authorization header
String get_or_post = "GET";
String oauth_signature_method = "HMAC-SHA1";
String uuid_string = UUID.randomUUID().toString();
uuid_string = uuid_string.replaceAll("-", "");
String oauth_nonce = uuid_string; // any relatively random alphanumeric string will work here
// get the timestamp
Calendar tempcal = Calendar.getInstance();
long ts = tempcal.getTimeInMillis();// get current time in milliseconds
String oauth_timestamp = (new Long(ts/1000)).toString(); // then divide by 1000 to get seconds
// the parameter string must be in alphabetical order
// this time, I add 3 extra params to the request, "lang", "result_type" and "q".
String parameter_string = "lang=en&oauth_consumer_key=" + twitter_consumer_key + "&oauth_nonce=" + oauth_nonce + "&oauth_signature_method=" + oauth_signature_method +
"&oauth_timestamp=" + oauth_timestamp + "&oauth_token=" + encode(oauth_token) + "&oauth_version=1.0&q=" + encode(q) + "&result_type=mixed";
System.out.println("parameter_string=" + parameter_string);
String twitter_endpoint = "https://api.twitter.com/1.1/search/tweets.json";
String twitter_endpoint_host = "api.twitter.com";
String twitter_endpoint_path = "/1.1/search/tweets.json";
String signature_base_string = get_or_post + "&"+ encode(twitter_endpoint) + "&" + encode(parameter_string);
System.out.println("signature_base_string=" + signature_base_string);
// this time the base string is signed using twitter_consumer_secret + "&" + encode(oauth_token_secret) instead of just twitter_consumer_secret + "&"
String oauth_signature = "";
try {
oauth_signature = computeSignature(signature_base_string, twitter_consumer_secret + "&" + encode(oauth_token_secret)); // note the & at the end. Normally the user access_token would go here, but we don't know it yet for request_token
} catch (GeneralSecurityException e) {
e.printStackTrace();
}
catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
String authorization_header_string = "OAuth oauth_consumer_key=\"" + twitter_consumer_key + "\",oauth_signature_method=\"HMAC-SHA1\",oauth_timestamp=\"" + oauth_timestamp +
"\",oauth_nonce=\"" + oauth_nonce + "\",oauth_version=\"1.0\",oauth_signature=\"" + encode(oauth_signature) + "\",oauth_token=\"" + encode(oauth_token) + "\"";
System.out.println("authorization_header_string=" + authorization_header_string);
HttpParams params = new SyncBasicHttpParams();
HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1);
HttpProtocolParams.setContentCharset(params, "UTF-8");
HttpProtocolParams.setUserAgent(params, "HttpCore/1.1");
HttpProtocolParams.setUseExpectContinue(params, false);
HttpProcessor httpproc = new ImmutableHttpProcessor(new HttpRequestInterceptor[] {
// Required protocol interceptors
new RequestContent(),
new RequestTargetHost(),
// Recommended protocol interceptors
new RequestConnControl(),
new RequestUserAgent(),
new RequestExpectContinue()});
HttpRequestExecutor httpexecutor = new HttpRequestExecutor();
HttpContext context = new BasicHttpContext(null);
HttpHost host = new HttpHost(twitter_endpoint_host,443);
DefaultHttpClientConnection conn = new DefaultHttpClientConnection();
context.setAttribute(ExecutionContext.HTTP_CONNECTION, conn);
context.setAttribute(ExecutionContext.HTTP_TARGET_HOST, host);
try {
try {
SSLContext sslcontext = SSLContext.getInstance("TLS");
sslcontext.init(null, null, null);
SSLSocketFactory ssf = sslcontext.getSocketFactory();
Socket socket = ssf.createSocket();
socket.connect(
new InetSocketAddress(host.getHostName(), host.getPort()), 0);
conn.bind(socket, params);
// the following line adds 3 params to the request just as the parameter string did above. They must match up or the request will fail.
BasicHttpEntityEnclosingRequest request2 = new BasicHttpEntityEnclosingRequest("GET", twitter_endpoint_path + "?lang=en&result_type=mixed&q=" + encode(q));
request2.setParams(params);
request2.addHeader("Authorization", authorization_header_string); // always add the Authorization header
httpexecutor.preProcess(request2, httpproc, context);
HttpResponse response2 = httpexecutor.execute(request2, conn, context);
response2.setParams(params);
httpexecutor.postProcess(response2, httpproc, context);
if(response2.getStatusLine().toString().indexOf("500") != -1)
{
jsonresponse.put("response_status", "error");
jsonresponse.put("message", "Twitter auth error.");
}
else
{
// if successful, the response should be a JSONObject of tweets
JSONObject jo = new JSONObject(EntityUtils.toString(response2.getEntity()));
if(jo.has("errors"))
{
jsonresponse.put("response_status", "error");
String message_from_twitter = jo.getJSONArray("errors").getJSONObject(0).getString("message");
if(message_from_twitter.equals("Invalid or expired token") || message_from_twitter.equals("Could not authenticate you"))
jsonresponse.put("message", "Twitter auth error.");
else
jsonresponse.put("message", jo.getJSONArray("errors").getJSONObject(0).getString("message"));
}
else
{
jsonresponse.put("twitter_jo", jo); // this is the full result object from Twitter
}
conn.close();
}
}
catch(HttpException he)
{
System.out.println(he.getMessage());
jsonresponse.put("response_status", "error");
jsonresponse.put("message", "searchTweets HttpException message=" + he.getMessage());
}
catch(NoSuchAlgorithmException nsae)
{
System.out.println(nsae.getMessage());
jsonresponse.put("response_status", "error");
jsonresponse.put("message", "searchTweets NoSuchAlgorithmException message=" + nsae.getMessage());
}
catch(KeyManagementException kme)
{
System.out.println(kme.getMessage());
jsonresponse.put("response_status", "error");
jsonresponse.put("message", "searchTweets KeyManagementException message=" + kme.getMessage());
}
finally {
conn.close();
}
}
catch(JSONException jsone)
{
}
catch(IOException ioe)
{
}
return jsonresponse;
} </code>
and replace the code
String parameter_string = "lang=en&oauth_consumer_key=" + twitter_consumer_key + "&oauth_nonce=" + oauth_nonce + "&oauth_signature_method=" + oauth_signature_method +
"&oauth_timestamp=" + oauth_timestamp + "&oauth_token=" + encode(oauth_token) + "&oauth_version=1.0&q=" + encode(q) + "&result_type=mixed";
with this:
String parameter_string = "id=" + encode(q) + "&oauth_consumer_key=" + twitter_consumer_key + "&oauth_nonce=" + oauth_nonce + "&oauth_signature_method=" + oauth_signature_method +
"&oauth_timestamp=" + oauth_timestamp + "&oauth_token=" + encode(oauth_token) + "&oauth_version=1.0";
Using this, I get a signature base string that is identical to this one found at https://dev.twitter.com/discussions/11927
GET&https%3A%2F%2Fapi.twitter.com%2F1.1%2Ftrends%2Fplace.json&id%3D2450022%26oauth_consumer_key%3D5aA6oofBOFAwN4tfmEYWjg%26oauth_nonce%3Dl7OtaK83Rlv4tQML84ZFydVO2fM3yTCcuBrq6Xh0UAY%26oauth_signature_method%3DHMAC-SHA1%26oauth_timestamp%3D1351010709%26oauth_token%3D119476949-oYGCs2M5duG5QalbOAK2YUZh8zG3ur7DPYo5qIFN%26oauth_version%3D1.0
however, when I do this, I get the error: {“message”:“Twitter auth error.”,“response_status”:“error”}
I know that my authorization keys work because I was able to get the methods already coded in this example to work.
Is there a better way I can implement the trends/ place? Why is this not working?