You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@openwhisk.apache.org by mr...@apache.org on 2018/02/28 00:45:09 UTC

[incubator-openwhisk-wskdeploy] branch master updated: Adding support for default package (#754)

This is an automated email from the ASF dual-hosted git repository.

mrutkowski pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/incubator-openwhisk-wskdeploy.git


The following commit(s) were added to refs/heads/master by this push:
     new fb07796  Adding support for default package (#754)
fb07796 is described below

commit fb07796d798d77eb5893b2f0722419a1123ef658
Author: Priti Desai <pd...@us.ibm.com>
AuthorDate: Tue Feb 27 16:45:07 2018 -0800

    Adding support for default package (#754)
    
    * default package support - first draft
    
    * testing default package with api
    
    * adding default to alarm trigger
    
    * adding translable message
    
    * commenting API gateway test
---
 deployers/servicedeployer.go                       |  72 ++++++++------
 parsers/manifest_parser.go                         |  34 +++++--
 tests/src/integration/alarmtrigger/deployment.yaml |  11 +++
 tests/src/integration/alarmtrigger/manifest.yaml   |  24 +++++
 tests/src/integration/common/wskdeploy.go          |   4 +
 .../integration/defaultpackage/actions/hello.js    |  25 +++++
 .../defaultpackage/defaultpackage_test.go          |  47 +++++++++
 .../defaultpackage/manifest-with-project.yaml      | 110 +++++++++++++++++++++
 tests/src/integration/defaultpackage/manifest.yaml | 108 ++++++++++++++++++++
 wski18n/i18n_ids.go                                |   2 +
 wski18n/i18n_resources.go                          |  22 ++---
 wski18n/resources/en_US.all.json                   |   4 +
 12 files changed, 411 insertions(+), 52 deletions(-)

diff --git a/deployers/servicedeployer.go b/deployers/servicedeployer.go
index 579d038..7e96df2 100644
--- a/deployers/servicedeployer.go
+++ b/deployers/servicedeployer.go
@@ -90,11 +90,10 @@ type ServiceDeployer struct {
 	ProjectPath    string
 	DeploymentPath string
 	// whether to deploy the action under the package
-	DeployActionInPackage bool
-	InteractiveChoice     bool
-	ClientConfig          *whisk.Config
-	DependencyMaster      map[string]utils.DependencyRecord
-	ManagedAnnotation     whisk.KeyValue
+	InteractiveChoice bool
+	ClientConfig      *whisk.Config
+	DependencyMaster  map[string]utils.DependencyRecord
+	ManagedAnnotation whisk.KeyValue
 }
 
 // NewServiceDeployer is a Factory to create a new ServiceDeployer
@@ -102,7 +101,6 @@ func NewServiceDeployer() *ServiceDeployer {
 	var dep ServiceDeployer
 	dep.Deployment = NewDeploymentProject()
 	dep.IsInteractive = true
-	dep.DeployActionInPackage = true
 	dep.DependencyMaster = make(map[string]utils.DependencyRecord)
 
 	return &dep
@@ -678,9 +676,16 @@ func (deployer *ServiceDeployer) RefreshManagedPackages(ma map[string]interface{
 
 func (deployer *ServiceDeployer) DeployPackages() error {
 	for _, pack := range deployer.Deployment.Packages {
-		err := deployer.createPackage(pack.Package)
-		if err != nil {
-			return err
+		// "default" package is a reserved package name
+		// all openwhisk entities will be deployed under
+		// /<namespace> instead of /<namespace>/<package> and
+		// therefore skip creating a new package and set
+		// deployer.DeployActionInPackage to false which is set to true by default
+		if strings.ToLower(pack.Package.Name) != parsers.DEFAULT_PACKAGE {
+			err := deployer.createPackage(pack.Package)
+			if err != nil {
+				return err
+			}
 		}
 	}
 	return nil
@@ -892,15 +897,11 @@ func (deployer *ServiceDeployer) createRule(rule *whisk.Rule) error {
 	displayPreprocessingInfo(parsers.YAML_KEY_RULE, rule.Name, true)
 
 	// The rule's trigger should include the namespace with pattern /namespace/trigger
-	rule.Trigger = deployer.getQualifiedName(rule.Trigger.(string), deployer.ClientConfig.Namespace)
-	// The rule's action should include the namespace and package
-	// with pattern /namespace/package/action
-	// TODO(TBD): please refer https://github.com/openwhisk/openwhisk/issues/1577
-
-	// if it contains a slash, then the action is qualified by a package name
-	if strings.Contains(rule.Action.(string), "/") {
-		rule.Action = deployer.getQualifiedName(rule.Action.(string), deployer.ClientConfig.Namespace)
-	}
+	rule.Trigger = deployer.getQualifiedName(rule.Trigger.(string))
+	// The rule's action should include the namespace and package with pattern
+	// /namespace/package/action if that action was created under a package
+	// otherwise action should include the namespace with pattern /namespace/action
+	rule.Action = deployer.getQualifiedName(rule.Action.(string))
 
 	var err error
 	var response *http.Response
@@ -920,7 +921,7 @@ func (deployer *ServiceDeployer) createRule(rule *whisk.Rule) error {
 // Utility function to call go-whisk framework to make action
 func (deployer *ServiceDeployer) createAction(pkgname string, action *whisk.Action) error {
 	// call ActionService through the Client
-	if deployer.DeployActionInPackage {
+	if strings.ToLower(pkgname) != parsers.DEFAULT_PACKAGE {
 		// the action will be created under package with pattern 'packagename/actionname'
 		action.Name = strings.Join([]string{pkgname, action.Name}, "/")
 	}
@@ -1111,9 +1112,15 @@ func (deployer *ServiceDeployer) UnDeployDependencies() error {
 
 func (deployer *ServiceDeployer) UnDeployPackages(deployment *DeploymentProject) error {
 	for _, pack := range deployment.Packages {
-		err := deployer.deletePackage(pack.Package)
-		if err != nil {
-			return err
+		// "default" package is a reserved package name
+		// all openwhisk entities were deployed under
+		// /<namespace> instead of /<namespace>/<package> and
+		// therefore skip deleting default package during undeployment
+		if strings.ToLower(pack.Package.Name) != parsers.DEFAULT_PACKAGE {
+			err := deployer.deletePackage(pack.Package)
+			if err != nil {
+				return err
+			}
 		}
 	}
 	return nil
@@ -1350,10 +1357,10 @@ func (deployer *ServiceDeployer) deleteApi(api *whisk.ApiCreateRequest) error {
 	return nil
 }
 
-// Utility function to call go-whisk framework to make action
+// Utility function to call go-whisk framework to delete action
 func (deployer *ServiceDeployer) deleteAction(pkgname string, action *whisk.Action) error {
 	// call ActionService through Client
-	if deployer.DeployActionInPackage {
+	if pkgname != parsers.DEFAULT_PACKAGE {
 		// the action will be deleted under package with pattern 'packagename/actionname'
 		action.Name = strings.Join([]string{pkgname, action.Name}, "/")
 	}
@@ -1403,18 +1410,21 @@ func retry(attempts int, sleep time.Duration, callback func() error) error {
 	return err
 }
 
-// from whisk go client
-func (deployer *ServiceDeployer) getQualifiedName(name string, namespace string) string {
+//  getQualifiedName(name) returns a fully qualified name given a
+//      (possibly fully qualified) resource name.
+//
+//  Examples:
+//      (foo) => /ns/foo
+//      (pkg/foo) => /ns/pkg/foo
+//      (/ns/pkg/foo) => /ns/pkg/foo
+func (deployer *ServiceDeployer) getQualifiedName(name string) string {
+	namespace := deployer.ClientConfig.Namespace
 	if strings.HasPrefix(name, "/") {
 		return name
 	} else if strings.HasPrefix(namespace, "/") {
 		return fmt.Sprintf("%s/%s", namespace, name)
-	} else {
-		if len(namespace) == 0 {
-			namespace = deployer.ClientConfig.Namespace
-		}
-		return fmt.Sprintf("/%s/%s", namespace, name)
 	}
+	return fmt.Sprintf("/%s/%s", namespace, name)
 }
 
 func (deployer *ServiceDeployer) printDeploymentAssets(assets *DeploymentProject) {
diff --git a/parsers/manifest_parser.go b/parsers/manifest_parser.go
index ab7a3c2..56b500c 100644
--- a/parsers/manifest_parser.go
+++ b/parsers/manifest_parser.go
@@ -35,12 +35,13 @@ import (
 )
 
 const (
-	PATH_SEPERATOR = "/"
-	API            = "API"
-	HTTPS          = "https"
-	HTTP           = "http"
-	API_VERSION    = "v1"
-	WEB            = "web"
+	PATH_SEPERATOR  = "/"
+	API             = "API"
+	HTTPS           = "https"
+	HTTP            = "http"
+	API_VERSION     = "v1"
+	WEB             = "web"
+	DEFAULT_PACKAGE = "default"
 )
 
 // Read existing manifest file or create new if none exists
@@ -322,6 +323,13 @@ func (dm *YAMLParser) ComposePackage(pkg Package, packageName string, filePath s
 		pag.Annotations = append(pag.Annotations, ma)
 	}
 
+	// "default" package is a reserved package name
+	// and in this case wskdeploy deploys openwhisk entities under
+	// /namespace instead of /namespace/package
+	if strings.ToLower(pag.Name) == DEFAULT_PACKAGE {
+		wskprint.PrintlnOpenWhiskInfo(wski18n.T(wski18n.ID_MSG_DEFAULT_PACKAGE))
+	}
+
 	return pag, nil
 }
 
@@ -359,7 +367,8 @@ func (dm *YAMLParser) ComposeSequences(namespace string, sequences map[string]Se
 		var components []string
 		for _, a := range actionList {
 			act := strings.TrimSpace(a)
-			if !strings.ContainsRune(act, '/') && !strings.HasPrefix(act, packageName+"/") {
+			if !strings.ContainsRune(act, '/') && !strings.HasPrefix(act, packageName+"/") &&
+				strings.ToLower(packageName) != DEFAULT_PACKAGE {
 				act = path.Join(packageName, act)
 			}
 			components = append(components, path.Join("/"+namespace, act))
@@ -849,7 +858,8 @@ func (dm *YAMLParser) ComposeRules(pkg Package, packageName string, ma whisk.Key
 		wskrule.Trigger = wskenv.ConvertSingleName(rule.Trigger)
 		wskrule.Action = wskenv.ConvertSingleName(rule.Action)
 		act := strings.TrimSpace(wskrule.Action.(string))
-		if !strings.ContainsRune(act, '/') && !strings.HasPrefix(act, packageName+"/") {
+		if !strings.ContainsRune(act, '/') && !strings.HasPrefix(act, packageName+"/") &&
+			strings.ToLower(packageName) != DEFAULT_PACKAGE {
 			act = path.Join(packageName, act)
 		}
 		wskrule.Action = act
@@ -981,10 +991,14 @@ func (dm *YAMLParser) ComposeApiRecords(client *whisk.Config, packageName string
 							request.ApiDoc.Id = strings.Join([]string{API, request.ApiDoc.Namespace, request.ApiDoc.GatewayRelPath}, ":")
 							// set action of an API Doc
 							request.ApiDoc.Action = new(whisk.ApiAction)
-							request.ApiDoc.Action.Name = packageName + PATH_SEPERATOR + actionName
-							request.ApiDoc.Action.Namespace = client.Namespace
+							if packageName == DEFAULT_PACKAGE {
+								request.ApiDoc.Action.Name = actionName
+							} else {
+								request.ApiDoc.Action.Name = packageName + PATH_SEPERATOR + actionName
+							}
 							url := []string{HTTPS + ":" + PATH_SEPERATOR, client.Host, strings.ToLower(API),
 								API_VERSION, WEB, client.Namespace, packageName, actionName + "." + HTTP}
+							request.ApiDoc.Action.Namespace = client.Namespace
 							request.ApiDoc.Action.BackendUrl = strings.Join(url, PATH_SEPERATOR)
 							request.ApiDoc.Action.BackendMethod = gatewayMethod
 							request.ApiDoc.Action.Auth = client.AuthToken
diff --git a/tests/src/integration/alarmtrigger/deployment.yaml b/tests/src/integration/alarmtrigger/deployment.yaml
index c7dc5eb..9fa9623 100644
--- a/tests/src/integration/alarmtrigger/deployment.yaml
+++ b/tests/src/integration/alarmtrigger/deployment.yaml
@@ -27,3 +27,14 @@ project:
                 Every12Hours:
                     inputs:
                         cron: "0 */12 * * *"
+        default:
+            actions:
+                helloworldInDefault:
+                    inputs:
+                        name: Bob
+                        place: London
+            triggers:
+                Every12HoursInDefault:
+                    inputs:
+                        cron: "0 */12 * * *"
+
diff --git a/tests/src/integration/alarmtrigger/manifest.yaml b/tests/src/integration/alarmtrigger/manifest.yaml
index 6055d78..de99908 100644
--- a/tests/src/integration/alarmtrigger/manifest.yaml
+++ b/tests/src/integration/alarmtrigger/manifest.yaml
@@ -38,3 +38,27 @@ packages:
             helloworldEvery12Hours:
                 action: helloworld
                 trigger: Every12Hours
+    default:
+        actions:
+            helloworldInDefault:
+                function: actions/hello.js
+                runtime: nodejs:6
+                inputs:
+                    name:
+                        type: string
+                        description: name of a person
+                    place:
+                        type: string
+                        description: location of a person
+                outputs:
+                    payload:
+                        type: string
+                        description: a simple greeting message, Hello World!
+        triggers:
+            Every12HoursInDefault:
+                feed: /whisk.system/alarms/alarm
+        rules:
+            helloworldEvery12HoursInDefault:
+                action: helloworldInDefault
+                trigger: Every12HoursInDefault
+
diff --git a/tests/src/integration/common/wskdeploy.go b/tests/src/integration/common/wskdeploy.go
index e8d943b..caddc99 100644
--- a/tests/src/integration/common/wskdeploy.go
+++ b/tests/src/integration/common/wskdeploy.go
@@ -170,6 +170,10 @@ func (Wskdeploy *Wskdeploy) ManagedDeployment(manifestPath string, deploymentPat
 	return Wskdeploy.RunCommand("-m", manifestPath, "-d", deploymentPath, "--managed")
 }
 
+func (Wskdeploy *Wskdeploy) ManagedUndeployment(manifestPath string, deploymentPath string) (string, error) {
+	return Wskdeploy.RunCommand("undeploy", "-m", manifestPath, "-d", deploymentPath, "--managed")
+}
+
 // This method is only for testing
 // This method will mock a construction of deployment plan, creating all the memory objects
 // This method CANNOT be used for real deployment!
diff --git a/tests/src/integration/defaultpackage/actions/hello.js b/tests/src/integration/defaultpackage/actions/hello.js
new file mode 100644
index 0000000..b1357b3
--- /dev/null
+++ b/tests/src/integration/defaultpackage/actions/hello.js
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/*
+ * Return a simple greeting message for the whole world.
+ */
+function main(params) {
+    msg = "Hello, " + params.name + " from " + params.place;
+    console.log(msg)
+    return { payload:  msg };
+}
diff --git a/tests/src/integration/defaultpackage/defaultpackage_test.go b/tests/src/integration/defaultpackage/defaultpackage_test.go
new file mode 100644
index 0000000..12e9c64
--- /dev/null
+++ b/tests/src/integration/defaultpackage/defaultpackage_test.go
@@ -0,0 +1,47 @@
+// +build integration
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package tests
+
+import (
+	"github.com/apache/incubator-openwhisk-wskdeploy/tests/src/integration/common"
+	"github.com/stretchr/testify/assert"
+	"os"
+	"testing"
+	"time"
+)
+
+func TestDefaultPackage(t *testing.T) {
+	path := "/src/github.com/apache/incubator-openwhisk-wskdeploy/tests/src/integration/defaultpackage/"
+	manifestPath := os.Getenv("GOPATH") + path + "manifest.yaml"
+	wskdeploy := common.NewWskdeploy()
+	_, err := wskdeploy.DeployManifestPathOnly(manifestPath)
+	assert.Equal(t, nil, err, "Failed to deploy based on the manifest file.")
+	_, err = wskdeploy.UndeployManifestPathOnly(manifestPath)
+	assert.Equal(t, nil, err, "Failed to undeploy based on the manifest file.")
+
+	time.Sleep(10 * time.Second)
+
+	manifestPath = os.Getenv("GOPATH") + path + "manifest-with-project.yaml"
+	_, err = wskdeploy.DeployManifestPathOnly(manifestPath)
+	assert.Equal(t, nil, err, "Failed to deploy based on the manifest file.")
+	_, err = wskdeploy.UndeployManifestPathOnly(manifestPath)
+	assert.Equal(t, nil, err, "Failed to undeploy based on the manifest file.")
+
+}
diff --git a/tests/src/integration/defaultpackage/manifest-with-project.yaml b/tests/src/integration/defaultpackage/manifest-with-project.yaml
new file mode 100644
index 0000000..536a1c8
--- /dev/null
+++ b/tests/src/integration/defaultpackage/manifest-with-project.yaml
@@ -0,0 +1,110 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more contributor
+# license agreements.  See the NOTICE file distributed with this work for additional
+# information regarding copyright ownership.  The ASF licenses this file to you
+# under the Apache License, Version 2.0 (the # "License"); you may not use this
+# file except in compliance with the License.  You may obtain a copy of the License
+# at:
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software distributed
+# under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+# CONDITIONS OF ANY KIND, either express or implied.  See the License for the
+# specific language governing permissions and limitations under the License.
+#
+
+project:
+    name: ProjectUnderDefaultPackage
+    packages:
+        default:
+            actions:
+                helloInDefaultPackage:
+                    function: actions/hello.js
+                    runtime: nodejs:6
+                    web-export: true
+                    inputs:
+                        name:
+                            type: string
+                            description: name of a person
+                        place:
+                            type: string
+                            description: location of a person
+                    outputs:
+                        payload:
+                            type: string
+                            description: a simple greeting message, Hello World!
+                greetingInDefaultPackage:
+                    function: actions/hello.js
+                    runtime: nodejs:6
+                    inputs:
+                        name:
+                            type: string
+                            description: name of a person
+                        place:
+                            type: string
+                            description: location of a person
+                    outputs:
+                        payload:
+                            type: string
+                            description: a simple greeting message, Hello World!
+            sequences:
+                hello-world-series:
+                    actions: helloInDefaultPackage, greetingInDefaultPackage
+            triggers:
+                triggerInDefaultPackage:
+            rules:
+                ruleInDefaultPackage:
+                    trigger: triggerInDefaultPackage
+                    action: hello-world-series
+#            apis:
+#                hello-world:
+#                    hello:
+#                        world:
+#                            helloInDefaultPackage: GET
+        package-with-default:
+            actions:
+                helloInsidePackage:
+                    function: actions/hello.js
+                    runtime: nodejs:6
+                    inputs:
+                        name:
+                            type: string
+                            description: name of a person
+                        place:
+                            type: string
+                            description: location of a person
+                    outputs:
+                        payload:
+                            type: string
+                            description: a simple greeting message, Hello World!
+                greetingInsidePackage:
+                    function: actions/hello.js
+                    runtime: nodejs:6
+                    web-export: true
+                    inputs:
+                        name:
+                            type: string
+                            description: name of a person
+                        place:
+                            type: string
+                            description: location of a person
+                    outputs:
+                        payload:
+                            type: string
+                            description: a simple greeting message, Hello World!
+            sequences:
+                hello-world-series:
+                    actions: helloInsidePackage, greetingInsidePackage
+            triggers:
+                triggerInsidePackage:
+            rules:
+                ruleInsidePackage:
+                    trigger: triggerInsidePackage
+                    action: hello-world-series
+#            apis:
+#                greeting-world:
+#                    greeting:
+#                        world:
+#                            greetingInsidePackage: GET
+
diff --git a/tests/src/integration/defaultpackage/manifest.yaml b/tests/src/integration/defaultpackage/manifest.yaml
new file mode 100644
index 0000000..6b57459
--- /dev/null
+++ b/tests/src/integration/defaultpackage/manifest.yaml
@@ -0,0 +1,108 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more contributor
+# license agreements.  See the NOTICE file distributed with this work for additional
+# information regarding copyright ownership.  The ASF licenses this file to you
+# under the Apache License, Version 2.0 (the # "License"); you may not use this
+# file except in compliance with the License.  You may obtain a copy of the License
+# at:
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software distributed
+# under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+# CONDITIONS OF ANY KIND, either express or implied.  See the License for the
+# specific language governing permissions and limitations under the License.
+#
+
+packages:
+    default:
+        actions:
+            helloInDefaultPackage:
+                function: actions/hello.js
+                runtime: nodejs:6
+                web-export: true
+                inputs:
+                    name:
+                        type: string
+                        description: name of a person
+                    place:
+                        type: string
+                        description: location of a person
+                outputs:
+                    payload:
+                        type: string
+                        description: a simple greeting message, Hello World!
+            greetingInDefaultPackage:
+                function: actions/hello.js
+                runtime: nodejs:6
+                inputs:
+                    name:
+                        type: string
+                        description: name of a person
+                    place:
+                        type: string
+                        description: location of a person
+                outputs:
+                    payload:
+                        type: string
+                        description: a simple greeting message, Hello World!
+        sequences:
+            hello-world-series:
+                actions: helloInDefaultPackage, greetingInDefaultPackage
+        triggers:
+            triggerInDefaultPackage:
+        rules:
+            ruleInDefaultPackage:
+                trigger: triggerInDefaultPackage
+                action: hello-world-series
+#        apis:
+#            hello-world:
+#                hello:
+#                    world:
+#                        helloInDefaultPackage: GET
+    package-with-default:
+        actions:
+            helloInsidePackage:
+                function: actions/hello.js
+                runtime: nodejs:6
+                inputs:
+                    name:
+                        type: string
+                        description: name of a person
+                    place:
+                        type: string
+                        description: location of a person
+                outputs:
+                    payload:
+                        type: string
+                        description: a simple greeting message, Hello World!
+            greetingInsidePackage:
+                function: actions/hello.js
+                runtime: nodejs:6
+                web-export: true
+                inputs:
+                    name:
+                        type: string
+                        description: name of a person
+                    place:
+                        type: string
+                        description: location of a person
+                outputs:
+                    payload:
+                        type: string
+                        description: a simple greeting message, Hello World!
+        sequences:
+            hello-world-series:
+                actions: helloInsidePackage, greetingInsidePackage
+        triggers:
+            triggerInsidePackage:
+        rules:
+            ruleInsidePackage:
+                trigger: triggerInsidePackage
+                action: hello-world-series
+#        apis:
+#            greeting-world:
+#                greeting:
+#                    world:
+#                        greetingInsidePackage: GET
+
diff --git a/wski18n/i18n_ids.go b/wski18n/i18n_ids.go
index 7b4fc8b..564ef27 100644
--- a/wski18n/i18n_ids.go
+++ b/wski18n/i18n_ids.go
@@ -128,6 +128,8 @@ const (
 	ID_MSG_DEPENDENCY_UNDEPLOYMENT_FAILURE_X_name_X = "msg_dependency_undeployment_failure"
 	ID_MSG_DEPENDENCY_UNDEPLOYMENT_SUCCESS_X_name_X = "msg_dependency_undeployment_success"
 
+	ID_MSG_DEFAULT_PACKAGE = "msg_default_package"
+
 	// Managed deployments
 	ID_MSG_MANAGED_UNDEPLOYMENT_FAILED                    = "msg_managed_undeployment_failed"
 	ID_MSG_MANAGED_FOUND_DELETED_X_key_X_name_X_project_X = "msg_managed_found_deleted_entity"
diff --git a/wski18n/i18n_resources.go b/wski18n/i18n_resources.go
index d7bd32d..9d3620d 100644
--- a/wski18n/i18n_resources.go
+++ b/wski18n/i18n_resources.go
@@ -92,12 +92,12 @@ func wski18nResourcesDe_deAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/de_DE.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/de_DE.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
 
-var _wski18nResourcesEn_usAllJson = []byte("\x1f\x8b\x08\x00\x00\x00\x00\x00\x00\xff\xc4\x5a\x7b\x8f\x1b\xb7\x11\xff\xdf\x9f\x62\x60\x14\x70\x02\x9c\x65\x27\x45\x81\xc2\xc0\xa1\x70\x6b\x37\xb9\x26\xf6\x19\xf7\x48\x10\x38\x87\x35\xb5\x1c\x49\x8c\xb8\xe4\x82\xe4\x4a\x56\x0e\xea\x67\x2f\x86\x5c\xae\x56\xba\xe3\x2e\x25\x27\x68\xfe\x89\x7c\x1c\xce\x6f\x1e\xe4\xbc\xb8\x1f\x9f\x00\xdc\x3f\x01\x00\x78\x2a\xf8\xd3\x57\xf0\xb4\xb2\xf3\xa2\x36\x38\x13\x9f\x0b\x34\x46\x9b\xa7\x67\x61\xd5\x19\xa6\xac [...]
+var _wski18nResourcesEn_usAllJson = []byte("\x1f\x8b\x08\x00\x00\x00\x00\x00\x00\xff\xc4\x1a\x6b\x8f\x1b\xb7\xf1\xbb\x7f\xc5\xc0\x28\xe0\x04\x38\xcb\x4e\x8a\x02\x85\x81\x43\xe1\xd6\x6e\x72\x4d\xec\x33\xee\xec\x04\x81\x73\x58\x53\xcb\x91\xc4\x68\x97\x5c\x90\xdc\x93\x95\x83\xfa\xdb\x8b\xe1\x63\x77\xa5\x3b\xee\x52\x72\x82\xe6\x4b\xe4\xe3\x70\xde\x9c\xe7\x7e\x7c\x04\x70\xf7\x08\x00\xe0\xb1\xe0\x8f\x5f\xc0\xe3\xda\x2c\x8b\x46\xe3\x42\x7c\x2e\x50\x6b\xa5\x1f\x9f\xf9\x53\xab\x99\x34\x15\xb3\x42 [...]
 
 func wski18nResourcesEn_usAllJsonBytes() ([]byte, error) {
 	return bindataRead(
@@ -112,7 +112,7 @@ func wski18nResourcesEn_usAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/en_US.all.json", size: 12953, mode: os.FileMode(420), modTime: time.Unix(1519054009, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/en_US.all.json", size: 13150, mode: os.FileMode(420), modTime: time.Unix(1519437986, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -132,7 +132,7 @@ func wski18nResourcesEs_esAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/es_ES.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/es_ES.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -152,7 +152,7 @@ func wski18nResourcesFr_frAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/fr_FR.all.json", size: 101, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/fr_FR.all.json", size: 101, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -172,7 +172,7 @@ func wski18nResourcesIt_itAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/it_IT.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/it_IT.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -192,7 +192,7 @@ func wski18nResourcesJa_jaAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/ja_JA.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/ja_JA.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -212,7 +212,7 @@ func wski18nResourcesKo_krAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/ko_KR.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/ko_KR.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -232,7 +232,7 @@ func wski18nResourcesPt_brAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/pt_BR.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/pt_BR.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -252,7 +252,7 @@ func wski18nResourcesZh_hansAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/zh_Hans.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/zh_Hans.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
@@ -272,7 +272,7 @@ func wski18nResourcesZh_hantAllJson() (*asset, error) {
 		return nil, err
 	}
 
-	info := bindataFileInfo{name: "wski18n/resources/zh_Hant.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1515697090, 0)}
+	info := bindataFileInfo{name: "wski18n/resources/zh_Hant.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1518211603, 0)}
 	a := &asset{bytes: bytes, info: info}
 	return a, nil
 }
diff --git a/wski18n/resources/en_US.all.json b/wski18n/resources/en_US.all.json
index f9681e4..b98062a 100644
--- a/wski18n/resources/en_US.all.json
+++ b/wski18n/resources/en_US.all.json
@@ -256,6 +256,10 @@
     "translation": "Do you really want to undeploy this? (y/N): "
   },
   {
+    "id": "msg_default_package",
+    "translation": "Package name default is reserved, all OpenWhisk entities under default package are deployed/undeployed directly under your namespace."
+  },
+  {
     "id": "ERRORS",
     "translation": "================= ERRORS ==================="
   },

-- 
To stop receiving notification emails like this one, please contact
mrutkowski@apache.org.