From fdd199ed14f43a5c419d66814f148cd9548dd6fe Mon Sep 17 00:00:00 2001 From: Andres Date: Thu, 31 Aug 2017 16:47:32 +0200 Subject: [PATCH 1/2] Allow to use hostname when deploying an http function --- deploy/kubelessDeploy.js | 29 ++-- examples/http-custom-path/README.md | 8 +- examples/todo-app/README.md | 4 - examples/todo-app/backend/README.md | 4 +- examples/todo-app/backend/todos-create.js | 7 +- examples/todo-app/backend/todos-delete.js | 1 - examples/todo-app/backend/todos-read-all.js | 1 - examples/todo-app/backend/todos-read-one.js | 1 - examples/todo-app/backend/todos-update.js | 65 +++++---- .../todo-app/frontend/react-redux/README.md | 4 +- .../react-redux/app/js/actions/index.js | 2 +- .../react-redux/app/js/actions/todos.js | 6 + info/kubelessInfo.js | 2 +- ingress-controller-http-only.yaml | 100 ++++++++++++++ ingress-controller.yaml | 102 ++++++++++++++ test/kubelessDeploy.test.js | 125 +++++++++++++++++- test/kubelessInfo.test.js | 6 +- 17 files changed, 395 insertions(+), 72 deletions(-) create mode 100644 ingress-controller-http-only.yaml create mode 100644 ingress-controller.yaml diff --git a/deploy/kubelessDeploy.js b/deploy/kubelessDeploy.js index 710cdc2..3212c8e 100644 --- a/deploy/kubelessDeploy.js +++ b/deploy/kubelessDeploy.js @@ -24,6 +24,7 @@ const helpers = require('../lib/helpers'); const JSZip = require('jszip'); const moment = require('moment'); const path = require('path'); +const url = require('url'); function getFunctionDescription( funcName, @@ -102,7 +103,7 @@ function getFunctionDescription( return funcs; } -function getIngressDescription(funcName, funcPath) { +function getIngressDescription(funcName, funcPath, funcHost) { return { kind: 'Ingress', metadata: { @@ -115,6 +116,7 @@ function getIngressDescription(funcName, funcPath) { }, spec: { rules: [{ + host: funcHost, http: { paths: [{ path: funcPath, @@ -225,8 +227,7 @@ class KubelessDeploy { const loop = setInterval(() => { if (retries > 3) { this.serverless.cli.log( - `Giving up, the deployment of the function ${funcName} seems to have failed. ` + - 'Check the kubeless-controller pod logs for more info' + `Giving up, unable to retrieve the status of the ${funcName} deployment. ` ); clearInterval(loop); return; @@ -330,17 +331,24 @@ class KubelessDeploy { }); } - addIngressRuleIfNecessary(funcName, eventType, eventPath, namespace) { + addIngressRuleIfNecessary(funcName, eventType, eventPath, eventHostname, namespace) { + const config = helpers.loadKubeConfig(); const extensions = this.getExtensions(helpers.getConnectionOptions( - helpers.loadKubeConfig(), { namespace }) + config, { namespace }) ); + const fpath = eventPath || '/'; + const hostname = eventHostname || + `${url.parse(helpers.getKubernetesAPIURL(config)).hostname}.nip.io`; return new BbPromise((resolve, reject) => { - if (eventType === 'http' && eventPath && eventPath !== '/') { + if ( + eventType === 'http' && + ((!_.isEmpty(eventPath) && eventPath !== '/') || !_.isEmpty(eventHostname)) + ) { // Found a path to deploy the function - const absolutePath = _.startsWith(eventPath, '/') ? - eventPath : - `/${eventPath}`; - const ingressDef = getIngressDescription(funcName, absolutePath); + const absolutePath = _.startsWith(fpath, '/') ? + fpath : + `/${fpath}`; + const ingressDef = getIngressDescription(funcName, absolutePath, hostname); extensions.ns.ingress.post({ body: ingressDef }, (err) => { if (err) { reject( @@ -433,6 +441,7 @@ class KubelessDeploy { name, eventType, event[eventType].path, + this.serverless.service.provider.hostname || event[eventType].hostname, connectionOptions.namespace ); }) diff --git a/examples/http-custom-path/README.md b/examples/http-custom-path/README.md index 9bc54cd..2745c69 100644 --- a/examples/http-custom-path/README.md +++ b/examples/http-custom-path/README.md @@ -7,7 +7,7 @@ In this example we will deploy a function that will be available under the path We will need to have an Ingress controller deployed in order to be able to deploy your function in a specific path. If you don't have it yet you can deploy one executing: ``` -curl -sL https://raw.githubusercontent.com/kubeless/kubeless/0.0.20/manifests/ingress/ingress-controller.yaml | kubectl create -f - +curl -sL https://raw.githubusercontent.com/kubeless/kubeless/master/manifests/ingress/ingress-controller-http-only.yaml | kubectl create -f - ``` ## Deployment @@ -22,7 +22,7 @@ Serverless: Waiting for function hello to be fully deployed. Pods status: {"wait Serverless: Function hello succesfully deployed ``` -As we can see in the logs an Ingress Rule has been deployed to run our function at `/hello`. We can know the specific URL in which the function will be listening executing `serverless info`: +As we can see in the logs an Ingress Rule has been deployed to run our function at `/hello`. If no host is specified, by default it will use `API_URL.nip.io` being `API_URL` the URL/IP of the Kubernetes IP. We can know the specific URL in which the function will be listening executing `serverless info`: ```console $ serverless info Service Information "hello" @@ -34,7 +34,7 @@ Ports: Target Port: 8080 Node Port: 31444 Function Info -URL: 192.168.99.100/hello +URL: 192.168.99.100.nip.io/hello Handler: handler.hello Runtime: python2.7 Trigger: HTTP @@ -43,7 +43,7 @@ Dependencies: Depending on the Ingress configuration the URL may be redirected to use the HTTPS protocol. You can call your function with a browser or executing: ```console -$ curl -kL 192.168.99.100/hello +$ curl 192.168.99.100.nip.io/hello hello world ``` diff --git a/examples/todo-app/README.md b/examples/todo-app/README.md index 599ac92..e76bc4d 100644 --- a/examples/todo-app/README.md +++ b/examples/todo-app/README.md @@ -11,10 +11,6 @@ You'll find two directories here. Deploy them in the following order: 1. The [backend](backend) directory contains the whole Serverless service and it's corresponding function code. 2. The [frontend](frontend) directory contains the frontend you can connect to your backend to use the Todos service through your web browser. -# Known issue - -When deploying this applicaiton with the default ingress controller the web browser may reject the self-signed certificate used. To be able to use the application go to `https://API_URL` (where API_URL is the URL of your cluster) and add the certificate to the white list. - # Source This is a modified version of Philipp Muens Todo example from his serverless [book](https://github.com/pmuens/serverless-book/blob/master/06-serverless-by-example/02-a-serverless-todo-application.md). Modified to run on [Kubeless](https://github.com/kubeless/kubeless) diff --git a/examples/todo-app/backend/README.md b/examples/todo-app/backend/README.md index 102e3a7..f60057d 100644 --- a/examples/todo-app/backend/README.md +++ b/examples/todo-app/backend/README.md @@ -5,14 +5,14 @@ Do the following to deploy and use the backend: 1. Install kubeless following the instruction from the main [README.md](../../../README.md) 2. Install an Ingress Controller in case you still don't have one: ``` -$ curl -sL https://raw.githubusercontent.com/kubeless/kubeless/0.0.20/manifests/ingress/ingress-controller.yaml | kubectl create -f - +$ curl -sL https://raw.githubusercontent.com/kubeless/kubeless/master/manifests/ingress/ingress-controller-http-only.yaml | kubectl create -f - ``` 3. Deploy a MongoDB service. It will be used to store the state of our application: ```console $ curl -sL https://raw.githubusercontent.com/bitnami/bitnami-docker-mongodb/master/kubernetes.yml | kubectl create -f - ``` 4. Run `npm install` to install the used npm packages -3. Run `serverless deploy` to deploy the `todo` service in our kubernetes cluster +5. Run `serverless deploy` to deploy the `todo` service in our kubernetes cluster ```console $ serverless deploy Serverless: Packaging service... diff --git a/examples/todo-app/backend/todos-create.js b/examples/todo-app/backend/todos-create.js index e4ee067..7c283fb 100644 --- a/examples/todo-app/backend/todos-create.js +++ b/examples/todo-app/backend/todos-create.js @@ -8,11 +8,7 @@ const url = 'mongodb://mongodb:27017/todo_app'; module.exports = { create: (req, res) => new Promise((resolve, reject) => { - res.header('Access-Control-Allow-Origin', '*'); - const body = []; - req.on('data', d => body.push(d)); - req.on('end', () => { - const data = JSON.parse(Buffer.concat(body)); + const data = req.body; data.id = uuid.v1(); data.updatedAt = new Date().getTime(); MongoClient.connect(url, (cerr, db) => { @@ -29,7 +25,6 @@ module.exports = { } }); } - }); }); }), }; diff --git a/examples/todo-app/backend/todos-delete.js b/examples/todo-app/backend/todos-delete.js index 915ac1e..2223603 100644 --- a/examples/todo-app/backend/todos-delete.js +++ b/examples/todo-app/backend/todos-delete.js @@ -8,7 +8,6 @@ const url = 'mongodb://mongodb:27017/todo_app'; module.exports = { delete: (req, res) => new Promise((resolve, reject) => { - res.header('Access-Control-Allow-Origin', '*'); MongoClient.connect(url, (err, db) => { if (err) { reject(err); diff --git a/examples/todo-app/backend/todos-read-all.js b/examples/todo-app/backend/todos-read-all.js index aaf24ea..b54789f 100644 --- a/examples/todo-app/backend/todos-read-all.js +++ b/examples/todo-app/backend/todos-read-all.js @@ -8,7 +8,6 @@ const url = 'mongodb://mongodb:27017/todo_app'; module.exports = { readAll: (req, res) => new Promise((resolve, reject) => { - res.header('Access-Control-Allow-Origin', '*'); MongoClient.connect(url, (err, db) => { if (err) { reject(err); diff --git a/examples/todo-app/backend/todos-read-one.js b/examples/todo-app/backend/todos-read-one.js index e11f83d..2244aeb 100644 --- a/examples/todo-app/backend/todos-read-one.js +++ b/examples/todo-app/backend/todos-read-one.js @@ -8,7 +8,6 @@ const url = 'mongodb://mongodb:27017/todo_app'; module.exports = { readOne: (req, res) => new Promise((resolve, reject) => { - res.header('Access-Control-Allow-Origin', '*'); MongoClient.connect(url, (err, db) => { if (err) { reject(err); diff --git a/examples/todo-app/backend/todos-update.js b/examples/todo-app/backend/todos-update.js index 8543f16..3f4a64a 100644 --- a/examples/todo-app/backend/todos-update.js +++ b/examples/todo-app/backend/todos-update.js @@ -9,41 +9,36 @@ const url = 'mongodb://mongodb:27017/todo_app'; module.exports = { update: (req, res) => new Promise((resolve, reject) => { - res.header('Access-Control-Allow-Origin', '*'); - const body = []; - req.on('data', (d) => body.push(d)); - req.on('end', () => { - const data = JSON.parse(Buffer.concat(body)); - MongoClient.connect(url, (err, db) => { - if (err) { - reject(err); - } else { - db.collection('todos', (errC, doc) => { - if (errC) { - reject(errC); - } else { - doc.find().toArray((ferr, docEntries) => { - if (ferr) { - reject(ferr); - } else { - const entry = _.find(docEntries, e => e.id === data.id); - const newEntry = _.cloneDeep(entry); - _.assign(newEntry, data, { id: uuid.v1(), updatedAt: new Date().getTime() }); - doc.updateOne(entry, { $set: newEntry }, (uerr) => { - if (uerr) { - reject(uerr); - } else { - res.end(JSON.stringify(newEntry)); - db.close(); - resolve(); - } - }); - } - }); - } - }); - } - }); + const data = req.body; + MongoClient.connect(url, (err, db) => { + if (err) { + reject(err); + } else { + db.collection('todos', (errC, doc) => { + if (errC) { + reject(errC); + } else { + doc.find().toArray((ferr, docEntries) => { + if (ferr) { + reject(ferr); + } else { + const entry = _.find(docEntries, e => e.id === data.id); + const newEntry = _.cloneDeep(entry); + _.assign(newEntry, data, { id: uuid.v1(), updatedAt: new Date().getTime() }); + doc.updateOne(entry, { $set: newEntry }, (uerr) => { + if (uerr) { + reject(uerr); + } else { + res.end(JSON.stringify(newEntry)); + db.close(); + resolve(); + } + }); + } + }); + } + }); + } }); }), }; diff --git a/examples/todo-app/frontend/react-redux/README.md b/examples/todo-app/frontend/react-redux/README.md index f0966ab..507ca72 100644 --- a/examples/todo-app/frontend/react-redux/README.md +++ b/examples/todo-app/frontend/react-redux/README.md @@ -6,7 +6,7 @@ Do the following to setup and use the frontend 1. Make sure that you've deployed the backend of the `todo` application 2. Run `npm install` to install the used npm packages -3. Go to `app/js/actions/index.js` and update the `API_URL` with the endpoint of your deployed `todo` Serverless service (e.g. `https://192.168.99.100`) - * NOTE: Check the [known issue](../../README.md#known-issue) for web browsers and the self-signed certificate +3. Go to `app/js/actions/index.js` and update the `API_URL` with the endpoint of your deployed `todo` Serverless service (e.g. `http://192.168.99.100.nip.io`) + * Note: You can find the application hostname executing `serverless info` in the backend folder and checking the field `URL` of any function. 4. Run `npm start` 5. Open up a browser on [localhost:8080](http://localhost:8080) and play around with the application diff --git a/examples/todo-app/frontend/react-redux/app/js/actions/index.js b/examples/todo-app/frontend/react-redux/app/js/actions/index.js index 2f23417..02025e3 100644 --- a/examples/todo-app/frontend/react-redux/app/js/actions/index.js +++ b/examples/todo-app/frontend/react-redux/app/js/actions/index.js @@ -1,4 +1,4 @@ -export const API_URL = 'https://backend'; +export const API_URL = 'http://backend'; console.log(process.env); if (!API_URL) { diff --git a/examples/todo-app/frontend/react-redux/app/js/actions/todos.js b/examples/todo-app/frontend/react-redux/app/js/actions/todos.js index 2429854..98a8cf3 100644 --- a/examples/todo-app/frontend/react-redux/app/js/actions/todos.js +++ b/examples/todo-app/frontend/react-redux/app/js/actions/todos.js @@ -13,6 +13,9 @@ import { export function createTodo(todo) { return (dispatch) => fetch(`${API_URL}/create`, { + headers: { + 'Content-Type': 'application/json' + }, method: 'POST', body: JSON.stringify(todo), }) @@ -59,6 +62,9 @@ export function getTodo(todo) { export function updateTodo(todo) { return (dispatch) => fetch(`${API_URL}/update?id=${todo.id}`, { + headers: { + 'Content-Type': 'application/json' + }, method: 'POST', body: JSON.stringify(todo), }) diff --git a/info/kubelessInfo.js b/info/kubelessInfo.js index e994d74..e3786b4 100644 --- a/info/kubelessInfo.js +++ b/info/kubelessInfo.js @@ -148,7 +148,7 @@ class KubelessInfo { )); let url = null; if (fIngress) { - url = `${fIngress.status.loadBalancer.ingress[0].ip || 'API_URL'}` + + url = `${fIngress.spec.rules[0].host || 'API_URL'}` + `${fIngress.spec.rules[0].http.paths[0].path}`; } const service = { diff --git a/ingress-controller-http-only.yaml b/ingress-controller-http-only.yaml new file mode 100644 index 0000000..9b835a8 --- /dev/null +++ b/ingress-controller-http-only.yaml @@ -0,0 +1,100 @@ +# https://github.com/kubernetes/contrib/blob/master/ingress/controllers/nginx/examples/default-backend.yaml +apiVersion: v1 +kind: ReplicationController +metadata: + name: default-http-backend +spec: + replicas: 1 + selector: + app: default-http-backend + template: + metadata: + labels: + app: default-http-backend + spec: + terminationGracePeriodSeconds: 60 + containers: + - name: default-http-backend + # Any image is permissable as long as: + # 1. It serves a 404 page at / + # 2. It serves 200 on a /healthz endpoint + image: gcr.io/google_containers/defaultbackend:1.0 + livenessProbe: + httpGet: + path: /healthz + port: 8080 + scheme: HTTP + initialDelaySeconds: 30 + timeoutSeconds: 5 + ports: + - containerPort: 8080 + resources: + limits: + cpu: 10m + memory: 20Mi + requests: + cpu: 10m + memory: 20Mi +--- +# create a service for the default backend +apiVersion: v1 +kind: Service +metadata: + labels: + app: default-http-backend + name: default-http-backend +spec: + ports: + - port: 80 + protocol: TCP + targetPort: 8080 + selector: + app: default-http-backend + sessionAffinity: None + type: ClusterIP +--- +# Replication controller for the load balancer +apiVersion: v1 +kind: ReplicationController +metadata: + name: nginx-ingress-controller + labels: + k8s-app: nginx-ingress-lb +spec: + replicas: 1 + selector: + k8s-app: nginx-ingress-lb + template: + metadata: + labels: + k8s-app: nginx-ingress-lb + name: nginx-ingress-lb + spec: + terminationGracePeriodSeconds: 60 + containers: + - image: gcr.io/google_containers/nginx-ingress-controller:0.8.2 + name: nginx-ingress-lb + imagePullPolicy: Always + livenessProbe: + httpGet: + path: /healthz + port: 10249 + scheme: HTTP + initialDelaySeconds: 30 + timeoutSeconds: 5 + # use downward API + env: + - name: POD_NAME + valueFrom: + fieldRef: + fieldPath: metadata.name + - name: POD_NAMESPACE + valueFrom: + fieldRef: + fieldPath: metadata.namespace + ports: + - containerPort: 80 + hostPort: 80 + args: + - /nginx-ingress-controller + - --default-backend-service=default/default-http-backend diff --git a/ingress-controller.yaml b/ingress-controller.yaml new file mode 100644 index 0000000..94254ff --- /dev/null +++ b/ingress-controller.yaml @@ -0,0 +1,102 @@ +# https://github.com/kubernetes/contrib/blob/master/ingress/controllers/nginx/examples/default-backend.yaml +apiVersion: v1 +kind: ReplicationController +metadata: + name: default-http-backend +spec: + replicas: 1 + selector: + app: default-http-backend + template: + metadata: + labels: + app: default-http-backend + spec: + terminationGracePeriodSeconds: 60 + containers: + - name: default-http-backend + # Any image is permissable as long as: + # 1. It serves a 404 page at / + # 2. It serves 200 on a /healthz endpoint + image: gcr.io/google_containers/defaultbackend:1.0 + livenessProbe: + httpGet: + path: /healthz + port: 8080 + scheme: HTTP + initialDelaySeconds: 30 + timeoutSeconds: 5 + ports: + - containerPort: 8080 + resources: + limits: + cpu: 10m + memory: 20Mi + requests: + cpu: 10m + memory: 20Mi +--- +# create a service for the default backend +apiVersion: v1 +kind: Service +metadata: + labels: + app: default-http-backend + name: default-http-backend +spec: + ports: + - port: 80 + protocol: TCP + targetPort: 8080 + selector: + app: default-http-backend + sessionAffinity: None + type: ClusterIP +--- +# Replication controller for the load balancer +apiVersion: v1 +kind: ReplicationController +metadata: + name: nginx-ingress-controller + labels: + k8s-app: nginx-ingress-lb +spec: + replicas: 1 + selector: + k8s-app: nginx-ingress-lb + template: + metadata: + labels: + k8s-app: nginx-ingress-lb + name: nginx-ingress-lb + spec: + terminationGracePeriodSeconds: 60 + containers: + - image: gcr.io/google_containers/nginx-ingress-controller:0.8.2 + name: nginx-ingress-lb + imagePullPolicy: Always + livenessProbe: + httpGet: + path: /healthz + port: 10249 + scheme: HTTP + initialDelaySeconds: 30 + timeoutSeconds: 5 + # use downward API + env: + - name: POD_NAME + valueFrom: + fieldRef: + fieldPath: metadata.name + - name: POD_NAMESPACE + valueFrom: + fieldRef: + fieldPath: metadata.namespace + ports: + - containerPort: 80 + hostPort: 80 + - containerPort: 443 + hostPort: 443 + args: + - /nginx-ingress-controller + - --default-backend-service=default/default-http-backend diff --git a/test/kubelessDeploy.test.js b/test/kubelessDeploy.test.js index 919b1d9..bce6b3a 100644 --- a/test/kubelessDeploy.test.js +++ b/test/kubelessDeploy.test.js @@ -408,7 +408,7 @@ describe('KubelessDeploy', () => { kubelessDeploy.waitForDeployment(f, moment()); clock.tick(10001); expect(logStub.lastCall.args[0]).to.contain( - 'the deployment of the function test seems to have failed' + 'unable to retrieve the status of the test deployment' ); } finally { logStub.restore(); @@ -799,6 +799,129 @@ describe('KubelessDeploy', () => { }, spec: { rules: [{ + host: '1.2.3.4.nip.io', + http: { + paths: [{ + path: '/test', + backend: { serviceName: functionName, servicePort: 8080 }, + }], + }, + }], + }, + }); + })).to.be.fulfilled; + return result; + }); + it('should deploy a function with a specific hostname', () => { + const serverlessWithCustomPath = _.cloneDeep(serverlessWithFunction); + serverlessWithCustomPath.service.functions[functionName].events = [{ + http: { }, + }]; + serverlessWithCustomPath.service.provider.hostname = 'test.com'; + kubelessDeploy = instantiateKubelessDeploy( + handlerFile, + depsFile, + serverlessWithCustomPath + ); + thirdPartyResources = mockThirdPartyResources(kubelessDeploy); + const extensions = mockExtensions(kubelessDeploy); + const result = expect( // eslint-disable-line no-unused-expressions + kubelessDeploy.deployFunction().then(() => { + expect(extensions.ns.ingress.post.firstCall.args[0].body).to.be.eql({ + kind: 'Ingress', + metadata: { + name: `ingress-${functionName}`, + labels: { function: functionName }, + annotations: + { + 'kubernetes.io/ingress.class': 'nginx', + 'ingress.kubernetes.io/rewrite-target': '/', + }, + }, + spec: { + rules: [{ + host: 'test.com', + http: { + paths: [{ + path: '/', + backend: { serviceName: functionName, servicePort: 8080 }, + }], + }, + }], + }, + }); + })).to.be.fulfilled; + return result; + }); + + it('should deploy a function with a specific hostname and path', () => { + const serverlessWithCustomPath = _.cloneDeep(serverlessWithFunction); + serverlessWithCustomPath.service.functions[functionName].events = [{ + http: { hostname: 'test.com', path: '/test' }, + }]; + kubelessDeploy = instantiateKubelessDeploy( + handlerFile, + depsFile, + serverlessWithCustomPath + ); + thirdPartyResources = mockThirdPartyResources(kubelessDeploy); + const extensions = mockExtensions(kubelessDeploy); + const result = expect( // eslint-disable-line no-unused-expressions + kubelessDeploy.deployFunction().then(() => { + expect(extensions.ns.ingress.post.firstCall.args[0].body).to.be.eql({ + kind: 'Ingress', + metadata: { + name: `ingress-${functionName}`, + labels: { function: functionName }, + annotations: + { + 'kubernetes.io/ingress.class': 'nginx', + 'ingress.kubernetes.io/rewrite-target': '/', + }, + }, + spec: { + rules: [{ + host: 'test.com', + http: { + paths: [{ + path: '/test', + backend: { serviceName: functionName, servicePort: 8080 }, + }], + }, + }], + }, + }); + })).to.be.fulfilled; + return result; + }); + it('should deploy a function with a specific hostname (in the function section)', () => { + const serverlessWithCustomPath = _.cloneDeep(serverlessWithFunction); + serverlessWithCustomPath.service.functions[functionName].events = [{ + http: { hostname: 'test.com', path: '/test' }, + }]; + kubelessDeploy = instantiateKubelessDeploy( + handlerFile, + depsFile, + serverlessWithCustomPath + ); + thirdPartyResources = mockThirdPartyResources(kubelessDeploy); + const extensions = mockExtensions(kubelessDeploy); + const result = expect( // eslint-disable-line no-unused-expressions + kubelessDeploy.deployFunction().then(() => { + expect(extensions.ns.ingress.post.firstCall.args[0].body).to.be.eql({ + kind: 'Ingress', + metadata: { + name: `ingress-${functionName}`, + labels: { function: functionName }, + annotations: + { + 'kubernetes.io/ingress.class': 'nginx', + 'ingress.kubernetes.io/rewrite-target': '/', + }, + }, + spec: { + rules: [{ + host: 'test.com', http: { paths: [{ path: '/test', diff --git a/test/kubelessInfo.test.js b/test/kubelessInfo.test.js index ca4951b..e08b448 100644 --- a/test/kubelessInfo.test.js +++ b/test/kubelessInfo.test.js @@ -153,7 +153,7 @@ describe('KubelessInfo', () => { }, }, spec: { - rules: [{ http: { paths: [{ path: f.path }] } }], + rules: [{ host: '1.2.3.4.nip.io', http: { paths: [{ path: f.path }] } }], }, status: { loadBalancer: { @@ -323,11 +323,11 @@ describe('KubelessInfo', () => { done(); }); }); - it('should return the trigger topic in case it exists', (done) => { + it('should return the URL in case a path is specified', (done) => { mockGetCalls([{ name: func, namespace: 'default', path: '/hello' }]); const kubelessInfo = new KubelessInfo(serverless, { function: func }); kubelessInfo.infoFunction({ color: false }).then((message) => { - expect(message).to.match(/URL: {2}1.2.3.4\/hello\n/); + expect(message).to.match(/URL: {2}1.2.3.4.nip.io\/hello\n/); done(); }); }); From 444bb7c9efca62f696121c4429fe5977653956f0 Mon Sep 17 00:00:00 2001 From: Andres Date: Fri, 1 Sep 2017 15:38:26 +0200 Subject: [PATCH 2/2] Bump version --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 678beef..98f8555 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "serverless-kubeless", - "version": "0.1.10", + "version": "0.1.11", "description": "This plugin enables support for Kubeless within the [Serverless Framework](https://github.com/serverless).", "main": "index.js", "directories": {