Skip to content

Commit ca98687

Browse files
author
Brad Friedman
committed
Add Java quickstart for Endpoints
1 parent 4a4cd3d commit ca98687

File tree

8 files changed

+431
-0
lines changed

8 files changed

+431
-0
lines changed
Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
# Google Cloud Endpoints
2+
This sample demonstrates how to use Google Cloud Endpoints using Java.
3+
4+
## Deploying to Google App Engine Flexible Environment
5+
6+
### Edit the Swagger API specification
7+
8+
Open the [src/main/appengine/swagger.yaml](src/main/appengine/swagger.yaml) file in your favorite editor, and replace the YOUR-PROJECT-ID `host` line with your actual Google Cloud Platform project Id.
9+
10+
### Running locally
11+
$ mvn jetty:run
12+
13+
### Deploying
14+
$ mvn gcloud:deploy
15+
16+
### Calling your API
17+
18+
Please refer to the Google Cloud Endpoints [documentation](https://cloud.google.com/endpoints/docs/app-engine/) for App Engine Flexible Environment to learn about creating an API Key and calling your API.
19+
20+
## Deploying to Google Container Engine
21+
22+
### Deploy the sample API to the GKE cluster
23+
24+
To deploy to a cluster:
25+
26+
For instructions on how to create a GKE cluster, please refer to the GKE [documentation](https://cloud.google.com/container-engine/docs/quickstart).
27+
28+
1. Edit the Kubernetes configuration file called gke.yaml in this directory, replacing SERVICE_NAME and SERVICE_VERSION shown in the snippet below with the values returned when you deployed the API:
29+
30+
```
31+
containers:
32+
- name: esp
33+
image: b.gcr.io/endpoints/endpoints-runtime:0.3
34+
args: [
35+
"-p", "8080", # the port ESP listens on
36+
"-a", "127.0.0.1:8081", # the backend address
37+
"-s", "SERVICE_NAME",
38+
"-v", "SERVICE_VERSION",
39+
]
40+
```
41+
42+
2. Start the service using the kubectl create command:
43+
44+
```
45+
kubectl create -f gke.yaml
46+
```
47+
48+
3. Get the service's external IP address (it can take a few minutes after you start your service in the container before the external IP address is ready):
49+
50+
```
51+
kubectl get service
52+
```
53+
54+
4. [Create an API key](https://console.cloud.google.com/apis/credentials) in the API credentials page.
55+
* Click Create credentials, then select API key > Server key, then click Create.
56+
* Copy the key, then paste it into the following export statement:
57+
58+
```
59+
export ENDPOINTS_KEY=AIza...
60+
```
61+
62+
5. Test the app by making a call to the EXTERNAL-IP returned in the previous step, at port 8080. For example, this curl will test the app:
63+
64+
```
65+
curl -d '{"message":"hello world"}' -H "content-type:application/json" http://[EXTERNAL-IP]/echo?key=${ENDPOINTS_KEY}
66+
```

endpoints/getting-started/gke.yaml

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
# Copyright 2015 Google Inc. All Rights Reserved.
2+
#
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
apiVersion: v1
16+
kind: Service
17+
metadata:
18+
name: esp-echo
19+
spec:
20+
ports:
21+
- port: 80
22+
targetPort: 8080
23+
protocol: TCP
24+
name: http
25+
selector:
26+
app: esp-echo
27+
type: LoadBalancer
28+
---
29+
apiVersion: extensions/v1beta1
30+
kind: Deployment
31+
metadata:
32+
name: esp-echo
33+
spec:
34+
replicas: 1
35+
template:
36+
metadata:
37+
labels:
38+
app: esp-echo
39+
spec:
40+
containers:
41+
- name: esp
42+
image: b.gcr.io/endpoints/endpoints-runtime:0.3
43+
args: [
44+
"-p", "8080",
45+
"-a", "127.0.0.1:8081",
46+
"-s", "SERVICE_NAME",
47+
"-v", "SERVICE_VERSION",
48+
]
49+
ports:
50+
- containerPort: 8080
51+
- name: echo
52+
image: b.gcr.io/endpoints/echo:latest
53+
ports:
54+
- containerPort: 8081

endpoints/getting-started/pom.xml

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
3+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
4+
5+
<modelVersion>4.0.0</modelVersion>
6+
<packaging>war</packaging>
7+
<version>1.0-SNAPSHOT</version>
8+
<groupId>com.example.managedvms</groupId>
9+
<artifactId>managed-vms-endpoints</artifactId>
10+
11+
<parent>
12+
<artifactId>doc-samples</artifactId>
13+
<groupId>com.google.cloud</groupId>
14+
<version>1.0.0</version>
15+
<relativePath>../..</relativePath>
16+
</parent>
17+
18+
<dependencies>
19+
<dependency>
20+
<groupId>javax.servlet</groupId>
21+
<artifactId>javax.servlet-api</artifactId>
22+
<version>3.1.0</version>
23+
<type>jar</type>
24+
<scope>provided</scope>
25+
</dependency>
26+
<!-- Gson: Java to Json conversion -->
27+
<dependency>
28+
<groupId>com.google.code.gson</groupId>
29+
<artifactId>gson</artifactId>
30+
<version>2.6.2</version>
31+
<scope>compile</scope>
32+
</dependency>
33+
</dependencies>
34+
35+
<build>
36+
<!-- for hot reload of the web application -->
37+
<outputDirectory>${project.build.directory}/${project.build.finalName}/WEB-INF/classes</outputDirectory>
38+
<plugins>
39+
<plugin>
40+
<groupId>com.google.appengine</groupId>
41+
<artifactId>gcloud-maven-plugin</artifactId>
42+
<version>2.0.9.121.v20160815</version>
43+
<configuration>
44+
<gcloud_app_prefix>beta</gcloud_app_prefix>
45+
</configuration>
46+
</plugin>
47+
<plugin>
48+
<groupId>org.apache.maven.plugins</groupId>
49+
<artifactId>maven-war-plugin</artifactId>
50+
<version>2.6</version>
51+
<configuration>
52+
<failOnMissingWebXml>false</failOnMissingWebXml>
53+
</configuration>
54+
</plugin>
55+
<plugin>
56+
<groupId>org.apache.maven.plugins</groupId>
57+
<version>3.3</version>
58+
<artifactId>maven-compiler-plugin</artifactId>
59+
<configuration>
60+
<source>1.7</source>
61+
<target>1.7</target>
62+
</configuration>
63+
</plugin>
64+
<plugin>
65+
<groupId>org.eclipse.jetty</groupId>
66+
<artifactId>jetty-maven-plugin</artifactId>
67+
<version>9.3.8.v20160314</version>
68+
</plugin>
69+
</plugins>
70+
</build>
71+
</project>
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
FROM gcr.io/google_appengine/jetty9
2+
3+
ADD managed-vms-endpoints-1.0-SNAPSHOT.war $JETTY_BASE/webapps/root.war
4+
ADD . /app
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
runtime: custom
2+
vm: true
3+
4+
handlers:
5+
- url: /.*
6+
script: this field is required, but ignored
7+
secure: always
8+
9+
beta_settings:
10+
# Enable Google Cloud Endpoints API management.
11+
use_endpoints_api_management: true
12+
# Specify the Swagger API specification.
13+
endpoints_swagger_spec_file: swagger.yaml
Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
swagger: "2.0"
2+
info:
3+
description: "A simple Google Cloud Endpoints API example."
4+
title: "Endpoints Example"
5+
version: "1.0.0"
6+
host: "YOUR-PROJECT-ID.appspot.com"
7+
basePath: "/"
8+
consumes:
9+
- "application/json"
10+
produces:
11+
- "application/json"
12+
schemes:
13+
- "https"
14+
paths:
15+
"/echo":
16+
post:
17+
description: "Echo back a given message."
18+
operationId: "echo"
19+
produces:
20+
- "application/json"
21+
responses:
22+
200:
23+
description: "Echo"
24+
schema:
25+
$ref: "#/definitions/echoMessage"
26+
parameters:
27+
- description: "Message to echo"
28+
in: body
29+
name: message
30+
required: true
31+
schema:
32+
$ref: "#/definitions/echoMessage"
33+
"/auth/info/googlejwt":
34+
get:
35+
description: "Returns the requests' authentication information."
36+
operationId: "auth_info_google_jwt"
37+
produces:
38+
- "application/json"
39+
responses:
40+
200:
41+
description: "Authenication info."
42+
schema:
43+
$ref: "#/definitions/authInfoResponse"
44+
x-security:
45+
- google_jwt:
46+
audiences:
47+
# This must match the "aud" field in the JWT. You can add multiple
48+
# audiences to accept JWTs from multiple clients.
49+
- "echo.endpoints.sample.google.com"
50+
"/auth/info/googleidtoken":
51+
get:
52+
description: "Returns the requests' authentication information."
53+
operationId: "authInfoGoogleIdToken"
54+
produces:
55+
- "application/json"
56+
responses:
57+
200:
58+
description: "Authenication info."
59+
schema:
60+
$ref: "#/definitions/authInfoResponse"
61+
x-security:
62+
- google_id_token:
63+
audiences:
64+
# Your OAuth2 client's Client ID must be added here. You can add
65+
# multiple client IDs to accept tokens from multiple clients.
66+
- "YOUR-CLIENT-ID"
67+
definitions:
68+
echoMessage:
69+
properties:
70+
message:
71+
type: "string"
72+
authInfoResponse:
73+
properties:
74+
id:
75+
type: "string"
76+
email:
77+
type: "string"
78+
# This section requires all requests to any path to require an API key.
79+
security:
80+
- api_key: []
81+
securityDefinitions:
82+
# This section configures basic authentication with an API key.
83+
api_key:
84+
type: "apiKey"
85+
name: "key"
86+
in: "query"
87+
# This section configures authentication using Google API Service Accounts
88+
# to sign a json web token. This is mostly used for server-to-server
89+
# communication.
90+
google_jwt:
91+
authorizationUrl: ""
92+
flow: "implicit"
93+
type: "oauth2"
94+
# This must match the 'iss' field in the JWT.
95+
x-issuer: "jwt-client.endpoints.sample.google.com"
96+
# Update this with your service account's email address.
97+
x-jwks_uri: "https://www.googleapis.com/service_accounts/v1/jwk/YOUR-SERVICE-ACCOUNT-EMAIL"
98+
# This section configures authentication using Google OAuth2 ID Tokens.
99+
# ID Tokens can be obtained using OAuth2 clients, and can be used to access
100+
# your API on behalf of a particular user.
101+
google_id_token:
102+
authorizationUrl: ""
103+
flow: "implicit"
104+
type: "oauth2"
105+
x-issuer: "accounts.google.com"
106+
x-jwks_uri: "https://www.googleapis.com/oauth2/v1/certs"
Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
/**
2+
* Copyright 2015 Google Inc. All Rights Reserved.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package com.example.managedvms.endpoints;
18+
19+
import java.io.IOException;
20+
import java.io.PrintWriter;
21+
import java.util.Base64;
22+
23+
import javax.servlet.annotation.WebServlet;
24+
import javax.servlet.http.HttpServlet;
25+
import javax.servlet.http.HttpServletRequest;
26+
import javax.servlet.http.HttpServletResponse;
27+
28+
import com.google.gson.Gson;
29+
import com.google.gson.JsonObject;
30+
31+
/**
32+
* A servlet that returns authentication information.
33+
* See swagger.yaml for authentication mechanisms (e.g. JWT tokens, Google ID token).
34+
*/
35+
@WebServlet("/auth/info/*")
36+
public class AuthInfoServlet extends HttpServlet {
37+
38+
@Override
39+
public void doGet(HttpServletRequest req, HttpServletResponse resp) throws IOException {
40+
String encodedInfo = req.getHeader("X-Endpoint-API-UserInfo");
41+
if (encodedInfo == null || encodedInfo == "") {
42+
JsonObject anon = new JsonObject();
43+
anon.addProperty("id", "anonymous");
44+
new Gson().toJson(anon, resp.getWriter());
45+
return;
46+
}
47+
48+
try {
49+
byte[] authInfo = Base64.getDecoder().decode(encodedInfo);
50+
resp.getOutputStream().write(authInfo);
51+
} catch (IllegalArgumentException iae) {
52+
resp.setStatus(HttpServletResponse.SC_BAD_REQUEST);
53+
JsonObject error = new JsonObject();
54+
error.addProperty("code", HttpServletResponse.SC_BAD_REQUEST);
55+
error.addProperty("message", "Could not decode auth info.");
56+
new Gson().toJson(error, resp.getWriter());
57+
}
58+
}
59+
}

0 commit comments

Comments
 (0)