Google Cloud Pub/Sub provides reliable, many-to-many, asynchronous messaging between applications. Publisher applications can send messages to a topic, and other applications can subscribe to that topic to receive the messages.
This document describes how to use the Google Cloud Client Library to send and receive Google Cloud Pub/Sub messages in an app running in the flexible environment.
Follow the instructions in "Hello, World!" for Python on App Engine to set up your environment and project, and to understand how App Engine Python apps are structured. Write down and save your project ID, because you will need it to run the sample application described in this document.
Clone the sample app
Copy the sample apps to your local machine, and cd to the pubsub directory:
git clone https://github.com/GoogleCloudPlatform/python-docs-samples cd python-docs-samples/appengine/flexible/pubsub
Create a topic and subscription
Create a topic and subscription, which includes specifying the endpoint to which the Pub/Sub server should send requests:
gcloud alpha pubsub topics create [your-topic-name] gcloud alpha pubsub subscriptions create [your-subscription-name] \ --topic [your-topic-name] \ --push-endpoint \ https://[your-app-id].appspot.com/pubsub/push?token=[your-token] \ --ack-deadline 30
app.yamlto set the environment variables for your project ID, topic, and verification token:
env_variables: PUBSUB_TOPIC: your-topic # This token is used to verify that requests originate from your # application. It can be any sufficiently random string. PUBSUB_VERIFICATION_TOKEN: 1234abc
The sample app uses the Google Cloud Client Libraries.
The sample app uses the values you set in the
app.yaml file to configure
environment variables. The push request handler uses these values to confirm
that the request came from Pub/Sub and originated from a trusted source:
app.config['PUBSUB_VERIFICATION_TOKEN'] = \ os.environ['PUBSUB_VERIFICATION_TOKEN'] app.config['PUBSUB_TOPIC'] = os.environ['PUBSUB_TOPIC']
The sample app maintains a global list to store messages received by this instance:
MESSAGES = 
pubsub_push() method receives pushed messages and adds them to the
@app.route('/pubsub/push', methods=['POST']) def pubsub_push(): if (request.args.get('token', '') != current_app.config['PUBSUB_VERIFICATION_TOKEN']): return 'Invalid request', 400 envelope = json.loads(request.data.decode('utf-8')) payload = base64.b64decode(envelope['message']['data']) MESSAGES.append(payload) # Returning any 2xx status indicates successful receipt of the message. return 'OK', 200
index() method interacts with the App Engine web app to publish new messages and display received messages:
@app.route('/', methods=['GET', 'POST']) def index(): if request.method == 'GET': return render_template('index.html', messages=MESSAGES) ps = pubsub.Client() topic = ps.topic(current_app.config['PUBSUB_TOPIC']) topic.publish( request.form.get('payload', 'Example payload').encode('utf-8')) return 'OK', 200
Run the sample locally
When running locally, you can use the Google Cloud SDK to provide authentication
to use Google Cloud APIs. Assuming you set up your environment as described in
Prerequisites, you have already run the
gcloud init command,
which provides this authentication.
Install dependencies, preferably with a
virtualenv env source env/bin/activate pip install -r requirements.txt
Then set environment variables before starting your application:
export GCLOUD_PROJECT=[your-project-id] export PUBSUB_VERIFICATION_TOKEN=[your-verification-token] export PUBSUB_TOPIC=[your-topic] python main.py
Simulate push notifications
The application can send messages locally, but it is not able to receive push
messages locally. You can, however, simulate a push message by making an HTTP
request to the local push notification endpoint. The sample includes the file
sample_message.json. You can use
curl or httpie
to POST this:
curl -i --data @sample_message.json ":8080/pubsub/push?token=[your-token]"
http POST ":8080/pubsub/push?token=[your-token]" < sample_message.json
HTTP/1.0 200 OK Content-Length: 2 Content-Type: text/html; charset=utf-8 Date: Mon, 10 Aug 2015 17:52:03 GMT Server: Werkzeug/0.10.4 Python/2.7.10 OK
After the request completes, you can refresh
localhost:8080 and see the message
in the list of received messages.
Run on App Engine
To deploy the demo app on App Engine using
gcloud, run the following:
gcloud app deploy
You can now access the application at
https://[your-proj-id].appspot.com. You can
use the form to submit messages, but there's no guarantee of which instance of
your application will receive the notification. You can send multiple messages
and refresh the page to see the received message.