diff --git a/.travis.yml b/.travis.yml index a9e63469ff..d6f950e40b 100644 --- a/.travis.yml +++ b/.travis.yml @@ -27,7 +27,14 @@ before_install: - php dump_credentials.php script: + # run bigquery tests - cd bigquery/api - composer install - phpunit mainTest.php - phpunit utilTest.php + - cd ../.. + # run pubsub tests + - cd pubsub + - composer install + - phpunit test + - cd .. diff --git a/pubsub/README.md b/pubsub/README.md new file mode 100644 index 0000000000..530e4706c4 --- /dev/null +++ b/pubsub/README.md @@ -0,0 +1,75 @@ +# Google PubSub PHP Sample Application + +## Description + +Note: The push endpoints don't work with the App Engine's local +devserver. The push notifications will go to an HTTP URL on the App +Engine server even when you run this sample locally. So we recommend +you deploy and run the app on App Engine. +TODO(tmatsuo): Better implementation for devserver. + +## Register your application + +- Go to + [Google Developers Console](https://console.developers.google.com/project) + and create a new project. This will automatically enable an App + Engine application with the same ID as the project. + +- Enable the "Google Cloud Pub/Sub" API under "APIs & auth > APIs." + +- For local development also follow the instructions below. + + - Go to "Credentials" and create a new Service Account. + + - Select "Generate new JSON key", then download a new JSON file. + + - Set the following environment variable. + + GOOGLE_APPLICATION_CREDENTIALS: the file path to the downloaded JSON file. + +## Prerequisites + +- Install [`composer`](https://getcomposer.org) +- Install the App Engine Python SDK. + We recommend you install + [Cloud SDK](https://developers.google.com/cloud/sdk/) rather than + just installing App Engine SDK. + +- Install Google API client library for PHP into 'lib' directory by running: + +``` +$ composer install +``` + +## Configuration + +- Edit config.json + - Replace '{A_UNIQUE_TOKEN}' with an arbitrary secret string of + your choice to protect the endpoint from abuse. + + - Replace '{YOUR_PROJECT_ID}' with your project ID + +## Deploy the application to App Engine + +``` +$ gcloud preview app deploy app.yaml --set-default --project YOUR_PROJECT_ID +``` + +Then access the following URL: + https://{YOUR_PROJECT_ID}.appspot.com/ + +## Run the application locally + +``` +$ dev_appserver.py -A your-project-id . +``` + +## Contributing changes + +* See [CONTRIBUTING.md](../CONTRIBUTING.md) + +## Licensing + +* See [LICENSE](../LICENSE) + + diff --git a/pubsub/app.yaml b/pubsub/app.yaml new file mode 100644 index 0000000000..166e1655fc --- /dev/null +++ b/pubsub/app.yaml @@ -0,0 +1,9 @@ +runtime: php55 +api_version: 1 +threadsafe: true + +handlers: +- url: /js + static_dir: web/js +- url: /.* + script: web/index.php diff --git a/pubsub/composer.json b/pubsub/composer.json new file mode 100644 index 0000000000..494853523a --- /dev/null +++ b/pubsub/composer.json @@ -0,0 +1,19 @@ +{ + "autoload": { + "psr-4": { + "GoogleCloudPlatform\\DocsSamples\\Pubsub\\": "src" + } + }, + "require": { + "php": ">=5.4", + "silex/silex": "~1.3", + "twig/twig": "~1.8|~2.0", + "symfony/twig-bridge": "~2.7|3.0.*", + "google/apiclient": "~2.0@dev" + }, + "require-dev": { + "symfony/dom-crawler": "~2.0", + "symfony/css-selector": "~2.0", + "symfony/browser-kit": "~2.7" + } +} diff --git a/pubsub/composer.lock b/pubsub/composer.lock new file mode 100644 index 0000000000..c5153b3b37 --- /dev/null +++ b/pubsub/composer.lock @@ -0,0 +1,1302 @@ +{ + "_readme": [ + "This file locks the dependencies of your project to a known state", + "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file", + "This file is @generated automatically" + ], + "hash": "599a8f73822924071c73244606ef1e51", + "content-hash": "d9b3373f7810fb679ff38b016ce7af79", + "packages": [ + { + "name": "firebase/php-jwt", + "version": "2.0.0", + "target-dir": "Firebase/PHP-JWT", + "source": { + "type": "git", + "url": "https://github.com/firebase/php-jwt.git", + "reference": "ffcfd888ce1e4f2d70cac2dc9b7301038332fe57" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/firebase/php-jwt/zipball/ffcfd888ce1e4f2d70cac2dc9b7301038332fe57", + "reference": "ffcfd888ce1e4f2d70cac2dc9b7301038332fe57", + "shasum": "" + }, + "require": { + "php": ">=5.2.0" + }, + "type": "library", + "autoload": { + "classmap": [ + "Authentication/", + "Exceptions/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Neuman Vong", + "email": "neuman+pear@twilio.com", + "role": "Developer" + }, + { + "name": "Anant Narayanan", + "email": "anant@php.net", + "role": "Developer" + } + ], + "description": "A simple library to encode and decode JSON Web Tokens (JWT) in PHP. Should conform to the current spec.", + "homepage": "https://github.com/firebase/php-jwt", + "time": "2015-04-01 18:46:38" + }, + { + "name": "google/apiclient", + "version": "dev-master", + "source": { + "type": "git", + "url": "https://github.com/google/google-api-php-client.git", + "reference": "ab953b94258bf54284f3ff2051e254fea32a9b38" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/google/google-api-php-client/zipball/ab953b94258bf54284f3ff2051e254fea32a9b38", + "reference": "ab953b94258bf54284f3ff2051e254fea32a9b38", + "shasum": "" + }, + "require": { + "google/auth": "v0.3", + "guzzlehttp/guzzle": "5.2.*", + "monolog/monolog": "^1.17", + "php": ">=5.4", + "phpseclib/phpseclib": "~2.0" + }, + "require-dev": { + "phpunit/phpunit": "~4", + "squizlabs/php_codesniffer": "~2.3", + "symfony/css-selector": "~2.0", + "symfony/dom-crawler": "~2.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.x-dev" + } + }, + "autoload": { + "psr-0": { + "Google_": "src/" + }, + "classmap": [ + "src/Google/Service/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "Apache-2.0" + ], + "description": "Client library for Google APIs", + "homepage": "http://developers.google.com/api-client-library/php", + "keywords": [ + "google" + ], + "time": "2015-10-28 19:50:34" + }, + { + "name": "google/auth", + "version": "v0.3", + "source": { + "type": "git", + "url": "https://github.com/google/google-auth-library-php.git", + "reference": "eed7a670da42f7fedd1d1b16f7be1f2be59bbcc2" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/google/google-auth-library-php/zipball/eed7a670da42f7fedd1d1b16f7be1f2be59bbcc2", + "reference": "eed7a670da42f7fedd1d1b16f7be1f2be59bbcc2", + "shasum": "" + }, + "require": { + "firebase/php-jwt": "2.0.0", + "guzzlehttp/guzzle": "5.2.*", + "php": ">=5.4" + }, + "require-dev": { + "phplint/phplint": "0.0.1", + "phpunit/phpunit": "3.7.*" + }, + "type": "library", + "autoload": { + "classmap": [ + "src/" + ], + "psr-4": { + "Google\\Auth\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "Apache-2.0" + ], + "description": "Google Auth Library for PHP", + "homepage": "http://github.com/google/google-auth-library-php", + "keywords": [ + "Authentication", + "google", + "oauth2" + ], + "time": "2015-10-23 21:25:29" + }, + { + "name": "guzzlehttp/guzzle", + "version": "5.2.0", + "source": { + "type": "git", + "url": "https://github.com/guzzle/guzzle.git", + "reference": "475b29ccd411f2fa8a408e64576418728c032cfa" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/guzzle/zipball/475b29ccd411f2fa8a408e64576418728c032cfa", + "reference": "475b29ccd411f2fa8a408e64576418728c032cfa", + "shasum": "" + }, + "require": { + "guzzlehttp/ringphp": "~1.0", + "php": ">=5.4.0" + }, + "require-dev": { + "ext-curl": "*", + "phpunit/phpunit": "~4.0", + "psr/log": "~1.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "5.0-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + } + ], + "description": "Guzzle is a PHP HTTP client library and framework for building RESTful web service clients", + "homepage": "http://guzzlephp.org/", + "keywords": [ + "client", + "curl", + "framework", + "http", + "http client", + "rest", + "web service" + ], + "time": "2015-01-28 01:03:29" + }, + { + "name": "guzzlehttp/ringphp", + "version": "1.1.0", + "source": { + "type": "git", + "url": "https://github.com/guzzle/RingPHP.git", + "reference": "dbbb91d7f6c191e5e405e900e3102ac7f261bc0b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/RingPHP/zipball/dbbb91d7f6c191e5e405e900e3102ac7f261bc0b", + "reference": "dbbb91d7f6c191e5e405e900e3102ac7f261bc0b", + "shasum": "" + }, + "require": { + "guzzlehttp/streams": "~3.0", + "php": ">=5.4.0", + "react/promise": "~2.0" + }, + "require-dev": { + "ext-curl": "*", + "phpunit/phpunit": "~4.0" + }, + "suggest": { + "ext-curl": "Guzzle will use specific adapters if cURL is present" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.1-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\Ring\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + } + ], + "description": "Provides a simple API and specification that abstracts away the details of HTTP into a single PHP function.", + "time": "2015-05-20 03:37:09" + }, + { + "name": "guzzlehttp/streams", + "version": "3.0.0", + "source": { + "type": "git", + "url": "https://github.com/guzzle/streams.git", + "reference": "47aaa48e27dae43d39fc1cea0ccf0d84ac1a2ba5" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/streams/zipball/47aaa48e27dae43d39fc1cea0ccf0d84ac1a2ba5", + "reference": "47aaa48e27dae43d39fc1cea0ccf0d84ac1a2ba5", + "shasum": "" + }, + "require": { + "php": ">=5.4.0" + }, + "require-dev": { + "phpunit/phpunit": "~4.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\Stream\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + } + ], + "description": "Provides a simple abstraction over streams of data", + "homepage": "http://guzzlephp.org/", + "keywords": [ + "Guzzle", + "stream" + ], + "time": "2014-10-12 19:18:40" + }, + { + "name": "monolog/monolog", + "version": "1.17.2", + "source": { + "type": "git", + "url": "https://github.com/Seldaek/monolog.git", + "reference": "bee7f0dc9c3e0b69a6039697533dca1e845c8c24" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/Seldaek/monolog/zipball/bee7f0dc9c3e0b69a6039697533dca1e845c8c24", + "reference": "bee7f0dc9c3e0b69a6039697533dca1e845c8c24", + "shasum": "" + }, + "require": { + "php": ">=5.3.0", + "psr/log": "~1.0" + }, + "provide": { + "psr/log-implementation": "1.0.0" + }, + "require-dev": { + "aws/aws-sdk-php": "^2.4.9", + "doctrine/couchdb": "~1.0@dev", + "graylog2/gelf-php": "~1.0", + "jakub-onderka/php-parallel-lint": "0.9", + "php-console/php-console": "^3.1.3", + "phpunit/phpunit": "~4.5", + "phpunit/phpunit-mock-objects": "2.3.0", + "raven/raven": "^0.13", + "ruflin/elastica": ">=0.90 <3.0", + "swiftmailer/swiftmailer": "~5.3", + "videlalvaro/php-amqplib": "~2.4" + }, + "suggest": { + "aws/aws-sdk-php": "Allow sending log messages to AWS services like DynamoDB", + "doctrine/couchdb": "Allow sending log messages to a CouchDB server", + "ext-amqp": "Allow sending log messages to an AMQP server (1.0+ required)", + "ext-mongo": "Allow sending log messages to a MongoDB server", + "graylog2/gelf-php": "Allow sending log messages to a GrayLog2 server", + "php-console/php-console": "Allow sending log messages to Google Chrome", + "raven/raven": "Allow sending log messages to a Sentry server", + "rollbar/rollbar": "Allow sending log messages to Rollbar", + "ruflin/elastica": "Allow sending log messages to an Elastic Search server", + "videlalvaro/php-amqplib": "Allow sending log messages to an AMQP server using php-amqplib" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.16.x-dev" + } + }, + "autoload": { + "psr-4": { + "Monolog\\": "src/Monolog" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jordi Boggiano", + "email": "j.boggiano@seld.be", + "homepage": "http://seld.be/" + } + ], + "description": "Sends your logs to files, sockets, inboxes, databases and various web services", + "homepage": "http://github.com/Seldaek/monolog", + "keywords": [ + "log", + "logging", + "psr-3" + ], + "time": "2015-10-14 12:51:02" + }, + { + "name": "phpseclib/phpseclib", + "version": "2.0.0", + "source": { + "type": "git", + "url": "https://github.com/phpseclib/phpseclib.git", + "reference": "a74aa9efbe61430fcb60157c8e025a48ec8ff604" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpseclib/phpseclib/zipball/a74aa9efbe61430fcb60157c8e025a48ec8ff604", + "reference": "a74aa9efbe61430fcb60157c8e025a48ec8ff604", + "shasum": "" + }, + "require": { + "php": ">=5.3.3" + }, + "require-dev": { + "phing/phing": "~2.7", + "phpunit/phpunit": "~4.0", + "sami/sami": "~2.0", + "squizlabs/php_codesniffer": "~2.0" + }, + "suggest": { + "ext-gmp": "Install the GMP (GNU Multiple Precision) extension in order to speed up arbitrary precision integer arithmetic operations.", + "ext-libsodium": "SSH2/SFTP can make use of some algorithms provided by the libsodium-php extension.", + "ext-mcrypt": "Install the Mcrypt extension in order to speed up a few other cryptographic operations.", + "ext-openssl": "Install the OpenSSL extension in order to speed up a wide variety of cryptographic operations.", + "pear-pear/PHP_Compat": "Install PHP_Compat to get phpseclib working on PHP < 5.0.0." + }, + "type": "library", + "autoload": { + "psr-4": { + "phpseclib\\": "phpseclib/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "include-path": [ + "phpseclib/" + ], + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jim Wigginton", + "email": "terrafrost@php.net", + "role": "Lead Developer" + }, + { + "name": "Patrick Monnerat", + "email": "pm@datasphere.ch", + "role": "Developer" + }, + { + "name": "Andreas Fischer", + "email": "bantu@phpbb.com", + "role": "Developer" + }, + { + "name": "Hans-Jürgen Petrich", + "email": "petrich@tronic-media.com", + "role": "Developer" + } + ], + "description": "PHP Secure Communications Library - Pure-PHP implementations of RSA, AES, SSH2, SFTP, X.509 etc.", + "homepage": "http://phpseclib.sourceforge.net/", + "keywords": [ + "BigInteger", + "aes", + "asn.1", + "asn1", + "blowfish", + "crypto", + "cryptography", + "encryption", + "rsa", + "security", + "sftp", + "signature", + "signing", + "ssh", + "twofish", + "x.509", + "x509" + ], + "time": "2015-08-04 04:48:03" + }, + { + "name": "pimple/pimple", + "version": "v1.1.1", + "source": { + "type": "git", + "url": "https://github.com/silexphp/Pimple.git", + "reference": "2019c145fe393923f3441b23f29bbdfaa5c58c4d" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/silexphp/Pimple/zipball/2019c145fe393923f3441b23f29bbdfaa5c58c4d", + "reference": "2019c145fe393923f3441b23f29bbdfaa5c58c4d", + "shasum": "" + }, + "require": { + "php": ">=5.3.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.1.x-dev" + } + }, + "autoload": { + "psr-0": { + "Pimple": "lib/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + } + ], + "description": "Pimple is a simple Dependency Injection Container for PHP 5.3", + "homepage": "http://pimple.sensiolabs.org/", + "keywords": [ + "container", + "dependency injection" + ], + "time": "2013-11-22 08:30:29" + }, + { + "name": "psr/log", + "version": "1.0.0", + "source": { + "type": "git", + "url": "https://github.com/php-fig/log.git", + "reference": "fe0936ee26643249e916849d48e3a51d5f5e278b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/log/zipball/fe0936ee26643249e916849d48e3a51d5f5e278b", + "reference": "fe0936ee26643249e916849d48e3a51d5f5e278b", + "shasum": "" + }, + "type": "library", + "autoload": { + "psr-0": { + "Psr\\Log\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Common interface for logging libraries", + "keywords": [ + "log", + "psr", + "psr-3" + ], + "time": "2012-12-21 11:40:51" + }, + { + "name": "react/promise", + "version": "v2.2.1", + "source": { + "type": "git", + "url": "https://github.com/reactphp/promise.git", + "reference": "3b6fca09c7d56321057fa8867c8dbe1abf648627" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/reactphp/promise/zipball/3b6fca09c7d56321057fa8867c8dbe1abf648627", + "reference": "3b6fca09c7d56321057fa8867c8dbe1abf648627", + "shasum": "" + }, + "require": { + "php": ">=5.4.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "psr-4": { + "React\\Promise\\": "src/" + }, + "files": [ + "src/functions_include.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jan Sorgalla", + "email": "jsorgalla@gmail.com" + } + ], + "description": "A lightweight implementation of CommonJS Promises/A for PHP", + "time": "2015-07-03 13:48:55" + }, + { + "name": "silex/silex", + "version": "v1.3.4", + "source": { + "type": "git", + "url": "https://github.com/silexphp/Silex.git", + "reference": "d6de62716fcda76084f3015165125f30b1563517" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/silexphp/Silex/zipball/d6de62716fcda76084f3015165125f30b1563517", + "reference": "d6de62716fcda76084f3015165125f30b1563517", + "shasum": "" + }, + "require": { + "php": ">=5.3.9", + "pimple/pimple": "~1.0", + "symfony/event-dispatcher": "~2.3|3.0.*", + "symfony/http-foundation": "~2.3|3.0.*", + "symfony/http-kernel": "~2.3|3.0.*", + "symfony/routing": "~2.3|3.0.*" + }, + "require-dev": { + "doctrine/dbal": "~2.2", + "monolog/monolog": "^1.4.1", + "swiftmailer/swiftmailer": "~5", + "symfony/browser-kit": "~2.3|3.0.*", + "symfony/config": "~2.3|3.0.*", + "symfony/css-selector": "~2.3|3.0.*", + "symfony/debug": "~2.3|3.0.*", + "symfony/dom-crawler": "~2.3|3.0.*", + "symfony/finder": "~2.3|3.0.*", + "symfony/form": "~2.3|3.0.*", + "symfony/locale": "~2.3|3.0.*", + "symfony/monolog-bridge": "~2.3|3.0.*", + "symfony/options-resolver": "~2.3|3.0.*", + "symfony/phpunit-bridge": "~2.7", + "symfony/process": "~2.3|3.0.*", + "symfony/security": "~2.3|3.0.*", + "symfony/serializer": "~2.3|3.0.*", + "symfony/translation": "~2.3|3.0.*", + "symfony/twig-bridge": "~2.3|3.0.*", + "symfony/validator": "~2.3|3.0.*", + "twig/twig": "~1.8|~2.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.3.x-dev" + } + }, + "autoload": { + "psr-4": { + "Silex\\": "src/Silex" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Igor Wiedler", + "email": "igor@wiedler.ch" + } + ], + "description": "The PHP micro-framework based on the Symfony Components", + "homepage": "http://silex.sensiolabs.org/", + "keywords": [ + "microframework" + ], + "time": "2015-09-15 06:53:42" + }, + { + "name": "symfony/debug", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/debug.git", + "reference": "fb9e6887db716939f41af0ba8ef38a1582eb501b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/debug/zipball/fb9e6887db716939f41af0ba8ef38a1582eb501b", + "reference": "fb9e6887db716939f41af0ba8ef38a1582eb501b", + "shasum": "" + }, + "require": { + "php": ">=5.3.9", + "psr/log": "~1.0" + }, + "conflict": { + "symfony/http-kernel": ">=2.3,<2.3.24|~2.4.0|>=2.5,<2.5.9|>=2.6,<2.6.2" + }, + "require-dev": { + "symfony/class-loader": "~2.2", + "symfony/http-kernel": "~2.3.24|~2.5.9|~2.6,>=2.6.2" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\Debug\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony Debug Component", + "homepage": "https://symfony.com/", + "time": "2015-10-11 09:39:48" + }, + { + "name": "symfony/event-dispatcher", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/event-dispatcher.git", + "reference": "87a5db5ea887763fa3a31a5471b512ff1596d9b8" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/87a5db5ea887763fa3a31a5471b512ff1596d9b8", + "reference": "87a5db5ea887763fa3a31a5471b512ff1596d9b8", + "shasum": "" + }, + "require": { + "php": ">=5.3.9" + }, + "require-dev": { + "psr/log": "~1.0", + "symfony/config": "~2.0,>=2.0.5", + "symfony/dependency-injection": "~2.6", + "symfony/expression-language": "~2.6", + "symfony/stopwatch": "~2.3" + }, + "suggest": { + "symfony/dependency-injection": "", + "symfony/http-kernel": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\EventDispatcher\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony EventDispatcher Component", + "homepage": "https://symfony.com/", + "time": "2015-10-11 09:39:48" + }, + { + "name": "symfony/http-foundation", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/http-foundation.git", + "reference": "7598eea151ae3d4134df1f9957364b17809eea75" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/http-foundation/zipball/7598eea151ae3d4134df1f9957364b17809eea75", + "reference": "7598eea151ae3d4134df1f9957364b17809eea75", + "shasum": "" + }, + "require": { + "php": ">=5.3.9" + }, + "require-dev": { + "symfony/expression-language": "~2.4" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\HttpFoundation\\": "" + }, + "classmap": [ + "Resources/stubs" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony HttpFoundation Component", + "homepage": "https://symfony.com/", + "time": "2015-10-23 14:47:27" + }, + { + "name": "symfony/http-kernel", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/http-kernel.git", + "reference": "4260f2273a446a6715063dc9ca89fd0c475c2f77" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/http-kernel/zipball/4260f2273a446a6715063dc9ca89fd0c475c2f77", + "reference": "4260f2273a446a6715063dc9ca89fd0c475c2f77", + "shasum": "" + }, + "require": { + "php": ">=5.3.9", + "psr/log": "~1.0", + "symfony/debug": "~2.6,>=2.6.2", + "symfony/event-dispatcher": "~2.6,>=2.6.7", + "symfony/http-foundation": "~2.5,>=2.5.4" + }, + "conflict": { + "symfony/config": "<2.7" + }, + "require-dev": { + "symfony/browser-kit": "~2.3", + "symfony/class-loader": "~2.1", + "symfony/config": "~2.7", + "symfony/console": "~2.3", + "symfony/css-selector": "~2.0,>=2.0.5", + "symfony/dependency-injection": "~2.2", + "symfony/dom-crawler": "~2.0,>=2.0.5", + "symfony/expression-language": "~2.4", + "symfony/finder": "~2.0,>=2.0.5", + "symfony/process": "~2.0,>=2.0.5", + "symfony/routing": "~2.2", + "symfony/stopwatch": "~2.3", + "symfony/templating": "~2.2", + "symfony/translation": "~2.0,>=2.0.5", + "symfony/var-dumper": "~2.6" + }, + "suggest": { + "symfony/browser-kit": "", + "symfony/class-loader": "", + "symfony/config": "", + "symfony/console": "", + "symfony/dependency-injection": "", + "symfony/finder": "", + "symfony/var-dumper": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\HttpKernel\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony HttpKernel Component", + "homepage": "https://symfony.com/", + "time": "2015-10-27 19:07:21" + }, + { + "name": "symfony/routing", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/routing.git", + "reference": "f353e1f588679c3ec987624e6c617646bd01ba38" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/routing/zipball/f353e1f588679c3ec987624e6c617646bd01ba38", + "reference": "f353e1f588679c3ec987624e6c617646bd01ba38", + "shasum": "" + }, + "require": { + "php": ">=5.3.9" + }, + "conflict": { + "symfony/config": "<2.7" + }, + "require-dev": { + "doctrine/annotations": "~1.0", + "doctrine/common": "~2.2", + "psr/log": "~1.0", + "symfony/config": "~2.7", + "symfony/expression-language": "~2.4", + "symfony/http-foundation": "~2.3", + "symfony/yaml": "~2.0,>=2.0.5" + }, + "suggest": { + "doctrine/annotations": "For using the annotation loader", + "symfony/config": "For using the all-in-one router or any loader", + "symfony/expression-language": "For using expression matching", + "symfony/yaml": "For using the YAML loader" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\Routing\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony Routing Component", + "homepage": "https://symfony.com/", + "keywords": [ + "router", + "routing", + "uri", + "url" + ], + "time": "2015-10-27 15:38:06" + }, + { + "name": "symfony/twig-bridge", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/twig-bridge.git", + "reference": "3dd44937b1e08af8c8f6b14850f4b9c4d1039c6f" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/twig-bridge/zipball/3dd44937b1e08af8c8f6b14850f4b9c4d1039c6f", + "reference": "3dd44937b1e08af8c8f6b14850f4b9c4d1039c6f", + "shasum": "" + }, + "require": { + "php": ">=5.3.9", + "twig/twig": "~1.20|~2.0" + }, + "require-dev": { + "symfony/asset": "~2.7", + "symfony/console": "~2.7", + "symfony/expression-language": "~2.4", + "symfony/finder": "~2.3", + "symfony/form": "~2.7,>=2.7.6", + "symfony/http-kernel": "~2.3", + "symfony/intl": "~2.3", + "symfony/routing": "~2.2", + "symfony/security": "~2.6", + "symfony/security-acl": "~2.6", + "symfony/stopwatch": "~2.2", + "symfony/templating": "~2.1", + "symfony/translation": "~2.7", + "symfony/var-dumper": "~2.6", + "symfony/yaml": "~2.0,>=2.0.5" + }, + "suggest": { + "symfony/asset": "For using the AssetExtension", + "symfony/expression-language": "For using the ExpressionExtension", + "symfony/finder": "", + "symfony/form": "For using the FormExtension", + "symfony/http-kernel": "For using the HttpKernelExtension", + "symfony/routing": "For using the RoutingExtension", + "symfony/security": "For using the SecurityExtension", + "symfony/stopwatch": "For using the StopwatchExtension", + "symfony/templating": "For using the TwigEngine", + "symfony/translation": "For using the TranslationExtension", + "symfony/var-dumper": "For using the DumpExtension", + "symfony/yaml": "For using the YamlExtension" + }, + "type": "symfony-bridge", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Bridge\\Twig\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony Twig Bridge", + "homepage": "https://symfony.com/", + "time": "2015-10-11 09:39:48" + }, + { + "name": "twig/twig", + "version": "v1.22.3", + "source": { + "type": "git", + "url": "https://github.com/twigphp/Twig.git", + "reference": "ebfc36b7e77b0c1175afe30459cf943010245540" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/twigphp/Twig/zipball/ebfc36b7e77b0c1175afe30459cf943010245540", + "reference": "ebfc36b7e77b0c1175afe30459cf943010245540", + "shasum": "" + }, + "require": { + "php": ">=5.2.7" + }, + "require-dev": { + "symfony/debug": "~2.7", + "symfony/phpunit-bridge": "~2.7" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.22-dev" + } + }, + "autoload": { + "psr-0": { + "Twig_": "lib/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com", + "homepage": "http://fabien.potencier.org/", + "role": "Lead Developer" + }, + { + "name": "Armin Ronacher", + "email": "armin.ronacher@active-4.com", + "role": "Project Founder" + }, + { + "name": "Twig Team", + "homepage": "http://twig.sensiolabs.org/contributors", + "role": "Contributors" + } + ], + "description": "Twig, the flexible, fast, and secure template language for PHP", + "homepage": "http://twig.sensiolabs.org/", + "keywords": [ + "templating" + ], + "time": "2015-10-13 07:07:02" + } + ], + "packages-dev": [ + { + "name": "symfony/browser-kit", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/browser-kit.git", + "reference": "07d664a052572ccc28eb2ab7dbbe82155b1ad367" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/browser-kit/zipball/07d664a052572ccc28eb2ab7dbbe82155b1ad367", + "reference": "07d664a052572ccc28eb2ab7dbbe82155b1ad367", + "shasum": "" + }, + "require": { + "php": ">=5.3.9", + "symfony/dom-crawler": "~2.0,>=2.0.5" + }, + "require-dev": { + "symfony/css-selector": "~2.0,>=2.0.5", + "symfony/process": "~2.3.34|~2.7,>=2.7.6" + }, + "suggest": { + "symfony/process": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\BrowserKit\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony BrowserKit Component", + "homepage": "https://symfony.com/", + "time": "2015-10-23 14:47:27" + }, + { + "name": "symfony/css-selector", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/css-selector.git", + "reference": "e1b865b26be4a56d22a8dee398375044a80c865b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/css-selector/zipball/e1b865b26be4a56d22a8dee398375044a80c865b", + "reference": "e1b865b26be4a56d22a8dee398375044a80c865b", + "shasum": "" + }, + "require": { + "php": ">=5.3.9" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\CssSelector\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jean-François Simon", + "email": "jeanfrancois.simon@sensiolabs.com" + }, + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony CssSelector Component", + "homepage": "https://symfony.com/", + "time": "2015-10-11 09:39:48" + }, + { + "name": "symfony/dom-crawler", + "version": "v2.7.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/dom-crawler.git", + "reference": "5fef7d8b80d8f9992df99d8ee283f420484c9612" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/dom-crawler/zipball/5fef7d8b80d8f9992df99d8ee283f420484c9612", + "reference": "5fef7d8b80d8f9992df99d8ee283f420484c9612", + "shasum": "" + }, + "require": { + "php": ">=5.3.9" + }, + "require-dev": { + "symfony/css-selector": "~2.3" + }, + "suggest": { + "symfony/css-selector": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Component\\DomCrawler\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony DomCrawler Component", + "homepage": "https://symfony.com/", + "time": "2015-10-11 09:39:48" + } + ], + "aliases": [], + "minimum-stability": "stable", + "stability-flags": { + "google/apiclient": 20 + }, + "prefer-stable": false, + "prefer-lowest": false, + "platform": { + "php": ">=5.4" + }, + "platform-dev": [] +} diff --git a/pubsub/config.json b/pubsub/config.json new file mode 100644 index 0000000000..98f9a6df9e --- /dev/null +++ b/pubsub/config.json @@ -0,0 +1,6 @@ +{ + "pubsub-token": "{A_UNIQUE_TOKEN}", + "project": "{YOUR_PROJECT_ID}", + "topic": "topic-pubsub-api-sample-php", + "subscription": "subscription-pubsub-api-sample-php" +} diff --git a/pubsub/php.ini b/pubsub/php.ini new file mode 100644 index 0000000000..4cae2279fa --- /dev/null +++ b/pubsub/php.ini @@ -0,0 +1,2 @@ +google_app_engine.enable_functions = "php_sapi_name, php_uname" +extension = "curl.so" \ No newline at end of file diff --git a/pubsub/src/DatastoreHelper.php b/pubsub/src/DatastoreHelper.php new file mode 100644 index 0000000000..e0f5f24cca --- /dev/null +++ b/pubsub/src/DatastoreHelper.php @@ -0,0 +1,106 @@ +setDirection('descending'); + $property = new \Google_Service_Datastore_PropertyReference(); + $property->setName('created'); + $order->setProperty($property); + $query->setOrder($order); + + $kind = new \Google_Service_Datastore_KindExpression(); + $kind->setName('PubSubMessage'); + $query->setKinds([$kind]); + + $query->setLimit($limit); + + $request->setQuery($query); + + return $request; + } + + /** + * Creates the request to store a PubSubMessage item in datastore + */ + public function createMessageRequest(\Google_Service_Datastore_Key $id, $message) + { + $entity = $this->createEntity($id, $message); + $mutation = new \Google_Service_Datastore_Mutation(); + $mutation->setUpsert([$entity]); + $req = new \Google_Service_Datastore_CommitRequest(); + $req->setMode('NON_TRANSACTIONAL'); + $req->setMutation($mutation); + + return $req; + } + + /** + * Creates the basic entity for PubSubMessage, with properties "created" + * and "message" + */ + public function createEntity(\Google_Service_Datastore_Key $key, $message) + { + $entity = new \Google_Service_Datastore_Entity(); + $entity->setKey($key); + $messageProp = new \Google_Service_Datastore_Property(); + $messageProp->setStringValue($message); + $createdProp = new \Google_Service_Datastore_Property(); + $createdProp->setDateTimeValue(date('c')); + $properties = [ + 'message' => $messageProp, + 'created' => $createdProp, + ]; + + $entity->setProperties($properties); + + return $entity; + } + + /** + * Fetches a unique key from Datastore for a PubSub message + */ + public function createUniqueKeyRequest() + { + // retrieve a unique ID from datastore + $path = new \Google_Service_Datastore_KeyPathElement(); + $path->setKind('PubSubMessage'); + $key = new \Google_Service_Datastore_Key(); + $key->setPath([$path]); + $idRequest = new \Google_Service_Datastore_AllocateIdsRequest(); + $idRequest->setKeys([$key]); + + return $idRequest; + } +} \ No newline at end of file diff --git a/pubsub/src/PubsubHelper.php b/pubsub/src/PubsubHelper.php new file mode 100644 index 0000000000..b39ae82874 --- /dev/null +++ b/pubsub/src/PubsubHelper.php @@ -0,0 +1,104 @@ +projects_topics; + $topics = $service->listProjectsTopics($projectId); + $topic = null; + foreach ($topics->getTopics() as $projectTopic) { + if ($projectTopic->getName() == $topicName) { + $topic = $projectTopic; + break; + } + } + + // create the default topic + if (is_null($topic)) { + $topic = new \Google_Service_Pubsub_Topic(); + $topic->setName($topicName); + $service->create($topicName, $topic); + } + + return true; + } + + /** + * Subscribes this app to the PubSub topic if the topic has no subscribers + */ + public function setupSubscription($projectId, $topicName, $subscriptionName, $token, \Google_Service_Pubsub $pubsub) + { + $fullSubscriptionName = sprintf('projects/%s/subscriptions/%s', $projectId, $subscriptionName); + + try { + // NOTE: if the version changes, the subscription will + // continue to point to the older version, so you'll need to + // delete the subscription in Google Developer Console in + // order for Cloud PubSub to push to newer versions + return $pubsub->projects_subscriptions->get($fullSubscriptionName); + } catch (\Google_Service_Exception $e) { + if ($e->getCode() != 404) { + throw $e; + } + } + + $endpoint = $this->getEndpoint($projectId, $token); + + $subscription = new \Google_Service_Pubsub_Subscription(); + $pushConfig = new \Google_Service_Pubsub_PushConfig(); + $pushConfig->setPushEndpoint($endpoint); + $subscription->setPushConfig($pushConfig); + $subscription->setTopic($topicName); + + return $pubsub->projects_subscriptions->create($fullSubscriptionName, $subscription); + } + + /** + * Returns the Push endpoint for this application to use in the Cloud PubSub + * subscription. The endpoint is created from the AppEngine Version ID and + * the pubsub token. + */ + public function getEndpoint($projectId, $token) + { + $versionSubdomain = ''; + $version = getenv('CURRENT_VERSION_ID'); + + // CURRENT_VERSION_ID in PHP represents major and minor version + if (1 === substr_count($version, '.')) { + list($major, $minor) = explode('.', $version); + $versionSubdomain = $major . '-dot-'; + } + + return sprintf('https://%s%s.appspot.com/receive_message?token=%s', + $versionSubdomain, + $projectId, + $token + ); + } +} \ No newline at end of file diff --git a/pubsub/templates/pubsub.html.twig b/pubsub/templates/pubsub.html.twig new file mode 100644 index 0000000000..deaca50b38 --- /dev/null +++ b/pubsub/templates/pubsub.html.twig @@ -0,0 +1,36 @@ + + +
+ +