Making Twitter OAuth1 PUT request with JSON body with scribejava - java

I am trying to call this twitter v2 endpoint to hide a tweet using OAuth1 and ScribeJava
Here is what I have tried
val service = ServiceBuilder(apiKey)
.apiSecret(apiSecret)
.build(TwitterApi.instance())
val url = "https://api.twitter.com/2/tweets/${tweetId}/hidden"
val oauth1 = OAuth1AccessToken(token,secret)
val request = OAuthRequest(Verb.PUT, url)
request.setPayload("{ \"hidden\": true }")
service.signRequest(oauth1, request)
val response = service.execute(request)
When I try that I get a 400 Bad Request back, what is the proper way to do this?

The reason of your problem probably has to do with the fact that you are trying to hide a tweet that you do not have the ability to do so. Please, note the restrictions that a tweet must adhere to in order to be hidden. It is stated in the section Step three: Find a Tweet ID to hide in the Twitter developer documentation:
The hide replies endpoint can hide or unhide replies on behalf of an authorized user. Because we are using the Access Tokens related to your user profile in this example, you will be able to hide replies from users who participate in a conversation started by you. Similarly, if you were using Access Tokens that belong to another user that authorized your app, you would be able to moderate replies to any conversations started by that account.
Ask a friend to reply to a Tweet (let them know you're testing hide replies) or reply to any of your Tweets from a test account. Click on that reply, then copy the numeric part of its URL. That will be the Tweet ID we will hide.

Related

How to retrieve access token from Reddit via OAuth flow with Java

I have my authorisation url - https://www.reddit.com/api/v1/authorize?client_id=xuJKekGTr1-V8Q&response_type=code&state=dfDfsd4gdf&redirect_uri=http://localhost:8080/redditimageuploader/callback&duration=permanent&scope=submit
But I don't really know what to do from here? I've found a few guides online but it's just a lot of jargon I don't really understand. When I click on the "allow" button, it takes me to the url that I defined as my redirect_uri, and appended to the end of the string is the state that I set, as well as code= and then a string - so I assume I need to do something with those, but I don't know what.
I was wondering if there is a super simple "explain like I'm 5" step-by-step guide on what to do from here?
It's a standard OAuth flow. From the doc :
When the user clicks the "Sign on with Reddit" button on your website, you must redirect the user to the authorisation URL at Reddit - the one in your question, starting with https://www.reddit.com/api/v1/authorize and enriched with the request params you specified. Reddit will then ask the user to sign in, and whether or not he wants to authorise your app access to the requested scope. See https://github.com/reddit-archive/reddit/wiki/OAuth2#allowing-the-user-to-authorize-your-application
If the user agrees, then Reddit will redirect the user to the redirect URI you specified as request param in the authorisation URL (in your case, http://localhost:8080/redditimageuploader/callback). Reddit will add a state request param: you need to ensure that this is the same as the one in your request.
Retrieve the access token with a POST request to https://www.reddit.com/api/v1/access_token, including the following data in your data: grant_type=authorization_code&code=CODE&redirect_uri=URI. Replace CODE with the value you received and URI with your same redirect URI as in the first step.
The response to this third step should return you an access token: store this for future requests on behalf of the user. See https://github.com/reddit-archive/reddit/wiki/OAuth2#retrieving-the-access-token
Extra steps are available and documented for error handling and access token operations (invalidation / renewal).
So, once you've correctly implemented the first step, all you need to do is create an endpoint (the one called when your redirect URI is redirected to) which will :
check the state request param
Retrieve the access token (third step) and store it
Let me know if this is clear enough.

How to get user information after REST authentication on client side?

I have Spring REST backend and Angular frontend.
Authentication is performed using a POST request to "/login" URL with username and password inside request JSON body (I use form based authentication).
REST backend replies with OK code. Everything is fine and I can perform other requests from frontend that requires authentication.
But frontend need to know what is the role of authenticated user so that it can display a proper view/rote for it. And where can we get this role on a frontend? The only response we got from authentication was OK and that is fine for REST.
We can get user information by performing GET request to "/users/[user_id]". But we don't have user id, just user name.
So the question is - what is a correct way for REST to get role (or other user information) from frontend having just user name?
As a workaround I can create new request on a backend that takes user name instead of id, or I can add user id to authentication response. But I'm not really sure that is a correct way from REST perspective.
You can not override HTTP Methods.So,if you are planning to write GET call with diffrent query parameters with the same path,then it is not allowed.You need to write two GET paths.
e.g.
GET /users/userid/{id}
GET /users/username/{name}
And in the second call,you can add desired logic for getting role in the second one.
There are two way's of doing it.
1) After successful authentication from the server, do one more $http call to the server with username from which you can fetch details from a server logic that fetches and store that result in the $rootScope.This info will be available through out the app.
2) When you are authenticating the user, if the user is valid then fetch his details and store those in an object.
Now in your server logic while returning response you can do like below
response.setHeaders("User",userDetilsObj);
NOTE: response is a HttpServletResponse object.
After the request is completed as you said we will get a status OK response that is 200. To access the user details at JS side follow below code
if(response.status == '200/OK'){
$rootScope.user = response.getHeaders().User;//In this object all the user details set at server side are available now..
}
Hope this gives you some light on how to achieve your desired results.
Get the user information from server at the the time when you authenticates the user.Pass the user details on successful user authentication.
After discussing the issue with #JBNizet in comments I decided to change REST endpoint from "/users/:user_id" to "/users/:user_name".

Android, AccountManager and OAuth

I'm sure this is basic and I'm missing something. I've read through other answers on SO, I've googled, I've read resources and I just can't wrap my head around what I need to do.
I'm trying to figure out how to write an app that connects to Twitch's API, specifically how to authenticate with Twitch's api. Their documentation is here: https://github.com/justintv/Twitch-API/blob/master/authentication.md
I've created an app and stored my keys.
Now comes the part where I want my user to click a button which launches the authentication on their website. From what I can tell I do this by using an AccountManager. Except... I can't figure out what I'm supposed to do.
Here's the excerpt I've found online:
AccountManager am = AccountManager.get(this);
Bundle options = new Bundle();
am.getAuthToken(
myAccount_, // Account retrieved using getAccountsByType()
"Manage your tasks", // Auth scope
options, // Authenticator-specific options
this, // Your activity
new OnTokenAcquired(), // Callback called when a token is successfully acquired
new Handler(new OnError())); // Callback called if an error occurs
According to twitch's documentation I want to send the user to:
https://api.twitch.tv/kraken/oauth2/authorize
?response_type=code
&client_id=[your client ID]
&redirect_uri=[your registered redirect URI]
&scope=[space separated list of scopes]
&state=[your provided unique token]
And I simply have no idea how these two things need to be combined.
Firstly, I recommend to read the OAuth2 RFC. This should cover everything you need to know.
The AccountManager code snippet won't help you much unless there already is an app that provides authentication for Twitch. If that's not the case you either need to use an existing OAuth2 library or implement your own.
You could write your own AccountAuthenticator but that's a different challenge (and you still need some kind of OAuth2 client).
Doing it yourself is not that hard, see below.
Steps to implement it yourself
Twitch recommends to use the "Implicit Grant Flow" for mobile apps. That's what I'm going to describe below.
1. Get a client ID
Register your app as outlined in Developer Setup to get a client ID
As redirect URI you can use something like https://localhost:12398/, the actual port doesn't really matter.
2. Build the authentication URL
In your client app you need to construct the authentication URL like so:
https://api.twitch.tv/kraken/oauth2/authorize?
response_type=token&
client_id=[your client ID]&
redirect_uri=[your registered redirect URI]&
scope=[space separated list of scopes]
Apparently [your client ID] should be replaced by the client ID you've received from Twitch, same goes for [your registered redirect URI] (that's the URL above, i.e. https://localhost:12398/). [space separated list of scopes] is the list of scopes (i.e. features your want to access), see Scopes. Make sure you URL-encode the parameter values properly.
Assuming your client ID is 123456 and the scopes you need are user_read and channel_read your URL would look like this:
https://api.twitch.tv/kraken/oauth2/authorize?
response_type=token&
client_id=123456&
redirect_uri=https%3A%2F%2Flocalhost%3A12398%2F&
scope=user_read%20channel_read
Note that you should also pass a state parameter, just use a randomly generated value. You can also append the (non-standard) force_verify parameter to make sure the user actually needs to log in each time (instead of continuing a previous session), but I think you can achieve the same by clearing the cookie store (given that you open the URL in a webview in the context of your app) before you open the login page.
With a random state the URL would look like this:
https://api.twitch.tv/kraken/oauth2/authorize?
response_type=token&
client_id=123456&
redirect_uri=https%3A%2F%2Flocalhost%3A12398%2F&
scope=user_read%20channel_read&
state=82hdknaizuVBfd9847guHUIhndzhuehnb
Again, make sure the state value is properly URL encoded.
3. Open the authentication URL
Ideally you just open the URL in a WebView inside of your app. In that case you need to intercept all request to load a new URL using WebViewClient.shouldOverrideUrlLoading
Once the client is redirected to your redirect URL you can close the webview and continue with step 4.
Theoretically it's possible to utilize the default browser to do the authentication, but I would have security concerns since an external app could learn about your client ID and the access token.
4. Extract the access token
The actual URL you get redirected to in step #3 will have the form:
https://[your registered redirect URI]/#access_token=[an access token]&scope=[authorized scopes]
or to pick up the example
https://localhost:12398/#access_token=xxx&scope=user_read%20channel_read
Where xxx is the actual access token.
If you passed a state it will be present like so:
https://localhost:12398/#access_token=xxx&scope=user_read%20channel_read&state=82hdknaizuVBfd9847guHUIhndzhuehnb
All you have to do now is to parse the (URL encoded) access token, scope and state. Compare the scopes and state to the ones that you actually sent. If they match you can start using the access_token to authenticate.
Note According to the OAuth2 RFC, the response URL MUST also contain a token_type and it SHOULD contain an expires_in duration in seconds.
Once you received the access token you can use it to authenticate as described here.
Access tokens issued by the Implicit Grant Flow usually expire after a certain time and the user needs to authenticate again. The Twitch documentation doesn't mention any expiration time, so it's possible that the token is valid forever. So make sure your app doesn't store it or store it in a secure way (like using Android's key store provider to generate and store a key to encrypt the access token).
If the implicitly issued access token expires you could consider using the "Authorization Code Flow". That's quite similar but it contains an additional step to receive the access token and a "refresh token" that can be used to renew the access token. I leave it up to you to figure out how that works.

Post on Facebook pages via Graph API with Facebook4j

I want to create a tool wich allow a user to post his planning on several media at once : he has to fill a form with his establishment week planning, then I post it via newsletter, on his facebook and on his website.
I am struggling with the facebook part. I created an app and made the page subscribe to this app then I tried to use Facebook4j to post something on the page but I am not even able to get the page.
Here is my code :
Facebook facebook = new FacebookFactory().getInstance();
facebook.setOAuthAppId("{app_id}", "{app_secret}");
facebook.setOAuthPermissions("public_profile, manage_pages, publish_pages, publish_actions");
facebook.setOAuthAccessToken(new AccessToken("app_id|app_secret", null));
try {
ResponseList<Account> accounts = facebook.getAccounts();
} catch (FacebookException e) {
e.printStackTrace();
}
which always return me the error :
An active access token must be used to query information about the current user.
How can I have an active access token in order to post on pages which suscribed to my app?
NB : I am not sure I actually need an app. If there is an other way to post on multiple pages without asking for logging each time, I am ok with that too. (some kind of permanent page token maybe?)
Thanks!
Okay first, yes you need an app to perform these requests.
To get what you describe you are requesting the permissions needed correctly, you still miss one - namely pages_show_list.
In addition you have to set the OAuthAccessToken to the users token not to the app token.

Post to Facebook Page wall using RestFB api

I am trying to post on the wall of a facebook page. I am able to post on the user wall using App Access token.
I got the App Access Token through extending the DefaultFacebookClient
public class ConnectionService extends DefaultFacebookClient{
public ConnectionService(String appId, String appSecret) {
AccessToken accessToken = this.obtainAppAccessToken(appId, appSecret);
this.accessToken = accessToken.getAccessToken();
}
}
With this I am able to post to user wall using the appID and appSecret. But when I tried to post to Page Wall
i get error of " The user hasn't authorized the application to perform this action"
Anyone can advice?
To post on a facebook page wall, you will need to follow these steps:
Head over to https://developers.facebook.com/tools/explorer
Click on "Get Access Token"
Under "Extended Permissions" tab, select select manage_pages and publish_actions and hit "Get Access Token"
Now under Graph API, under Get call, type in "me/accounts" and hit Submit
In the screen below, you will see the "data" json object with all your pages and page access tokens.
Grab the desired page token access and replace the PAGE_ACCESS_TOKEN in the code below with this token.
Replace PAGE_NAME with your page name (the page name slug in the URL).
Run the below code and that should do the job :)
final FacebookClient fb = new DefaultFacebookClient(PAGE_ACCESS_TOKEN);
final Page page = facebookClient.fetchObject(PAGE_NAME, Page.class);
facebookClient.publish("PAGE_NAME/feed", FacebookType.class, Parameter.with("message", "RestFB test"));
The App Access Token is the most basic one, and will not allow you to post anything. In order to post something to a Facebook Page (as a Page), you need to get a Page Access Token.
The process is a bit complicated, because you actually need to authorize the user with the "manage_pages" permission first, with the User Access Token you can call the API to get a Page Access Token (/me/accounts).
See those links:
https://developers.facebook.com/docs/facebook-login/
https://developers.facebook.com/docs/facebook-login/access-tokens/
http://www.devils-heaven.com/facebook-access-tokens/
Btw, the REST API is deprecated: https://developers.facebook.com/blog/post/616/
You can also try the "Client Token" (Developer Settings > Advanced), i never worked with that one but it could be the easiest solution. In any case, an App Access Token is the wrong one.
Make sure that the scopes you mentioned while authenticating user includes manage_pages also. This error occurs when you have not included this in your scope. Refer this
Since u r generating access token from java class. u can set the permissions u require from user in ur manage app link from ur facebook profile page and get the access token here.....

Categories

Resources