Way to print Twitter handle in json via Python with requests module?

Viewed 375

I'm making a Twitter bot to search Twitter for specific keywords and phrases from recent Tweets. I've been using this document as a guide, which uses the Python requests module.

import requests
import json

BEARER_TOKEN = "XYZ"

#define search twitter function
def search_twitter(query, tweet_fields, bearer_token = BEARER_TOKEN):
    headers = {"Authorization": "Bearer {}".format(bearer_token)}

    url = "https://api.twitter.com/2/tweets/search/recent?query={}&{}".format(
        query, tweet_fields
    )
    response = requests.request("GET", url, headers=headers)

    print(response.status_code)

    if response.status_code != 200:
        raise Exception(response.status_code, response.text)
    return response.json()

#search term
query = "new music"
#twitter fields to be returned by api call
tweet_fields = "tweet.fields=text,author_id,created_at"

#twitter api call
json_response = search_twitter(query=query, tweet_fields=tweet_fields, bearer_token=BEARER_TOKEN)
#pretty printing
print(json.dumps(json_response, indent=4, sort_keys=True))

Everything works fine when I run it in the terminal, but I can't seem to find a way to print each Tweet's associated Twitter handle. I can't find the specific documentation/syntax.

I know I have to edit this line of code to include the Twitter handle:

tweet_fields = "tweet.fields=text,author_id,created_at"

Simply put, I also want to print the actual Twitter handle associated with these Tweets. Any and all information would be deeply appreciated.


New code including expansions:

import requests
import json
#its bad practice to place your bearer token directly into the script (this is just done for illustration purposes)
BEARER_TOKEN = "XYZ"
#define search twitter function
def search_twitter(query, tweet_fields, expansions, bearer_token = BEARER_TOKEN):
    headers = {"Authorization": "Bearer {}".format(bearer_token)}

    url = "https://api.twitter.com/2/tweets/search/recent?query={}&{}".format(
        query, tweet_fields, expansions
    )
    response = requests.request("GET", url, headers=headers)

    print(response.status_code)

    if response.status_code != 200:
        raise Exception(response.status_code, response.text)
    return response.json()

#search term
query = "new music"
#twitter fields to be returned by api call
# twitter fields to be returned by api call
tweet_fields = "tweet.fields=author_id,created_at"
expansions = "expansions=author_id"

# twitter api call
json_response = search_twitter(query=query, tweet_fields=tweet_fields, expansions=expansions, bearer_token=BEARER_TOKEN)
#pretty printing
print(json.dumps(json_response, indent=4, sort_keys=True))
1 Answers

You can use expansions in the v2 Twitter API to get back the associated user object in the same call.

The simplest way to illustrate this is with a single Tweet. For example, using curl:

$ curl 'https://api.twitter.com/2/tweets/1212092628029698048?tweet.fields=author_id,created_at&expansions=author_id' --header 'Authorization: Bearer $BEARER_TOKEN'

This requests a Tweet with the default fields (text and id are always included so you do not specifically have to request them) as well as the author_id and created_at values, and then asks for the author_id aka User object to be expanded in the response as well:

{
  "data": {
    "id": "1212092628029698048",
    "author_id": "2244994945",
    "created_at": "2019-12-31T19:26:16.000Z",
    "text": "We believe the best future version of our API will come from building it with YOU. Here’s to another great year with everyone who builds on the Twitter platform. We can’t wait to continue working with you in the new year. <short url removed for SO posting>"
  },
  "includes": {
    "users": [
      {
        "id": "2244994945",
        "name": "Twitter Dev",
        "username": "TwitterDev"
      }
    ]
  }

You will find the handle of the Twitter user in the includes.users.username field.

So, in your code, you could do this:

# twitter fields to be returned by api call
tweet_fields = "tweet.fields=author_id,created_at"
expansions = "expansions=author_id"

# twitter api call
json_response = search_twitter(query=query, tweet_fields=tweet_fields, expansions=expansions, bearer_token=BEARER_TOKEN)

(also add expansions to the search_twitter function as an input, and for the url string formatting)

For an array / list of Tweets that you might get returned from a search call, note that you might need to do a lookup into the includes, as you will get data (Tweet objects) and then includes (User objects + any other expansions you might request), and if the same user is represented more than once in the list of Tweets, it will only be returned once in the includes - in this case, match up the author_id values to find the username for the associated Tweet.

Related