From 3092f1f2d7d591cbdc953876dca0cfaccb75e493 Mon Sep 17 00:00:00 2001 From: Priti Desai Date: Tue, 16 Oct 2018 14:33:53 -0700 Subject: [PATCH] Introducing include and exclude in zip action (#991) * adding include in yaml parser * wip include * wip * wip - dir level include * wip - dir level include * wip - dir level include * wip * wip * wip * wip * wip * wip * wip * wip * wip * include * deleting debugging statement * cleaning up * adding unit test * adding unit test * wip * refactoring * wip * wip * wip * wip * adding more unit tests * fixing unit test * fixing unit test * fixing unit test * adding exclude * fixing unit test * adding warning * adding exclude * refactoring exclude code * adding exclude test case * exclude integration test * cleaning up * adding wski18 strings --- parsers/manifest_parser.go | 2 +- parsers/yamlparser.go | 4 +- tests/dat/manifest_validate_inputs.yaml | 13 + .../actions/common/utils.js | 9 + .../actions/greeting/index.js | 21 + .../actions/greeting/package.json | 6 + .../zipactionwithexclude/actions/index.js | 21 + .../actions/libs/lib1/utils.js | 9 + .../actions/libs/lib2/utils.js | 9 + .../actions/libs/lib3/utils.js | 9 + .../zipactionwithexclude/actions/package.json | 6 + .../zipactionwithexclude/manifest.yml | 18 + .../zipactionwithexclude_test.go | 40 ++ .../actions/common/utils.js | 9 + .../actions/greeting1/index.js | 21 + .../actions/greeting1/package.json | 6 + .../actions/greeting10/index.js | 23 ++ .../actions/greeting10/package.json | 6 + .../actions/greeting2/index.js | 23 ++ .../actions/greeting2/package.json | 6 + .../actions/greeting3/index.js | 22 ++ .../actions/greeting3/package.json | 6 + .../actions/greeting4/index.js | 21 + .../actions/greeting4/package.json | 6 + .../actions/greeting5/index.js | 21 + .../actions/greeting5/package.json | 6 + .../actions/greeting6/index.js | 21 + .../actions/greeting6/package.json | 6 + .../actions/greeting7/index.js | 23 ++ .../actions/greeting7/package.json | 6 + .../actions/greeting8/index.js | 23 ++ .../actions/greeting8/package.json | 6 + .../actions/greeting9/index.js | 23 ++ .../actions/greeting9/package.json | 6 + .../actions/libs/lib1/utils.js | 9 + .../actions/libs/lib2/utils.js | 9 + .../actions/libs/lib3/utils.js | 9 + .../zipactionwithinclude/deployment.yml | 28 ++ .../zipactionwithinclude/manifest.yml | 63 +++ .../zipactionwithinclude_test.go | 40 ++ utils/file.go | 152 ++++++++ utils/file_test.go | 85 ++++ utils/misc.go | 59 --- utils/misc_test.go | 2 +- utils/zip.go | 363 ++++++++++++++++++ wski18n/i18n_ids.go | 18 +- wski18n/i18n_resources.go | 56 +-- wski18n/resources/en_US.all.json | 28 ++ 48 files changed, 1283 insertions(+), 95 deletions(-) create mode 100644 tests/dat/manifest_validate_inputs.yaml create mode 100644 tests/src/integration/zipactionwithexclude/actions/common/utils.js create mode 100644 tests/src/integration/zipactionwithexclude/actions/greeting/index.js create mode 100644 tests/src/integration/zipactionwithexclude/actions/greeting/package.json create mode 100644 tests/src/integration/zipactionwithexclude/actions/index.js create mode 100644 tests/src/integration/zipactionwithexclude/actions/libs/lib1/utils.js create mode 100644 tests/src/integration/zipactionwithexclude/actions/libs/lib2/utils.js create mode 100644 tests/src/integration/zipactionwithexclude/actions/libs/lib3/utils.js create mode 100644 tests/src/integration/zipactionwithexclude/actions/package.json create mode 100644 tests/src/integration/zipactionwithexclude/manifest.yml create mode 100644 tests/src/integration/zipactionwithexclude/zipactionwithexclude_test.go create mode 100644 tests/src/integration/zipactionwithinclude/actions/common/utils.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting1/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting1/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting10/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting10/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting2/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting2/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting3/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting3/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting4/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting4/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting5/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting5/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting6/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting6/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting7/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting7/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting8/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting8/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting9/index.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/greeting9/package.json create mode 100644 tests/src/integration/zipactionwithinclude/actions/libs/lib1/utils.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/libs/lib2/utils.js create mode 100644 tests/src/integration/zipactionwithinclude/actions/libs/lib3/utils.js create mode 100644 tests/src/integration/zipactionwithinclude/deployment.yml create mode 100644 tests/src/integration/zipactionwithinclude/manifest.yml create mode 100644 tests/src/integration/zipactionwithinclude/zipactionwithinclude_test.go create mode 100644 utils/file.go create mode 100644 utils/file_test.go create mode 100644 utils/zip.go diff --git a/parsers/manifest_parser.go b/parsers/manifest_parser.go index ff2124bf9..619cf911d 100644 --- a/parsers/manifest_parser.go +++ b/parsers/manifest_parser.go @@ -649,7 +649,7 @@ func (dm *YAMLParser) readActionFunction(manifestFilePath string, manifestFileNa if utils.IsDirectory(actionFilePath) { zipFileName = actionFilePath + "." + runtimes.ZIP_FILE_EXTENSION - err := utils.NewZipWritter(actionFilePath, zipFileName).Zip() + err := utils.NewZipWritter(actionFilePath, zipFileName, action.Include, action.Exclude, filepath.Dir(manifestFilePath)).Zip() if err != nil { return actionFilePath, nil, err } diff --git a/parsers/yamlparser.go b/parsers/yamlparser.go index 5f12370a9..4776e6ef7 100644 --- a/parsers/yamlparser.go +++ b/parsers/yamlparser.go @@ -114,8 +114,8 @@ type Action struct { Inputs map[string]Parameter `yaml:"inputs"` Outputs map[string]Parameter `yaml:"outputs"` Annotations map[string]interface{} `yaml:"annotations,omitempty"` - // TODO() this is propoagated from package to every action within that package - //Parameters map[string]interface{} `yaml:parameters` + Include [][]string `yaml:"include,omitempty"` + Exclude []string `yaml:"exclude,omitempty"` } type Limits struct { diff --git a/tests/dat/manifest_validate_inputs.yaml b/tests/dat/manifest_validate_inputs.yaml new file mode 100644 index 000000000..4c721c820 --- /dev/null +++ b/tests/dat/manifest_validate_inputs.yaml @@ -0,0 +1,13 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more contributor +# license agreements; and to You under the Apache License, Version 2.0. + +packages: + helloworld: + actions: + helloNodejs: + function: actions/ + runtime: nodejs:6 + include: + - ["actions/hello.js"] + - ["actions/hello.js", "actions/hello.js"] + - ["actions/hello.js", "actions/hello.js", "actions/hello.js"] diff --git a/tests/src/integration/zipactionwithexclude/actions/common/utils.js b/tests/src/integration/zipactionwithexclude/actions/common/utils.js new file mode 100644 index 000000000..9abcf165d --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/common/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Hello Dear"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithexclude/actions/greeting/index.js b/tests/src/integration/zipactionwithexclude/actions/greeting/index.js new file mode 100644 index 000000000..e61d71ab4 --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/greeting/index.js @@ -0,0 +1,21 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common = require('./common/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithexclude/actions/greeting/package.json b/tests/src/integration/zipactionwithexclude/actions/greeting/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/greeting/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithexclude/actions/index.js b/tests/src/integration/zipactionwithexclude/actions/index.js new file mode 100644 index 000000000..e61d71ab4 --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/index.js @@ -0,0 +1,21 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common = require('./common/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithexclude/actions/libs/lib1/utils.js b/tests/src/integration/zipactionwithexclude/actions/libs/lib1/utils.js new file mode 100644 index 000000000..9abcf165d --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/libs/lib1/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Hello Dear"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithexclude/actions/libs/lib2/utils.js b/tests/src/integration/zipactionwithexclude/actions/libs/lib2/utils.js new file mode 100644 index 000000000..9abcf165d --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/libs/lib2/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Hello Dear"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithexclude/actions/libs/lib3/utils.js b/tests/src/integration/zipactionwithexclude/actions/libs/lib3/utils.js new file mode 100644 index 000000000..9abcf165d --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/libs/lib3/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Hello Dear"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithexclude/actions/package.json b/tests/src/integration/zipactionwithexclude/actions/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/actions/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithexclude/manifest.yml b/tests/src/integration/zipactionwithexclude/manifest.yml new file mode 100644 index 000000000..c79b83cb0 --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/manifest.yml @@ -0,0 +1,18 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more contributor +# license agreements; and to You under the Apache License, Version 2.0. + +packages: + zipactionwithexclude: + version: 1.0 + license: Apache-2.0 + actions: + greeting1: + function: actions + runtime: nodejs:6 + exclude: + - actions/* + include: + - ["actions/common/utils.js", "common/utils.js"] + - ["actions/index.js", "index.js"] + - ["actions/package.json", "package.json"] + diff --git a/tests/src/integration/zipactionwithexclude/zipactionwithexclude_test.go b/tests/src/integration/zipactionwithexclude/zipactionwithexclude_test.go new file mode 100644 index 000000000..027285b0a --- /dev/null +++ b/tests/src/integration/zipactionwithexclude/zipactionwithexclude_test.go @@ -0,0 +1,40 @@ +// +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" +) + +func TestZipActionWithExclude(t *testing.T) { + wskdeploy := common.NewWskdeploy() + _, err := wskdeploy.Deploy(manifestPath, deploymentPath) + assert.Equal(t, nil, err, "Failed to deploy based on the manifest and deployment files.") + _, err = wskdeploy.Undeploy(manifestPath, deploymentPath) + assert.Equal(t, nil, err, "Failed to undeploy based on the manifest and deployment files.") +} + +var ( + manifestPath = os.Getenv("GOPATH") + "/src/github.com/apache/incubator-openwhisk-wskdeploy/tests/src/integration/zipactionwithexclude/manifest.yml" + deploymentPath = "" +) diff --git a/tests/src/integration/zipactionwithinclude/actions/common/utils.js b/tests/src/integration/zipactionwithinclude/actions/common/utils.js new file mode 100644 index 000000000..9abcf165d --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/common/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Hello Dear"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting1/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting1/index.js new file mode 100644 index 000000000..af3597bdf --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting1/index.js @@ -0,0 +1,21 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common = require('./actions/common/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting1/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting1/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting1/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting10/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting10/index.js new file mode 100644 index 000000000..85e3ed775 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting10/index.js @@ -0,0 +1,23 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var lib1 = require('./actions/libs/lib1/utils.js') +var lib2 = require('./actions/libs/lib2/utils.js') +var lib3 = require('./actions/libs/lib3/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = lib1.hello || lib2.hello || lib3.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting10/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting10/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting10/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting2/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting2/index.js new file mode 100644 index 000000000..383653998 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting2/index.js @@ -0,0 +1,23 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common1 = require('./common/utils.js') +var common2 = require('./common/common1/utils.js') +var common3 = require('./common/common1/copyUtils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common1.hello || common2.hello || common3.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting2/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting2/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting2/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting3/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting3/index.js new file mode 100644 index 000000000..ab9b3df05 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting3/index.js @@ -0,0 +1,22 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common1 = require('./common/utils.js') +var common2 = require('./common/common1/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common1.hello || common2.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting3/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting3/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting3/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting4/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting4/index.js new file mode 100644 index 000000000..e61d71ab4 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting4/index.js @@ -0,0 +1,21 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common = require('./common/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting4/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting4/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting4/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting5/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting5/index.js new file mode 100644 index 000000000..e61d71ab4 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting5/index.js @@ -0,0 +1,21 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common = require('./common/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting5/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting5/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting5/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting6/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting6/index.js new file mode 100644 index 000000000..af3597bdf --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting6/index.js @@ -0,0 +1,21 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var common = require('./actions/common/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = common.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting6/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting6/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting6/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting7/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting7/index.js new file mode 100644 index 000000000..3461c6955 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting7/index.js @@ -0,0 +1,23 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var lib1 = require('./libs/lib1/utils.js') +var lib2 = require('./libs/lib2/utils.js') +var lib3 = require('./libs/lib3/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = lib1.hello || lib2.hello || lib3.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting7/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting7/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting7/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting8/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting8/index.js new file mode 100644 index 000000000..3461c6955 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting8/index.js @@ -0,0 +1,23 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var lib1 = require('./libs/lib1/utils.js') +var lib2 = require('./libs/lib2/utils.js') +var lib3 = require('./libs/lib3/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = lib1.hello || lib2.hello || lib3.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting8/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting8/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting8/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting9/index.js b/tests/src/integration/zipactionwithinclude/actions/greeting9/index.js new file mode 100644 index 000000000..85e3ed775 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting9/index.js @@ -0,0 +1,23 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +/** + * Return a simple greeting message for someone. + * + * @param name A person's name. + * @param place Where the person is from. + */ + + +var lib1 = require('./actions/libs/lib1/utils.js') +var lib2 = require('./actions/libs/lib2/utils.js') +var lib3 = require('./actions/libs/lib3/utils.js') + +function main(params) { + var name = params.name || params.payload || 'stranger'; + var place = params.place || 'somewhere'; + var hello = lib1.hello || lib2.hello || lib3.hello || 'Hello'; + return {payload: hello + ', ' + name + ' from ' + place + '!'}; +} +exports.main = main; + diff --git a/tests/src/integration/zipactionwithinclude/actions/greeting9/package.json b/tests/src/integration/zipactionwithinclude/actions/greeting9/package.json new file mode 100644 index 000000000..80cb6cd99 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/greeting9/package.json @@ -0,0 +1,6 @@ +{ + "name": "my-action", + "main": "index.js", + "dependencies" : { + } +} diff --git a/tests/src/integration/zipactionwithinclude/actions/libs/lib1/utils.js b/tests/src/integration/zipactionwithinclude/actions/libs/lib1/utils.js new file mode 100644 index 000000000..308416b15 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/libs/lib1/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Good Morning"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithinclude/actions/libs/lib2/utils.js b/tests/src/integration/zipactionwithinclude/actions/libs/lib2/utils.js new file mode 100644 index 000000000..031e63ee7 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/libs/lib2/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Good Evening"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithinclude/actions/libs/lib3/utils.js b/tests/src/integration/zipactionwithinclude/actions/libs/lib3/utils.js new file mode 100644 index 000000000..1fd7cf3d5 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/actions/libs/lib3/utils.js @@ -0,0 +1,9 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more contributor +// license agreements; and to You under the Apache License, Version 2.0. + +const hello = "Hello Afternoon"; + +module.exports = { + hello: hello +}; + diff --git a/tests/src/integration/zipactionwithinclude/deployment.yml b/tests/src/integration/zipactionwithinclude/deployment.yml new file mode 100644 index 000000000..dcd26c867 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/deployment.yml @@ -0,0 +1,28 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more contributor +# license agreements; and to You under the Apache License, Version 2.0. + +project: + packages: + zipactionwithinclude: + actions: + greeting1: + inputs: + name: Amy + place: Vermont + greeting2: + inputs: + name: Bernie + place: Paris + greeting3: + inputs: + name: Cindy + place: New York + greeting4: + inputs: + name: Dough + place: Spain + greeting5: + inputs: + name: Evya + place: Japan + diff --git a/tests/src/integration/zipactionwithinclude/manifest.yml b/tests/src/integration/zipactionwithinclude/manifest.yml new file mode 100644 index 000000000..6f0c29882 --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/manifest.yml @@ -0,0 +1,63 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more contributor +# license agreements; and to You under the Apache License, Version 2.0. + +packages: + zipactionwithinclude: + version: 1.0 + license: Apache-2.0 + actions: + greeting1: + function: actions/greeting1 + runtime: nodejs:6 + include: + - [] + - ["actions/common/utils.js"] + greeting2: + function: actions/greeting2 + runtime: nodejs:6 + include: + - ["actions/common/utils.js", "common/utils.js"] + - ["actions/common/utils.js", "common/common1/utils.js"] + - ["actions/common/utils.js", "common/common1/copyUtils.js"] + greeting3: + function: actions/greeting3 + runtime: nodejs:6 + include: + - ["actions/common/", "common/"] + - ["actions/common/", "common/common1/"] + greeting4: + function: actions/greeting4 + runtime: nodejs:6 + include: + - ["actions/common/*.js", "common/"] + greeting5: + function: actions/greeting5 + runtime: nodejs:6 + include: + - ["actions/common/utils.js", "./common/"] + greeting6: + function: actions/greeting6 + runtime: nodejs:6 + include: + - ["actions/common/*.js"] + greeting7: + function: actions/greeting7 + runtime: nodejs:6 + include: + - ["actions/libs/*", "libs/"] + greeting8: + function: actions/greeting8 + runtime: nodejs:6 + include: + - ["actions/libs/*/utils.js", "libs/"] + greeting9: + function: actions/greeting9 + runtime: nodejs:6 + include: + - ["actions/*/*/utils.js"] + greeting10: + function: actions/greeting10 + runtime: nodejs:6 + include: + - ["actions/*/*/utils.js", "actions/"] + diff --git a/tests/src/integration/zipactionwithinclude/zipactionwithinclude_test.go b/tests/src/integration/zipactionwithinclude/zipactionwithinclude_test.go new file mode 100644 index 000000000..4032f53fa --- /dev/null +++ b/tests/src/integration/zipactionwithinclude/zipactionwithinclude_test.go @@ -0,0 +1,40 @@ +// +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" +) + +func TestZipActionWithInclude(t *testing.T) { + wskdeploy := common.NewWskdeploy() + _, err := wskdeploy.Deploy(manifestPath, deploymentPath) + assert.Equal(t, nil, err, "Failed to deploy based on the manifest and deployment files.") + _, err = wskdeploy.Undeploy(manifestPath, deploymentPath) + assert.Equal(t, nil, err, "Failed to undeploy based on the manifest and deployment files.") +} + +var ( + manifestPath = os.Getenv("GOPATH") + "/src/github.com/apache/incubator-openwhisk-wskdeploy/tests/src/integration/zipactionwithinclude/manifest.yml" + deploymentPath = os.Getenv("GOPATH") + "/src/github.com/apache/incubator-openwhisk-wskdeploy/tests/src/integration/zipactionwithinclude/deployment.yml" +) diff --git a/utils/file.go b/utils/file.go new file mode 100644 index 000000000..415535870 --- /dev/null +++ b/utils/file.go @@ -0,0 +1,152 @@ +/* + * 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 utils + +import ( + "io" + "io/ioutil" + "os" + "path" + "path/filepath" + + "github.com/apache/incubator-openwhisk-wskdeploy/wskprint" +) + +// check if the path represents file path or dir path +func isFilePath(path string) bool { + // when split returns dir and file, splitting path on the final "/" + // check if file is not empty to classify that path as a file path + _, file := filepath.Split(path) + if len(file) == 0 { + return false + } + return true +} + +// check if the given path exists as a file +func isFile(path string) (bool, error) { + var err error + var info os.FileInfo + // run stat on the file and if the it returns no error, + // read the fileInfo to check if its a file or not + if info, err = os.Stat(path); err == nil { + if info.Mode().IsRegular() { + return true, nil + } + } + // stat returned an error and here we are chekcking if it was os.PathError + if !os.IsNotExist(err) { + return false, nil + } + // after running through all the possible checks, return false and an err + return false, err +} + +// copy one single source file to the destination path +func copyFile(src, dst string) error { + var err error + var sourceFD *os.File + var destFD *os.File + var srcInfo os.FileInfo + var srcDirInfo os.FileInfo + + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, "Source File ["+src+"] is being copied to ["+dst+"]") + + // open source file to read it from disk and defer to close the file + // once this function is done executing + if sourceFD, err = os.Open(src); err != nil { + return err + } + defer sourceFD.Close() + + // running stat on Dir(src), Dir returns all but the last element of the src + // this info is needed in case when a destination path has a directory structure which does not exist + if srcDirInfo, err = os.Stat(filepath.Dir(src)); err != nil { + return err + } + + // check if the parent directory exist before creating a destination file + // create specified path along with creating any parent directory + // e.g. when destination is greeting/common/utils.js and parent dir common + // doesn't exist, its getting created here at greeting/common + if _, err = os.Stat(filepath.Dir(dst)); os.IsNotExist(err) { + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, "Creating directory pattern ["+filepath.Dir(dst)+"] before creating destination file") + if err = os.MkdirAll(filepath.Dir(dst), srcDirInfo.Mode()); err != nil { + return err + } + } + + // create destination file before copying source content + // defer closing the destination file until the function is done executing + if destFD, err = os.Create(dst); err != nil { + return err + } + defer destFD.Close() + + // now, actually copy the source file content into destination file + if _, err = io.Copy(destFD, sourceFD); err != nil { + return err + } + + // retrieve the file mode bits of the source file + // so that the bits can be set to the destination file + if srcInfo, err = os.Stat(src); err != nil { + return err + } + return os.Chmod(dst, srcInfo.Mode()) +} + +// recursively copy the entire source directory to destination path +func copyDir(src, dst string) error { + var err error + var fileDescriptors []os.FileInfo + var srcInfo os.FileInfo + + // retrieve os.fileInfo of the source directory + if srcInfo, err = os.Stat(src); err != nil { + return err + } + + // create destination directory with parent directories + if err = os.MkdirAll(dst, srcInfo.Mode()); err != nil { + return err + } + + // now, retrieve all the directory/file entries under the source directory + if fileDescriptors, err = ioutil.ReadDir(src); err != nil { + return err + } + + // iterating over the entire list of files/directories under the destination path + // run copyFile or recursive copyDir based on if its file or dir + for _, fd := range fileDescriptors { + srcFilePath := path.Join(src, fd.Name()) + dstFilePath := path.Join(dst, fd.Name()) + + if fd.IsDir() { + if err = copyDir(srcFilePath, dstFilePath); err != nil { + return err + } + } else { + if err = copyFile(srcFilePath, dstFilePath); err != nil { + return err + } + } + } + return nil +} diff --git a/utils/file_test.go b/utils/file_test.go new file mode 100644 index 000000000..cb8f98dd9 --- /dev/null +++ b/utils/file_test.go @@ -0,0 +1,85 @@ +// +build unit + +/* + * 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 utils + +import ( + "fmt" + "github.com/stretchr/testify/assert" + "testing" +) + +const IS_FILE_PATH_FAILURE_FOR_FILE = "Failed to classify the file path [%s] as file." +const IS_FILE_PATH_FAILURE_FOR_DIR = "Failed to classify the dir path [%s] as dir." +const IS_FILE_PATH_FAILURE_FOR_EMPTY_PATH = "Failed to classify empty path [%s] as dir." +const IS_FILE_FAILURE_FOR_FILE = "Failed to detect if the path [%s] is a valid file." +const IS_FILE_FAILURE_FOR_DIR = "Failed to detect if the path [%s] is a dir." +const TEST_ERROR_IS_FILE_FAILURE = "Failed to run isFile on [%s] Error: %s" + +func TestIsFilePath(t *testing.T) { + paths := []string{ + "", + "/home/arnie/amelia.jpg", + "/mnt/photos/", + "rabbit.jpg", + "/usr/local//go", + "common/actions/*.js/", + "common/*/actions/*/code/*.js", + "common/actions/", + } + for _, p := range paths { + switch p { + case "": + assert.False(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_EMPTY_PATH, p)) + case "/home/arnie/amelia.jpg": + assert.True(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_FILE, p)) + case "/mnt/photos/": + assert.False(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_DIR, p)) + case "rabbit.jpg": + assert.True(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_FILE, p)) + case "/usr/local//go": + assert.True(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_FILE, p)) + case "common/actions/*.js/": + assert.False(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_DIR, p)) + case "common/*/actions/*/code/*.js": + assert.True(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_FILE, p)) + case "common/actions/": + assert.False(t, isFilePath(p), fmt.Sprintf(IS_FILE_PATH_FAILURE_FOR_DIR, p)) + } + } +} + +func TestIsFile(t *testing.T) { + paths := []string{ + "../tests/dat/", + "../tests/dat/manifest_hello_swift.yaml", + } + for _, p := range paths { + f, err := isFile(p) + if err != nil { + assert.Fail(t, fmt.Sprintf(TEST_ERROR_IS_FILE_FAILURE, p, err.Error())) + } + switch p { + case "tests/dat/": + assert.False(t, f, fmt.Sprintf(IS_FILE_FAILURE_FOR_FILE, p)) + case "tests/dat/manifest_hello_swift.yaml": + assert.True(t, f, fmt.Sprintf(IS_FILE_FAILURE_FOR_FILE, p)) + } + } +} diff --git a/utils/misc.go b/utils/misc.go index 81ea403db..715db303d 100644 --- a/utils/misc.go +++ b/utils/misc.go @@ -18,15 +18,12 @@ package utils import ( - "archive/zip" "encoding/json" - "io" "io/ioutil" "net/http" "os" "os/user" "path" - "path/filepath" "strings" "github.com/apache/incubator-openwhisk-client-go/whisk" @@ -99,62 +96,6 @@ func PrettyJSON(j interface{}) (string, error) { return string(bytes), nil } -func NewZipWritter(src, des string) *ZipWritter { - zw := &ZipWritter{src: src, des: des} - return zw -} - -type ZipWritter struct { - src string - des string - zipWritter *zip.Writer -} - -func (zw *ZipWritter) zipFile(path string, f os.FileInfo, err error) error { - if err != nil { - return err - } - if !f.Mode().IsRegular() || f.Size() == 0 { - return nil - } - file, err := os.Open(path) - if err != nil { - return err - } - defer file.Close() - - fileName := strings.TrimPrefix(path, zw.src+"/") - wr, err := zw.zipWritter.Create(fileName) - if err != nil { - return err - } - - _, err = io.Copy(wr, file) - if err != nil { - return err - } - return nil -} - -func (zw *ZipWritter) Zip() error { - // create zip file - zipFile, err := os.Create(zw.des) - if err != nil { - return err - } - defer zipFile.Close() - zw.zipWritter = zip.NewWriter(zipFile) - err = filepath.Walk(zw.src, zw.zipFile) - if err != nil { - return nil - } - err = zw.zipWritter.Close() - if err != nil { - return err - } - return nil -} - func GetManifestFilePath(projectPath string) string { if _, err := os.Stat(path.Join(projectPath, ManifestFileNameYaml)); err == nil { return path.Join(projectPath, ManifestFileNameYaml) diff --git a/utils/misc_test.go b/utils/misc_test.go index 72d518b00..4f92be279 100644 --- a/utils/misc_test.go +++ b/utils/misc_test.go @@ -61,7 +61,7 @@ func TestDependencies(t *testing.T) { func TestNewZipWritter(t *testing.T) { filePath := "../tests/src/integration/zipaction/actions/cat" zipName := filePath + ".zip" - err := NewZipWritter(filePath, zipName).Zip() + err := NewZipWritter(filePath, zipName, make([][]string, 0), make([]string, 0), "").Zip() defer os.Remove(zipName) assert.Equal(t, nil, err, "zip folder error happened.") } diff --git a/utils/zip.go b/utils/zip.go new file mode 100644 index 000000000..a818bc0fd --- /dev/null +++ b/utils/zip.go @@ -0,0 +1,363 @@ +/* + * 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 utils + +import ( + "archive/zip" + "io" + "os" + "path/filepath" + "strings" + + "github.com/apache/incubator-openwhisk-wskdeploy/wski18n" + "github.com/apache/incubator-openwhisk-wskdeploy/wskprint" +) + +const PATH_WILDCARD = "*" +const ONE_DIR_UP = "../" + +func NewZipWritter(src string, des string, include [][]string, exclude []string, manifestFilePath string) *ZipWritter { + zw := &ZipWritter{ + src: src, + des: des, + include: include, + exclude: exclude, + excludedFiles: make(map[string]bool, 0), + manifestFilePath: manifestFilePath, + } + return zw +} + +type ZipWritter struct { + src string + des string + include [][]string + exclude []string + excludedFiles map[string]bool + manifestFilePath string + zipWritter *zip.Writer +} + +type Include struct { + source string + destination string +} + +func (zw *ZipWritter) zipFile(path string, f os.FileInfo, err error) error { + var file *os.File + var wr io.Writer + var verboseMsg string + + if err != nil { + return err + } + + if zw.excludedFiles[filepath.Clean(path)] { + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_ZIP_EXCLUDING_FILE_X_path_X, + map[string]interface{}{ + wski18n.KEY_PATH: path, + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + return nil + } + + if !f.Mode().IsRegular() || f.Size() == 0 { + return nil + } + if file, err = os.Open(path); err != nil { + return err + } + defer file.Close() + + fileName := strings.TrimPrefix(path, zw.src+"/") + if wr, err = zw.zipWritter.Create(fileName); err != nil { + return err + } + + if _, err = io.Copy(wr, file); err != nil { + return err + } + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_ZIP_ADDING_FILE_X_path_X, + map[string]interface{}{ + wski18n.KEY_PATH: path, + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + return nil +} + +func (zw *ZipWritter) buildIncludeMetadata() ([]Include, error) { + var includeInfo []Include + var listOfSourceFiles []string + var err error + var verboseMsg string + + // iterate over set of included files specified in manifest YAML e.g. + // include: + // - ["source"] + // - ["source", "destination"] + for _, includeData := range zw.include { + var i Include + // if "destination" is not specified, its considered same as "source" + // "source" is relative to where manifest.yaml file is located + // relative source path is converted to absolute path by appending manifest path + // since the relative source path might not be accessible from where wskdeploy is invoked + // "destination" is relative to the action directory, the one specified in function + // relative path is converted to absolute path by appending function directory + if len(includeData) == 1 { + i.source = filepath.Join(zw.manifestFilePath, includeData[0]) + i.destination = filepath.Join(zw.src, includeData[0]) + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_ZIP_INCLUDE_SOURCE_PATH_X_path_X, + map[string]interface{}{ + wski18n.KEY_PATH: includeData[0], + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + } else if len(includeData) == 2 { + i.source = filepath.Join(zw.manifestFilePath, includeData[0]) + i.destination = zw.src + "/" + includeData[1] + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_ZIP_INCLUDE_SOURCE_PATH_X_path_X_DESTINATION_PATH_X_dest_X, + map[string]interface{}{ + wski18n.KEY_PATH: includeData[0], + wski18n.KEY_DESTINATION: includeData[1], + }) + } else { + if len(includeData) == 0 { + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_INVALID_INCLUDE_ENTRY, + map[string]interface{}{ + wski18n.KEY_INCLUDE: "", + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + } else { + for index, d := range includeData { + includeData[index] = "\"" + d + "\"" + } + includeEntry := strings.Join(includeData, ", ") + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_INVALID_INCLUDE_ENTRY, + map[string]interface{}{ + wski18n.KEY_INCLUDE: includeEntry, + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + } + continue + } + + // set destDir to the destination location + // check if its a file than change it to the Dir of destination file + destDir := i.destination + if isFilePath(destDir) { + destDir = filepath.Dir(destDir) + } + // trim path wildcard "*" from the destination path as if it has any + destDirs := strings.Split(destDir, PATH_WILDCARD) + destDir = destDirs[0] + + // retrieve the name of all files matching pattern or nil if there is no matching file + // listOfSourceFiles will hold a list of files matching patterns such as + // actions/* or actions/libs/* or actions/libs/*/utils.js or actions/*/*/utils.js + if listOfSourceFiles, err = filepath.Glob(i.source); err != nil { + return includeInfo, err + } + + // handle the scenarios where included path is something similar to actions/common/*.js + // or actions/libs/* or actions/libs/*/utils.js + // and destination is set to libs/ or libs/* or ./libs/* or libs/*/utils.js or libs/ or ./libs/ + if strings.ContainsAny(i.source, PATH_WILDCARD) { + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, wski18n.T(wski18n.ID_VERBOSE_LIST_OF_FILES_MATCHING_PATTERN)) + for _, file := range listOfSourceFiles { + var relPath string + if relPath, err = filepath.Rel(i.source, file); err != nil { + return includeInfo, err + } + relPath = strings.TrimLeft(relPath, ONE_DIR_UP) + j := Include{ + source: file, + destination: filepath.Join(destDir, relPath), + } + includeInfo = append(includeInfo, j) + zw.excludedFiles[j.source] = false + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_ZIP_INCLUDE_SOURCE_PATH_X_path_X_DESTINATION_PATH_X_dest_X, + map[string]interface{}{ + wski18n.KEY_PATH: j.source, + wski18n.KEY_DESTINATION: j.destination, + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + } + // handle scenarios where included path is something similar to actions/common/utils.js + // and destination is set to ./common/ i.e. no file name specified in the destination + } else { + if f, err := isFile(i.source); err == nil && f { + if _, file := filepath.Split(i.destination); len(file) == 0 { + _, sFile := filepath.Split(i.source) + i.destination = i.destination + sFile + } + } + // append just parsed include info to the list for further processing + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, wski18n.T(wski18n.ID_VERBOSE_LIST_OF_FILES_MATCHING_PATTERN)) + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_ZIP_INCLUDE_SOURCE_PATH_X_path_X_DESTINATION_PATH_X_dest_X, + map[string]interface{}{ + wski18n.KEY_PATH: i.source, + wski18n.KEY_DESTINATION: i.destination, + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + includeInfo = append(includeInfo, i) + zw.excludedFiles[i.source] = false + } + } + return includeInfo, nil +} + +func (zw *ZipWritter) buildExcludeMetadata() error { + var err error + for _, exclude := range zw.exclude { + exclude = filepath.Join(zw.manifestFilePath, exclude) + if err = zw.findExcludedIncludedFiles(exclude, true); err != nil { + return err + } + } + return err +} + +func (zw *ZipWritter) findExcludedIncludedFiles(functionPath string, flag bool) error { + var err error + var files []string + var excludedFiles []string + var f bool + + if !strings.HasSuffix(functionPath, PATH_WILDCARD) { + functionPath = filepath.Join(functionPath, PATH_WILDCARD) + } + if excludedFiles, err = filepath.Glob(functionPath); err != nil { + return err + } + for _, file := range excludedFiles { + err = filepath.Walk(file, func(path string, info os.FileInfo, err error) error { + files = append(files, path) + return nil + }) + if err != nil { + return err + } + } + for _, file := range files { + if f, err = isFile(file); err != nil { + return err + } else if f { + zw.excludedFiles[file] = flag + } else { + if err = zw.findExcludedIncludedFiles(file, flag); err != nil { + return err + } + } + } + return err +} + +func (zw *ZipWritter) Zip() error { + + var zipFile *os.File + var err error + var fileInfo os.FileInfo + var verboseMsg string + + // create zip file e.g. greeting.zip + if zipFile, err = os.Create(zw.des); err != nil { + return err + } + defer zipFile.Close() + + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_CREATING_ZIP_FILE_X_path_X, + map[string]interface{}{ + wski18n.KEY_PATH: zipFile.Name(), + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + + // creating a new zip writter for greeting.zip + zw.zipWritter = zip.NewWriter(zipFile) + + // build a map of file names and bool indicating whether the file is included or excluded + // iterate over the directory specified in "function", find the list of files and mark them as not excluded + if err = zw.findExcludedIncludedFiles(zw.src, false); err != nil { + return err + } + + if err = zw.buildExcludeMetadata(); err != nil { + return err + } + + // walk file system rooted at the directory specified in "function" + // walk over each file and dir under root directory e.g. function: actions/greeting + // add actions/greeting/index.js and actions/greeting/package.json to zip file + if err = filepath.Walk(zw.src, zw.zipFile); err != nil { + return nil + } + + // maintain a list of included files and/or directories with their destination + var includeInfo []Include + includeInfo, err = zw.buildIncludeMetadata() + if err != nil { + return err + } + + for _, i := range includeInfo { + if i.source != i.destination { + // now determine whether the included item is file or dir + // it could list something like this as well, "actions/common/*.js" + if fileInfo, err = os.Stat(i.source); err != nil { + return err + } + + // if the included item is a directory, call a function to copy the + // entire directory recursively including its subdirectories and files + if fileInfo.Mode().IsDir() { + if err = copyDir(i.source, i.destination); err != nil { + return err + } + // if the included item is a file, call a function to copy the file + // along with its path by creating the parent directories + } else if fileInfo.Mode().IsRegular() { + if err = copyFile(i.source, i.destination); err != nil { + return err + } + } + } + // add included item into zip file greeting.zip + if err = filepath.Walk(i.destination, zw.zipFile); err != nil { + return nil + } + } + + // now close the zip file greeting.zip as all the included items + // are added into the zip file along with the action root dir + if err = zw.zipWritter.Close(); err != nil { + return err + } + + // and its safe to delete the files/directories which we copied earlier + // to include them in the zip file greeting.zip + for _, i := range includeInfo { + if filepath.Clean(i.source) != filepath.Clean(i.destination) { + verboseMsg = wski18n.T(wski18n.ID_VERBOSE_DELETING_FILE_X_path_X, + map[string]interface{}{ + wski18n.KEY_PATH: i.destination, + }) + wskprint.PrintlnOpenWhiskVerbose(Flags.Verbose, verboseMsg) + os.RemoveAll(i.destination) + } + } + + return nil +} diff --git a/wski18n/i18n_ids.go b/wski18n/i18n_ids.go index 0cdd2dd4b..1203516d7 100644 --- a/wski18n/i18n_ids.go +++ b/wski18n/i18n_ids.go @@ -86,6 +86,8 @@ const ( KEY_API_BASE_PATH = "apibasepath" KEY_RESPONSE = "response" KEY_API_RELATIVE_PATH = "apirelativepath" + KEY_DESTINATION = "destination" + KEY_INCLUDE = "include" ) // DO NOT TRANSLATE @@ -241,10 +243,18 @@ const ( **/ // Verbose (Debug/Trace) messages - ID_DEBUG_PROJECT_SEARCH_X_path_X_key_X = "msg_dbg_searching_project_directory" - ID_DEBUG_DEPLOYMENT_NAME_FOUND_X_key_X_name_X = "msg_dbg_deployment_name_found" - ID_DEBUG_PACKAGES_FOUND_UNDER_ROOT_X_path_X = "msg_dbg_packages_found_root" - ID_DEBUG_PACKAGES_FOUND_UNDER_PROJECT_X_path_X_name_X = "msg_dbg_packages_found_project" + ID_DEBUG_PROJECT_SEARCH_X_path_X_key_X = "msg_dbg_searching_project_directory" + ID_DEBUG_DEPLOYMENT_NAME_FOUND_X_key_X_name_X = "msg_dbg_deployment_name_found" + ID_DEBUG_PACKAGES_FOUND_UNDER_ROOT_X_path_X = "msg_dbg_packages_found_root" + ID_DEBUG_PACKAGES_FOUND_UNDER_PROJECT_X_path_X_name_X = "msg_dbg_packages_found_project" + ID_VERBOSE_ZIP_EXCLUDING_FILE_X_path_X = "msg_verbose_zip_exclude_file_path" + ID_VERBOSE_ZIP_ADDING_FILE_X_path_X = "msg_verbose_zip_adding_file_path" + ID_VERBOSE_ZIP_INCLUDE_SOURCE_PATH_X_path_X = "msg_verbose_zip_include_source_path" + ID_VERBOSE_ZIP_INCLUDE_SOURCE_PATH_X_path_X_DESTINATION_PATH_X_dest_X = "msg_verbose_zip_include_source_path_destination_path" + ID_VERBOSE_INVALID_INCLUDE_ENTRY = "msg_verbose_invalid_include_entry" + ID_VERBOSE_CREATING_ZIP_FILE_X_path_X = "msg_verbose_creating_zip_file" + ID_VERBOSE_DELETING_FILE_X_path_X = "msg_verbose_deleting_file" + ID_VERBOSE_LIST_OF_FILES_MATCHING_PATTERN = "msg_verbose_list_of_files_matching_pattern" ) // DO NOT TRANSLATE diff --git a/wski18n/i18n_resources.go b/wski18n/i18n_resources.go index 72285a7be..164bc680b 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/de_DE.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 0)} a := &asset{bytes: bytes, info: info} return a, nil } -var _wski18nResourcesEn_usAllJson = []byte("\x1f\x8b\x08\x00\x00\x00\x00\x00\x00\xff\xcc\x7c\x7b\x6f\x1b\xb7\x96\xf8\xff\xf9\x14\x07\xc5\x05\xd2\x02\xb6\xdc\xde\x1f\x7e\xc0\x22\xd8\x2c\xe0\x4d\xdc\x5e\xdf\x26\x71\xe0\x38\x2d\x8a\x24\x98\x50\x33\x47\x12\xaf\x67\xc8\xb9\x24\x47\x8a\x6a\xe8\xbb\x2f\xce\x21\x39\x0f\x59\xf3\x90\x92\x62\x37\xff\x44\x12\xc9\xf3\xe2\xe1\x79\x92\xfe\xf0\x04\xe0\xe1\x09\x00\xc0\x77\x32\xfb\xee\x19\x7c\x57\xd8\x65\x52\x1a\x5c\xc8\x2f\x09\x1a\xa3\xcd\x77\x67\x7e\xd4\x19\xa1\x6c\x2e\x9c\xd4\x8a\xa6\x5d\xf1\xd8\x13\x80\xdd\xd9\x00\x04\xa9\x16\xba\x07\xc0\x35\x0d\x8d\xad\xb7\x55\x9a\xa2\xb5\x3d\x20\xde\x85\xd1\x31\x28\x1b\x61\x94\x54\xcb\x1e\x28\xbf\x87\xd1\x5e\x28\x69\x91\x25\x19\xda\x34\xc9\xb5\x5a\x26\x06\x4b\x6d\x5c\x0f\xac\x5b\x1e\xb4\xa0\x15\x64\x58\xe6\x7a\x8b\x19\xa0\x72\xd2\x49\xb4\xf0\xbd\x9c\xe1\xec\x0c\xde\x8a\xf4\x5e\x2c\xd1\x9e\xc1\x65\x4a\xeb\xec\x19\xdc\x19\xb9\x5c\xa2\xb1\x67\x70\x5b\xe5\x34\x82\x2e\x9d\xfd\x00\xc2\xc2\x06\xf3\x9c\xfe\x37\x98\xa2\x72\xbc\x62\xcd\xd8\x2c\x48\x05\x6e\x85\x60\x4b\x4c\xe5\x42\x62\x06\x4a\x14\x68\x4b\x91\xe2\x6c\x32\x2f\x5a\xf7\x71\x72\xb7\x42\xb8\x29\x51\xfd\xbe\x92\xf6\x1e\x5e\x32\x33\x05\x91\x70\xa7\x75\xfe\x51\x7d\x54\x77\x1a\xe6\xb8\x94\x0a\x36\xda\xdc\x4b\xb5\x84\x8d\x74\x2b\xd8\xd8\x7b\xcf\xf8\x19\x98\xca\x13\xf8\xb4\xfe\xed\x29\xa4\xba\x28\x84\xca\x9e\x11\x80\x8f\xee\x6f\xcd\x74\x86\xb8\x92\x16\x36\x32\xcf\x83\xec\x5a\xf8\x85\xb5\xe8\x6c\x8b\x57\xa9\xa0\x10\x4a\x2e\xd0\xba\xd9\x56\x14\x39\x68\xd3\xfa\xa1\xc8\x3f\xaa\xeb\x05\xa4\x95\x31\x44\x72\x26\x0d\xa6\x4e\x9b\x2d\x64\x1a\xad\x72\xb0\x12\x6b\x04\xa1\xb6\xf5\x12\x58\xc8\x1c\xcf\x1a\x72\xa0\x34\x52\x39\x0b\x8e\x48\x5a\x61\x5e\x42\x81\xd6\x8a\x25\xce\x3c\xa1\x08\x85\xb6\x8e\xd9\xd1\x0a\x36\x62\x6b\x41\x2f\xa0\xb2\x2c\x87\x1a\x88\xd3\x91\x13\xa1\xb2\x0b\x6d\xa0\x52\x7d\x9c\x09\x83\x2c\x94\x8e\x48\x5a\x5f\xe0\xbc\x80\x52\xb8\xd5\x85\xd3\x17\x1d\xc6\xa7\xcd\x82\xf3\xac\x1e\xc8\xea\xbd\x3c\x00\x20\x52\x78\xf8\xd7\x89\x54\x8c\x4e\x1f\x24\xe7\xa3\xba\xac\x94\x5b\xd1\xb1\x49\x59\x1d\x9f\x7d\x54\x0d\x6c\x83\x22\xb3\x90\x1a\xcc\x68\x82\xc8\x2d\x2c\x8c\x2e\xe0\x6f\xff\xb8\x79\x7d\x75\x31\xdb\xd8\xfb\xd2\xe8\xd2\xc2\x7c\x0b\x19\x2e\x44\x95\xbb\x8f\xea\x66\x8d\x66\x63\xa4\xc3\xf8\x13\xa4\x5a\x2d\xe4\x92\x37\x9d\x8e\xea\x8b\x57\xd7\xcf\x3e\x2a\x80\x8e\x24\xcf\xc3\xa4\xff\x6c\x4d\xfe\xaf\x01\x01\xdc\x98\xa0\x9e\x5b\x10\x79\x0e\x6e\x65\x70\x00\xb8\x28\xe5\x8a\x34\xe8\x1f\x37\xef\xee\xe8\x6b\xe5\x56\xf0\xeb\xd5\x1f\x70\x7e\x5e\x9f\x62\x78\x73\xf9\xfa\xea\xdd\xdb\xcb\x17\x57\xbd\x58\x27\x9c\x73\xbb\xd2\xc6\x0d\x1b\xad\xb7\x46\xaf\x65\x86\x16\x04\xd8\xaa\x28\x84\x21\x29\xd3\x7c\xd2\xe9\x47\x9a\x3a\x47\x52\xf2\x68\xdd\x2e\xe2\x5e\x63\x06\x73\x61\x31\x23\x96\x23\x8d\xad\xbd\x85\x3f\x2e\x5f\xbf\x9a\x62\x97\x02\xbd\xfd\x86\xe9\x12\x9c\xd6\x39\x58\x74\x74\xbe\xf8\x6c\x06\xa9\x6e\x75\x65\x40\x97\xa8\x36\x4c\x6f\x19\xec\x6c\x38\x96\xa2\x7b\xd8\xa7\xd3\xb2\x46\x63\x09\x77\x9f\xf0\xa4\x72\x6c\xe7\xc2\x3c\x50\x55\x31\x47\x43\xb2\xab\x37\x7c\x32\x2e\xbb\x55\xe9\x30\xdf\x4e\x03\x4d\xf2\xcc\x36\x9b\x53\x33\x3b\x47\xb7\x41\x54\x90\xe6\x92\xc4\x2e\x54\x06\x16\xcd\x1a\xcd\x64\xa7\x30\x9d\x86\xd6\xf6\x12\x9e\xa8\x0a\xfc\x43\x47\x75\xfa\xb7\x82\xd6\xe9\x92\xe0\x8b\xbc\x0d\x8f\xb6\x28\x4e\x67\xd5\x21\xbb\xf0\x52\x2e\x16\xc8\x16\x3d\x5a\x5c\x53\x29\xf2\xdd\x4c\xce\xb3\xae\x11\xa2\x9f\x1e\xff\x32\xd1\x82\x0d\x4e\x6d\x5b\xaf\xd3\x61\x9c\x97\x46\xff\x0b\x53\x47\xe7\x1d\xde\xde\xde\xfc\xf3\xea\xc5\xdd\x64\x3d\x89\xa2\xee\xd9\xa7\xf7\xbd\x7e\x86\x8d\xa5\x57\x88\xa9\xfa\x30\x15\x97\xc1\x42\xaf\xd1\x3e\xc6\xb9\x59\xc9\x74\x05\x1b\x34\xd8\x04\x45\x4c\x07\x9d\x9a\x8e\x26\xec\xdb\x8b\x4e\x9c\x91\x61\x8e\x8e\x36\xfb\x30\x53\x1d\x60\xde\x9d\x9b\x4a\x3d\xfb\x3f\xe7\xde\x0e\x43\x3a\xa4\x0d\xf0\xbd\x56\xf9\x96\xe3\x2b\x0b\x0b\x6d\x5a\xe2\xe1\xe8\x8f\x15\xac\xd0\x19\xfe\x30\x59\x6f\xf0\xcb\x80\x1f\xb8\xe2\x41\x08\x94\x74\x84\x5b\x8b\x7c\xaa\xd2\x4c\x40\x64\x69\xbb\xc4\x12\xb3\x61\x8c\x64\x6d\x3a\x4a\xb2\xa8\x14\xc7\xcd\xde\x46\xf4\xc4\x63\xb4\x8a\x02\x50\x4f\xc7\x9e\x16\xf8\x1f\x7b\x84\xde\xda\x54\x3f\x0f\xb3\xf3\x23\x9c\xee\x22\x17\xcb\x44\x94\x32\x21\xf7\xde\xc3\xbf\xf7\x4f\x97\x6f\xaf\xe1\x33\xf9\xff\xcf\x13\x21\x0e\x3b\xa2\x16\xd0\xdf\xae\x6e\xdf\x5d\xdf\xbc\x99\x04\xb7\x72\xab\xe4\x1e\xfb\x0e\x37\x0d\x6b\x23\xff\xe4\x1f\xe0\xf3\xaf\x57\x7f\x4c\x01\x9a\xa2\x71\x09\xed\x4e\x0f\x54\x92\x2f\x59\x6f\x3a\xb2\x33\x9a\xcc\x5b\x39\x05\x30\x87\x62\x3d\x50\xdb\x41\xdd\xf7\x31\xd2\x93\x76\x3f\x34\x1c\x39\x2c\x5e\x2a\x79\xae\x37\x49\x80\xd1\x97\x7d\xf2\x24\xa8\x27\x8d\x43\x6d\x8e\xef\x90\x5c\xea\xa4\xa1\xf6\x83\x13\x40\x97\x06\xd7\x12\x37\x3d\x70\xed\x8a\x09\x8d\x40\x2f\x3a\x8e\xba\xcc\x85\x9a\x80\xe1\x1e\xb7\x93\xb7\xf4\x1e\xb7\x53\x09\xf7\x92\x0e\x86\x60\x50\xd0\xd1\x48\xd4\xe9\xb4\x23\xc7\x00\x85\x30\xf7\x98\x45\x53\x32\x49\x54\x0c\x27\xa1\x43\xdf\xc7\x4c\x40\xc5\x53\xc6\x21\x46\xeb\x30\xb2\xab\x1d\xe7\x34\x01\x6c\x9d\x08\xf4\xc0\x6d\xc6\x27\x33\x3d\x42\xa1\x8f\x0b\x72\xb4\x36\x4a\x7b\x02\x68\xeb\x8c\xec\x85\xec\xb7\xae\xb2\x48\xce\x6b\x21\x15\x66\x64\x95\x9d\x2c\xea\x70\x79\x02\x06\x67\xfa\x85\xc0\x63\xa0\x2b\x57\x56\x53\x88\xf5\xea\xb6\x46\x33\xd7\xb6\x0f\x64\x18\x3d\x16\x68\x29\x8c\x28\x7a\x05\x6c\x44\x81\x0e\x0d\xac\x45\x5e\x21\x7b\x6f\x32\xa6\xf0\xdb\xe5\xab\xf7\x57\x9f\xc9\xb9\x17\xe2\x48\x54\x43\xa7\xf1\xf3\xcf\xd7\xaf\xae\x3e\x53\x9a\xeb\x84\xe4\x00\xf9\x10\x05\xff\x7c\x77\xf3\x66\x1c\x35\x5b\xd5\xa4\x90\x96\x62\x71\xf6\x17\xfd\xee\x82\x1c\x31\xcd\x68\x72\x77\x20\x5b\x20\x2d\x28\x1d\xb3\xee\xca\x60\x36\xfb\x38\xb4\xef\x7b\x18\x7d\xa6\x3c\x80\x91\x7c\x1e\x27\xd3\x5f\x85\x67\xec\xb8\x11\xa6\x26\x37\x3f\x09\x55\x60\x65\xa8\x2a\xba\xcf\xcf\x87\x87\x87\x19\x7d\xde\xed\x3e\x9d\xf9\xc0\xe8\xe1\x61\x66\x75\x65\x52\xdc\xed\x26\xe1\xf4\x1b\x36\x86\x93\x0b\x10\x61\xaf\x2c\xba\xd3\x70\xd5\xe2\x19\xc3\xd6\x91\x23\xb1\x58\xff\x70\x3a\x9f\xa5\x5c\x6e\x12\xc1\x05\xe1\xc4\xe9\x7b\x54\xa3\x2c\xd3\x0a\xf0\x2b\x80\x57\x9c\xc6\x7c\xa5\x0a\x61\xec\x4a\xe4\x49\xae\x53\x91\xf7\xa6\x49\x61\x56\x2b\xb2\x0d\xa6\x30\x44\xbc\xbc\x3a\x1c\xcf\x89\x08\x15\x3a\xca\x0e\x4e\x46\x29\x95\x43\xa3\xd0\x81\x70\xc4\x6e\x65\xf2\x11\x5e\x9b\xb8\x21\x49\x85\x4a\x31\xcf\x7b\xbd\xf6\xcd\xaf\x33\x78\xe1\xe7\x34\x05\x23\xce\x83\x26\x22\x58\x08\xd9\x0f\xbd\x55\x90\xce\x64\x16\xce\x62\x51\xe6\xe8\x10\x6c\x45\x5b\xba\xa8\xf2\x7c\x3b\x83\xdb\x4a\xc1\xe7\xc7\x19\xd7\x67\x4e\x10\x38\x63\x25\xdb\xe8\xa4\xc8\xf3\x6d\x93\x9e\xfa\x4c\x64\x2a\xa5\xbe\x5a\x96\x58\x27\x5c\xd5\x17\x2d\x9e\x9f\x9f\x9f\x3f\x7f\xfe\xfc\xf9\xe1\xa2\xfa\x3b\x5e\x0a\x34\x81\x26\x4e\xc2\xca\xbd\x11\xcc\xa6\x88\x28\x8a\x26\x83\xd0\x50\xf1\xc2\x19\x56\xb2\xd3\xf7\xba\xbd\x76\x3a\x92\xc1\xfd\x7e\xdf\x0e\x59\x07\x77\x7c\x32\xbe\x31\xf9\x75\x50\x9e\x20\xc1\xd0\xeb\x48\xb8\x88\xc5\xde\x9a\xac\x5c\x22\x5c\x42\xf1\x56\x0f\xd2\x87\x87\x59\x5a\x64\xbb\x5d\x28\x7d\x3d\x3c\xcc\x68\xa1\xdb\x96\xb8\xdb\xb1\xa5\xa4\xb5\xbb\xdd\xa7\xd9\x6c\x10\x37\x07\xc9\xdb\x24\xea\xf3\x48\x1f\xed\xe1\x81\x42\xf6\x80\x80\x88\xdc\xed\x3e\xc1\x4a\x58\x98\x23\xaa\x0e\xc3\xf5\x09\x99\x8e\xbd\xbf\xf1\xf6\x32\x8e\xc3\x41\x02\x66\xb3\x81\x92\x65\x40\xd1\x54\x9f\xbf\x1d\x8b\x0d\xcc\x29\x4c\xc6\xd9\xfd\x6c\xbe\x6f\x66\x1c\x64\x74\x90\xcf\x0c\x4b\x54\x19\xaa\xf4\x18\x71\x36\x8b\x4e\xc7\xd3\x1c\x91\x5e\x99\xbe\x3c\x88\xe6\x6b\x14\xe7\x30\x15\x64\x18\x2a\xd3\x17\x97\xbd\xec\xd4\x9c\x0f\xb3\xfe\xbf\xe8\x23\x22\x3f\xc7\xe9\xc9\xd7\xed\xe0\x63\x33\xf7\x6d\xf6\x70\xe2\xc9\xe8\xa3\x64\x78\x1f\xdf\xef\x75\x0f\x4e\xd9\xc9\x21\xaa\x42\x85\xe0\x54\x9f\xc3\x14\x79\x0f\x50\x57\x20\x86\x68\x81\xac\x32\xb4\x93\xb1\xc6\xd9\xf2\x88\x7f\x9d\xbe\x45\x1e\x17\xba\x52\x59\x12\xe8\x0d\x96\xaa\x57\x01\x42\x55\xfd\xa0\x85\x0c\xa5\x7b\xbe\x80\x40\x74\xb5\x0a\xf7\xb1\xb9\xbe\x5f\xc4\x65\x27\xe5\x3f\x13\x04\x61\x99\x17\x6e\x8f\x4f\x0d\x0b\x42\x4d\x2d\x09\x6d\xa3\xbe\xce\x9b\x1f\xe5\x64\x02\x5a\xf5\x3e\x83\x5c\xc7\xc8\xce\xb8\x0f\xdb\x84\x5b\xf5\xb6\x11\x1d\xa6\x5e\x11\x90\x80\x68\xb5\x27\xda\x5d\x4d\x7f\x79\x20\x68\xbf\xf1\x7d\xb7\xb1\x9b\x16\x57\xb7\xb7\x37\xb7\xef\x7a\xe8\x7e\xbe\xff\x0f\xfc\x74\x78\x34\xf0\xfc\xf9\x80\xfb\x31\xa6\x7b\xd0\xee\x95\xde\xa8\x84\x22\x85\xf1\xa3\x4e\xb3\x48\x54\x61\xd5\x0c\x5a\xc5\x71\xee\x39\xd8\xaa\xf4\x25\xfa\x0b\x2e\x2b\xcf\xec\xd6\x3a\x2c\x60\x2e\x55\x26\xd5\xd2\x82\x36\xb0\x94\x6e\x55\xcd\x67\xa9\x2e\xea\xf6\xde\xb0\xbf\x34\x26\xfa\xcc\xd4\xa0\x70\x7d\x64\xf2\xc5\x22\xe0\x29\x1d\xb5\xe4\xeb\x25\x7c\x23\x29\xde\xc5\x78\x46\x83\x68\xcc\x6e\xc7\x7d\x01\x3f\x96\xea\xcc\x0f\xd0\x87\x91\x6c\xa6\x45\x92\x3f\x2b\x83\x24\x65\x8f\x4e\xca\x5f\x44\xd2\x02\x31\x4b\xa4\x5a\xeb\xfb\x3e\x82\x7e\x66\xb3\x45\xe6\xc2\x4f\xe3\x03\x49\xcb\x60\xb3\xc2\x56\xa7\xcc\xf9\x7b\x45\x61\xe8\xaf\xa1\xf6\x1e\xb7\x75\x0d\x85\xe2\x5d\xe1\xb4\x19\xaa\x0f\xd5\x73\xb8\xdc\xf0\x21\x0a\xf3\x13\xe9\x63\x80\x33\x8a\x33\x96\x52\x13\xa5\x9d\x37\x76\x3d\x08\x5f\xb7\x6b\xae\x6c\xab\x79\x36\xe5\xbb\x5c\xf4\x6c\x47\xd4\x63\x48\x39\x7a\x2f\xa4\x2d\x84\x4b\xfb\xc2\x77\x62\xb0\x56\x0f\x5a\x90\x31\x8a\x2c\xda\x53\xa9\xf6\x8b\xfb\x7e\x3c\xd0\xc0\xf7\x93\x98\x4c\x46\xc2\xdb\xca\xe6\x8d\x26\x15\x2d\x20\x9d\x5a\xb2\x1f\x8d\x6c\x0c\x33\x11\xf2\x7f\x52\x2f\x91\xcb\x3e\xb1\x5d\xfb\x51\xbe\x54\xe5\xb7\xa4\x2e\xdb\x12\xae\xf0\x99\x68\x39\x78\x23\x8b\x9b\x95\x44\xbb\xf0\x8d\x3a\x5a\xe3\x3f\x4e\x91\x73\x24\x71\x44\xd4\xb7\xc7\x10\xb4\x27\x57\x3e\x0a\x9e\xa2\xa7\x16\x7c\x95\xc7\x8b\x12\xbf\x38\x54\x36\x12\x8d\x5f\xd8\x87\x11\x3b\x5f\xc3\x8a\x4d\x96\xd8\x57\xc0\x6c\x8e\xf2\x12\xfd\x3d\x92\x60\x7b\x9b\x52\xf9\xa3\x8e\x28\xf9\x37\x99\xb6\x8e\xef\x64\x99\x7a\xd2\x13\xcf\x31\x9f\x9e\x1a\x5b\x0f\x7d\x1d\x86\x39\x2e\x24\x31\x36\x52\x16\x6a\x5b\xeb\x06\x19\x91\xd6\xb6\x8f\xca\x35\x14\x51\x6b\x12\x46\xd9\xa8\x4c\x7e\xbc\xe6\xfa\xc2\x56\x48\xa1\xdf\xdf\xbe\x62\x0a\xb8\xd4\xc5\x47\xe9\x43\x27\xc7\xfe\xe4\x2f\x07\x4d\x21\xa4\x10\xf9\x42\x9b\xa2\x57\x72\xaf\xe3\xf8\x10\x05\x33\xb8\x33\x5b\x10\x4b\x21\xd5\x58\x4a\x6f\x4c\xf2\x2f\xab\x55\x6d\x6c\xd3\x22\x1b\xe8\xdc\x72\x71\x5f\xaa\xb2\x72\x90\x09\x27\xe0\x75\x90\xc6\xd3\xb4\xc8\x9e\x92\xe9\x1d\xc6\x24\x4a\xd9\x54\xe0\xbd\xd2\x68\x93\x58\xfc\x77\x85\xaa\xb7\x44\xee\xef\xb3\x5e\xbc\x0b\xb3\xba\x87\xa5\x65\xdf\xbd\x3e\xef\x5d\xd6\xb8\x7c\x7b\xed\x17\x94\x92\x66\xa7\x42\xf9\x50\x64\x8e\x3e\x18\x68\x5f\x30\x6b\x94\xec\x22\x92\x74\x00\xe6\x0c\xde\xe6\x28\x2c\x42\x55\x66\xc2\xed\xdd\x0e\xf1\xce\x33\xcd\xab\x6c\x9f\x4e\x61\x41\xc0\x06\xe7\xfb\x18\x46\x77\x27\xc8\x69\x58\x41\x2f\x0f\xd8\x11\x12\x4d\x58\x35\x83\x6b\xe7\xb3\x2f\xed\x56\xec\x8b\xbb\x77\x1e\xea\x83\x77\xe6\xa5\xa3\x15\x86\xb6\x6b\x41\x50\xf0\x4b\x89\xe9\x94\x93\x14\x68\x8d\x5b\x1c\xed\x03\x19\xc6\x84\xb0\x7e\x25\xf5\x4c\x78\x63\x24\x08\xac\xae\x5c\xdb\x58\xcc\xe0\xf7\xc6\x08\x47\x53\x41\xcb\xce\x6a\x73\x22\x6d\x13\x2c\x8c\xb8\xb5\xc0\x4e\x14\x53\x42\xd9\x8a\xc3\x24\x93\x66\x92\x91\x3b\xc8\x16\xf1\x51\xcb\xbd\xd4\x52\xf9\x90\xca\xa7\x68\x0e\x5b\xb7\x8a\x9b\xe3\x7c\x46\x29\x60\xe4\x8a\x6f\xf5\xee\x59\xb8\x61\x36\x52\x41\x09\xbb\x58\x63\x92\xe9\xf4\x1e\xfb\xee\xde\xbf\x10\x8a\xa1\x8a\x35\xc2\x4b\x9e\x08\xb2\xe0\x00\x7c\x24\xb0\x94\x39\x26\x22\x37\x28\xb2\x6d\x82\x5f\xa4\xed\xbd\xdb\xf0\x33\x9d\x90\x30\x13\xfc\xcc\x11\xd8\x59\xbc\x9b\xd7\x64\x25\x12\xad\x57\x28\x4b\x91\x53\x2e\xe6\xd8\xd7\x1c\xb9\x51\x08\xa4\x87\x39\xee\xa7\xfd\xcd\xd7\xb8\x25\x6e\xa3\xa1\x46\xc6\x4d\x13\x2f\x6b\x9a\x1d\xbf\x79\xc3\xba\x92\x16\xee\xa5\xca\xe8\x80\x04\x5d\x0c\x4d\xc9\x47\x8e\x67\xcf\x52\x90\x7d\x69\x11\xc2\xa4\x1f\x20\x27\xdc\xc0\x7f\x64\x57\x58\x59\xb8\xa1\x4e\xb1\x5b\x24\x0a\x62\x5a\x83\xcc\x83\xc5\x52\x18\xfa\xc2\xd0\xfd\x05\xaf\x1e\xde\xa6\x29\x7f\x38\x64\x09\xb1\x7c\xac\x9e\x2b\xed\x25\x65\xd1\x1d\x87\xec\x58\x5b\x11\x90\xb5\xce\xfb\x08\xbe\x68\x7d\x93\x95\x58\x93\xa5\x62\x5d\xf2\x85\x74\x1b\x88\xe9\x7b\x1d\xd2\x76\x43\x11\x4c\xb0\x57\x51\xb5\xe3\xa5\x04\xb2\xf9\x2a\x1a\x23\x9f\xe8\x73\x28\x46\xfb\x17\xb2\xdb\x59\x7c\xae\x11\xee\xd4\x7a\x78\x96\x1d\x15\x29\x13\xbf\x29\xe0\x05\x1c\xb1\x4b\x05\x22\xea\x74\x84\x30\x72\xf8\xb5\x5a\xe4\x32\x25\x2b\x93\x84\xc4\x8d\x38\x34\xda\xda\x58\x09\xe9\x3b\xae\xad\xf3\x13\x53\x3e\x62\x3a\x7c\x0e\x3c\x47\x5e\x39\xf8\x2d\xaa\xdc\xc9\x32\xf7\x59\xa3\x3f\x3c\xf4\x29\x44\x24\x1e\x39\x9b\xaf\xe8\x7b\xf7\xca\x20\xae\xdd\xc5\x3d\x03\xe9\xfc\x89\x2a\xb5\xb5\x72\xee\x4f\x01\x0b\x24\x32\xe2\xb1\x36\xe2\x99\x53\x5c\x52\x6b\x3a\x13\xf1\xe8\x10\x06\x4e\x18\xcd\xa3\xa4\xe7\x08\x61\x9a\x2a\xc7\x13\x24\x49\xcb\x42\x76\x91\xe3\x21\x19\x36\xf4\x47\x7b\xbf\x17\x48\xf8\x47\x1f\xb5\x08\xba\x5b\x32\xf3\x6f\x7d\xbe\x85\x90\x99\xc1\x43\x12\x16\xd6\xea\x54\x32\xe8\xc3\x14\x5f\x44\xe2\xf6\x85\xcf\xcc\x9f\x24\x79\x61\x9a\x3b\x15\xdc\xcc\xee\xbd\x4b\x1e\x1a\x64\x90\x4b\x85\x20\xcc\xb2\xe2\xa4\x98\x44\x68\x96\xbb\x5d\x3b\x5e\x64\x38\x67\x50\x7a\x12\xe3\x33\x0b\x92\x07\x8f\x1c\x41\xd1\x3d\x6e\xbf\x19\x55\xf7\xb8\xbd\x60\x58\x50\x0a\x69\x1e\x91\xd7\x1d\x66\xfb\x8e\x5f\x44\x51\x52\xb0\x5b\x83\xbb\xc7\xed\x24\x1e\x42\x80\x35\x7e\xf5\xa7\x8f\x81\xef\x23\xca\x1f\xd8\x06\x07\x78\xfe\x5e\x90\x77\x5c\x75\x29\xe4\xcc\x17\x24\x5b\xe9\x65\x54\x8e\xfa\x81\x0b\xf8\xd5\x9c\x64\x34\x20\xc6\x6a\x0f\xf8\xef\x4a\x1a\xae\x6d\x95\x95\xb3\x93\xb4\xe4\x36\xac\xf1\xa9\x8c\x3f\x2d\x1d\xad\xb0\x80\x6b\x54\x20\x16\x0e\x0d\x88\xb2\xcc\xb9\x7f\xc2\x17\x1b\x4a\xed\xe1\x84\x5e\x2a\xaa\xf5\x0c\xd6\xc2\x48\x31\xcf\xb1\x51\x78\x8b\xae\x86\xd8\x9d\x12\x0f\xb0\xcf\xa2\x9a\x7b\x53\x87\x9e\xb7\xf8\xa7\x44\x26\x3c\xf8\xe1\xcd\x5e\xe8\x3c\xd7\x1b\x4f\x0d\xd1\xce\xf2\xf4\x1f\x77\xbb\xf1\xec\x6b\x29\x1c\x6e\xc4\x36\xa1\xa4\x87\x3b\xc6\x63\x89\xc5\xdb\x6b\xf8\xc5\xaf\xe1\x44\xa9\x29\x70\x89\x52\xd2\x0f\xb1\xc6\x74\x20\x5c\xe7\xa9\xf5\x15\xb1\x78\x63\x7f\x3f\x4a\x0a\x29\x87\x41\x42\xba\x0e\x08\xea\x4a\xf1\x1e\x8c\x89\x75\xa8\x52\x18\x8b\x66\xf0\xa5\x69\x53\x21\x31\xe8\x8c\x44\x36\x78\xa1\x30\x52\x6b\xe8\x61\x6c\xbf\x5f\xde\xbe\xb9\x7e\xf3\xcb\xf4\x4a\x7c\x5c\x70\x5c\x2d\x7e\x23\x8c\xaa\xdb\xfd\x44\x64\x5f\x52\x7e\x4b\x63\xa4\x11\x1f\x62\x9f\xff\x53\xd0\x5c\x16\xc0\x33\x5f\x1c\x21\x86\x3e\x0d\x25\x70\x01\x1f\xdf\x7b\x3a\xba\x1c\xd2\xbe\x26\xdd\x2a\x7f\x42\x86\x6e\x3c\x75\x64\xcc\x64\x43\x33\x2c\x0d\xa6\xe4\x59\x12\x83\x65\x2e\xd2\xde\xdc\xea\x6e\xe5\xf1\xe8\x3c\x0b\x85\x5e\xbe\x66\xe6\x43\xe7\xee\xfd\x06\x7e\xfb\x69\xb5\x56\x94\xf4\x37\x18\x6a\xcb\x5a\x59\x1f\x9a\x73\x87\x0a\x37\x1d\x70\xd6\xa1\x98\x48\x7b\x90\xc4\x29\x35\x6a\xbb\xd2\x55\x9e\x11\x79\x14\x29\xc3\x7b\xeb\x9b\xb5\xbe\x93\xe4\x8d\x3d\xcd\xe6\x4f\xe3\xb7\x34\x6a\x8a\x78\xfe\xc8\x56\x12\x5d\x1e\x03\x19\x97\xc7\xb5\x73\x3a\xaa\xfe\x54\x1f\x81\x92\x93\x63\xb1\x1e\xdc\xbc\x31\xa4\xbc\x3e\x6e\x68\xec\x0a\xc6\xc7\x70\xed\x57\x70\xe3\x84\xe5\xb2\x90\x2e\x91\x4b\xa5\x4d\x2f\x49\x51\xa5\x43\xb0\xce\x4b\x7c\xf2\x47\x9f\xf6\xeb\xe3\x64\xec\x3c\xb8\xa9\xd8\xd3\x95\x50\x4b\x24\x07\xd0\x43\xc0\xab\x1a\x63\x5d\x90\xb7\x91\xef\x7c\xeb\x1b\xc2\x35\x8c\x19\x5c\x13\x7a\xa9\x96\x53\x74\x81\x29\xb0\x49\xae\x97\x89\x95\x7f\xf6\x11\x90\xeb\xe5\x3b\xf9\x27\xd7\x7d\xfc\x82\x0e\xc7\x8d\x8a\x0a\xc5\x7e\x90\x62\xe8\xf8\x2a\xf0\x47\x4e\x5e\x7e\xfa\x71\x32\x29\x05\x16\xda\x6c\x87\xa8\xf1\x33\x4e\x25\xe8\xa7\xbf\xff\x07\x93\xf4\xff\x7f\xfa\xfb\x64\x9a\xc8\xf4\xeb\xaa\xaf\xa0\x1e\x46\x4f\x22\xe6\x47\x2f\x9f\xff\xf7\x23\xfd\x1b\xa7\x87\x7b\xa3\x49\x69\x74\x89\xc6\xc9\xde\x9c\x22\x5a\xc0\x96\xbd\xf2\x1d\x75\xef\xcd\x42\x4f\xdd\x37\x5a\x1b\x60\xb1\xf7\x7e\xd8\x26\x46\x93\x98\x69\x56\x38\xb2\x8c\xd2\x81\xae\x9c\x95\x19\x6f\xc4\x9d\x11\x6b\x69\x61\x5e\xc9\x3c\x1b\x6e\xcc\x32\x2b\xde\x1c\x18\x52\xdb\x49\xa6\xa0\xd6\xfe\x8e\x41\x50\x7b\x06\x3d\x48\x9b\xdb\xcd\x94\xfc\xf8\x5f\xa3\xb8\x1f\x1e\x66\x85\x54\xa1\xf9\x48\x5f\x44\x3a\xd2\xca\x60\x52\x63\xe8\xe0\x0f\x59\x9f\x99\x88\xed\xa1\x30\x8b\xc2\x87\xbd\x4e\xd1\x81\x6a\x72\x6f\x33\xe8\xa4\x0e\x10\x53\x1b\xfa\xcb\x5c\xb1\x18\x2c\xb9\x3d\x6a\x1d\x76\x4c\xcc\x5e\x2d\xae\x09\x5e\x73\x7e\x38\xa7\xb4\x5b\x85\x54\x79\x9c\xa4\x98\x02\x8f\x76\x4f\xef\x1e\x15\xb7\xda\x01\x43\x78\x5d\x80\x19\x28\x3d\xed\x0a\x00\x63\x6f\xdd\xbe\x61\xa1\x4c\x21\xe2\xe0\xdd\x94\xe0\x71\xf6\x83\xf0\x4d\x68\x51\xf9\x46\xef\xa1\x12\xdd\x04\x09\xb5\xde\x08\x25\x7a\x8d\xc6\xc8\x2c\xc3\xbe\x42\x13\x51\xd8\x7e\x32\xd4\xdc\x9e\x6a\x96\xc6\x58\xa1\x7d\x39\x66\xea\x46\x25\xd2\x26\x65\x35\xcf\x65\xdf\xb3\x6c\xbf\x2b\x3c\x37\x36\x5a\xfc\xab\x28\x0a\xed\x79\xe1\xa3\x24\xfe\x8c\xcc\x05\xdb\x96\x39\xc2\x5a\xfa\x7a\x02\x9d\xc3\x54\xb0\xa5\xf1\xd7\xe2\x31\x83\xf9\x16\x84\xda\x6a\x35\xf0\xca\x88\x69\x8d\x75\x41\x9c\x87\xb7\x9f\x23\x6e\xfc\x71\x59\x90\x3b\x1e\xdc\x77\x51\x19\xfd\x7f\x1e\x9e\x69\xee\xb7\x3c\xe8\x20\xf0\xdf\xd9\xc0\xf9\x99\x77\xee\xe1\x5b\x58\x30\x90\x79\x78\x4a\x5b\xad\x2d\x22\x77\xb0\x88\xd8\xd7\xf0\x20\x0d\x6b\x77\x89\x26\xf5\xaf\xc2\xdf\x07\xa9\x17\xcd\xe0\x85\x56\x6b\x32\xf7\x21\x25\x68\x50\x38\xdd\x01\x3f\xae\xb2\xfb\x5c\x8d\xb4\xea\x86\x8a\xa3\x0d\x6f\x71\xe0\x48\xee\xea\x8e\xd9\x3e\x7f\x6d\x44\x35\x87\x93\xfa\x6b\x35\x8f\xb1\x10\x62\xd0\x96\x5a\x59\x1c\xba\xf1\xb4\x47\x34\x97\xc0\xf6\x53\xdd\x30\x1e\x93\xda\x56\x92\x1c\xcb\x15\x75\x99\x6d\xe5\x5c\xe9\xff\x16\x8f\x47\xcd\x7e\x6d\x06\x2f\xc8\xc3\xf0\x15\x89\xf6\xef\xde\xa9\xb3\xcb\x09\x3f\x07\xa6\x19\x0a\xf9\x93\x86\xb2\x31\x8d\x8d\xfb\x8a\x6a\x2d\x8d\x56\x6c\x3b\x63\x95\xa2\xaf\xf9\x1c\xb2\xbd\xab\x66\x09\xfc\x16\x96\x74\x53\x94\xc3\xb8\x5f\x5e\xfd\xf7\xfb\x5f\x26\xa7\xcd\x3c\xfb\xb8\x9c\x39\x9b\x2f\x13\x8b\xc2\xa4\x2b\xe2\x2c\x1a\xdc\xba\xa7\xd6\xab\xb6\x61\x45\x6d\x70\xbb\x5d\xb8\xb8\x7d\x51\xbe\x3e\x30\x19\x09\xbd\x89\x94\x7d\xaf\xf4\xad\x3d\xd2\x89\xde\x88\x48\xab\xdd\xb5\xbf\xd5\x39\xf0\xa7\x51\x5e\x1e\xb8\x5a\x14\x24\xf2\x0c\x7e\x66\x0a\x9a\xbf\xc4\xc1\x15\x66\x02\x76\x2c\x01\xc3\x6f\x49\x8f\xa7\xa1\x7d\x71\x34\x5e\x74\x3e\xee\x7d\xe0\xde\xc3\xaf\xa3\xdf\x7c\x1d\x7e\xc9\xf7\xe4\xd3\x93\xff\x09\x00\x00\xff\xff\xf1\xc2\x73\x19\x1d\x4d\x00\x00") +var _wski18nResourcesEn_usAllJson = []byte("\x1f\x8b\x08\x00\x00\x00\x00\x00\x00\xff\xcc\x3c\xfd\x6f\x1b\xb7\x92\xbf\xe7\xaf\x18\x14\x0f\x48\x0b\xd8\x72\xfb\x0e\x07\x1c\x8c\xcb\x01\xbe\xc4\xe9\xf3\x6b\x12\x1b\xb6\xd3\xa2\x97\x04\x1b\x6a\x77\x24\xf1\x79\x97\xdc\x92\x5c\x29\xaa\xa1\xff\xfd\x30\x43\x72\x77\x25\x6b\x3f\xa4\xa4\xb8\xcb\x2f\x91\xb4\xe4\x7c\x71\x38\xdf\xeb\x0f\xcf\x00\x1e\x9f\x01\x00\x7c\x27\xb3\xef\xce\xe1\xbb\xc2\xce\x93\xd2\xe0\x4c\x7e\x49\xd0\x18\x6d\xbe\x3b\xf1\x4f\x9d\x11\xca\xe6\xc2\x49\xad\x68\xd9\x25\x3f\x7b\x06\xb0\x39\xe9\x81\x20\xd5\x4c\x77\x00\xb8\xa2\x47\x43\xfb\x6d\x95\xa6\x68\x6d\x07\x88\xbb\xf0\x74\x08\xca\x4a\x18\x25\xd5\xbc\x03\xca\x6f\xe1\x69\x27\x94\xb4\xc8\x92\x0c\x6d\x9a\xe4\x5a\xcd\x13\x83\xa5\x36\xae\x03\xd6\x2d\x3f\xb4\xa0\x15\x64\x58\xe6\x7a\x8d\x19\xa0\x72\xd2\x49\xb4\xf0\xbd\x9c\xe0\xe4\x04\x6e\x44\xfa\x20\xe6\x68\x4f\xe0\x22\xa5\x7d\xf6\x04\xee\x8d\x9c\xcf\xd1\xd8\x13\xb8\xad\x72\x7a\x82\x2e\x9d\xfc\x00\xc2\xc2\x0a\xf3\x9c\xfe\x37\x98\xa2\x72\xbc\x63\xc9\xd8\x2c\x48\x05\x6e\x81\x60\x4b\x4c\xe5\x4c\x62\x06\x4a\x14\x68\x4b\x91\xe2\x64\x34\x2f\x5a\x77\x71\x72\xbf\x40\xb8\x2e\x51\xfd\xb6\x90\xf6\x01\x5e\x31\x33\x05\x91\x70\xaf\x75\xfe\x51\x7d\x54\xf7\x1a\xa6\x38\x97\x0a\x56\xda\x3c\x48\x35\x87\x95\x74\x0b\x58\xd9\x07\xcf\xf8\x09\x98\xca\x13\xf8\xbc\xfe\xed\x39\xa4\xba\x28\x84\xca\xce\x09\xc0\x47\xf7\xb7\x66\x39\x43\x5c\x48\x0b\x2b\x99\xe7\x41\x76\x2d\xfc\xc2\x5a\x74\xb6\xc5\xab\x54\x50\x08\x25\x67\x68\xdd\x64\x2d\x8a\x1c\xb4\x69\xfd\x50\xe4\x1f\xd5\xd5\x0c\xd2\xca\x18\x22\x39\x93\x06\x53\xa7\xcd\x1a\x32\x8d\x56\x39\x58\x88\x25\x82\x50\xeb\x7a\x0b\xcc\x64\x8e\x27\x0d\x39\x50\x1a\xa9\x9c\x05\x47\x24\x2d\x30\x2f\xa1\x40\x6b\xc5\x1c\x27\x9e\x50\x84\x42\x5b\xc7\xec\x68\x05\x2b\xb1\xb6\xa0\x67\x50\x59\x96\x43\x0d\xc4\xe9\xc8\x89\x50\xd9\x99\x36\x50\xa9\x2e\xce\x84\x41\x16\xca\x96\x48\x5a\x5f\xe0\xb4\x80\x52\xb8\xc5\x99\xd3\x67\x5b\x8c\x8f\x5b\x05\xa7\x59\xfd\x20\xab\xcf\x72\x0f\x80\x48\xe1\xfe\x5f\x47\x52\x31\xb8\xbc\x97\x9c\x8f\xea\xa2\x52\x6e\x41\xd7\x26\x65\x75\x3c\xff\xa8\x1a\xd8\x06\x45\x66\x21\x35\x98\xd1\x02\x91\x5b\x98\x19\x5d\xc0\xdf\xfe\x71\xfd\xf6\xf2\x6c\xb2\xb2\x0f\xa5\xd1\xa5\x85\xe9\x1a\x32\x9c\x89\x2a\x77\x1f\xd5\xf5\x12\xcd\xca\x48\x87\xf1\x27\x48\xb5\x9a\xc9\x39\x1f\x3a\x5d\xd5\x97\x6f\xae\xce\x3f\x2a\x80\x2d\x49\x9e\x86\x45\xff\xd9\x5a\xfc\x5f\x3d\x02\xb8\x36\x41\x3d\xd7\x20\xf2\x1c\xdc\xc2\x60\x0f\x70\x51\xca\x05\x69\xd0\x3f\xae\xef\xee\xe9\x6b\xe5\x16\xf0\xcb\xe5\xef\x70\x7a\x5a\xdf\x62\x78\x77\xf1\xf6\xf2\xee\xe6\xe2\xe5\x65\x27\xd6\x11\xf7\xdc\x2e\xb4\x71\xfd\x46\xeb\xc6\xe8\xa5\xcc\xd0\x82\x00\x5b\x15\x85\x30\x24\x65\x5a\x4f\x3a\xfd\x44\x53\xa7\x48\x4a\x1e\xad\xdb\x59\x3c\x6b\xcc\x60\x2a\x2c\x66\xc4\x72\xa4\xb1\x75\xb6\xf0\xfb\xc5\xdb\x37\x63\xec\x52\xa0\xb7\xdb\x30\x5d\x80\xd3\x3a\x07\x8b\x8e\xee\x17\xdf\xcd\x20\xd5\xb5\xae\x0c\xe8\x12\xd5\x8a\xe9\x2d\x83\x9d\x0d\xd7\x52\x6c\x5f\xf6\xf1\xb4\x2c\xd1\x58\xc2\xdd\x25\x3c\xa9\x1c\xdb\xb9\xb0\x0e\x54\x55\x4c\xd1\x90\xec\xea\x03\x1f\x8d\xcb\xae\x55\xda\xcf\xb7\xd3\x40\x8b\x3c\xb3\xcd\xe1\xd4\xcc\x4e\xd1\xad\x10\x15\xa4\xb9\x24\xb1\x0b\x95\x81\x45\xb3\x44\x33\xda\x29\x8c\xa7\xa1\x75\xbc\x84\x27\xaa\x02\xff\xb0\xa5\x3a\xdd\x47\x41\xfb\x74\x49\xf0\x45\xde\x86\x47\x47\x14\x97\xb3\xea\x90\x5d\x78\x25\x67\x33\x64\x8b\x1e\x2d\xae\xa9\x14\xf9\x6e\x26\xe7\x7c\xdb\x08\xd1\x4f\x4f\x7f\x19\x69\xc1\x7a\x97\xb6\xad\xd7\xf1\x30\x4e\x4b\xa3\xff\x85\xa9\xa3\xfb\x0e\x37\xb7\xd7\xff\xbc\x7c\x79\x3f\x5a\x4f\xa2\xa8\x3b\xce\xe9\x7d\xa7\x9f\x61\x63\xe9\x15\x62\xac\x3e\x8c\xc5\x65\xb0\xd0\x4b\xb4\x4f\x71\xae\x16\x32\x5d\xc0\x0a\x0d\x36\x41\x11\xd3\x41\xb7\x66\x4b\x13\x76\xed\xc5\x56\x9c\x91\x61\x8e\x8e\x0e\x7b\x3f\x53\x5b\xc0\xbc\x3b\x37\x95\x3a\xff\x7f\xe7\xde\xf6\x43\xda\xa7\x0d\xf0\xbd\x56\xf9\x9a\xe3\x2b\x0b\x33\x6d\x5a\xe2\xe1\xe8\x8f\x15\xac\xd0\x19\xfe\x30\x5a\x6f\xf0\x4b\x8f\x1f\xb8\xe4\x87\x10\x28\xd9\x12\x6e\x2d\xf2\xb1\x4a\x33\x02\x91\xa5\xe3\x12\x73\xcc\xfa\x31\x92\xb5\xd9\x52\x92\x59\xa5\x38\x6e\xf6\x36\xa2\x23\x1e\xa3\x5d\x14\x80\x7a\x3a\x76\xb4\xc0\xff\xd8\x21\xf4\xd6\xa1\xfa\x75\x98\x9d\x1e\xe0\x74\x67\xb9\x98\x27\xa2\x94\x09\xb9\xf7\x0e\xfe\xbd\x7f\xba\xb8\xb9\x82\xcf\xe4\xff\x3f\x8f\x84\xd8\xef\x88\x5a\x40\x7f\xbd\xbc\xbd\xbb\xba\x7e\x37\x0a\x6e\xe5\x16\xc9\x03\x76\x5d\x6e\x7a\xac\x8d\xfc\x93\x7f\x80\xcf\xbf\x5c\xfe\x3e\x06\x68\x8a\xc6\x25\x74\x3a\x1d\x50\x49\xbe\x64\xbd\xe9\xca\x4e\x68\x31\x1f\xe5\x18\xc0\x1c\x8a\x75\x40\x6d\x07\x75\xdf\xc7\x48\x4f\xda\xdd\xd0\x70\xe0\xb2\x78\xa9\xe4\xb9\x5e\x25\x01\x46\x57\xf6\xc9\x8b\xa0\x5e\x34\x0c\xb5\xb9\xbe\x7d\x72\xa9\x93\x86\xda\x0f\x8e\x00\x5d\x1a\x5c\x4a\x5c\x75\xc0\xb5\x0b\x26\x34\x02\x3d\xdb\x72\xd4\x65\x2e\xd4\x08\x0c\x0f\xb8\x1e\x7d\xa4\x0f\xb8\x1e\x4b\xb8\x97\x74\x30\x04\xbd\x82\x8e\x46\xa2\x4e\xa7\x1d\x39\x06\x28\x84\x79\xc0\x2c\x9a\x92\x51\xa2\x62\x38\x09\x5d\xfa\x2e\x66\x02\x2a\x5e\x32\x0c\x31\x5a\x87\x81\x53\xdd\x72\x4e\x23\xc0\xd6\x89\x40\x07\xdc\xe6\xf9\x68\xa6\x07\x28\xf4\x71\x41\x8e\xd6\x46\x69\x8f\x00\x6d\x9d\x91\x9d\x90\xfd\xd1\x55\x16\xc9\x79\xcd\xa4\xc2\x8c\xac\xb2\x93\x45\x1d\x2e\x8f\xc0\xe0\x4c\xb7\x10\xf8\x19\xe8\xca\x95\xd5\x18\x62\xbd\xba\x2d\xd1\x4c\xb5\xed\x02\x19\x9e\x1e\x0a\xb4\x14\x46\x14\x9d\x02\x36\xa2\x40\x87\x06\x96\x22\xaf\x90\xbd\x37\x19\x53\xf8\xf5\xe2\xcd\xfb\xcb\xcf\xe4\xdc\x0b\x71\x20\xaa\xbe\xdb\xf8\xf9\xf5\xd5\x9b\xcb\xcf\x94\xe6\x3a\x21\x39\x40\xde\x47\xc1\x3f\xef\xae\xdf\x0d\xa3\x66\xab\x9a\x14\xd2\x52\x2c\xce\xfe\xa2\xdb\x5d\x90\x23\xa6\x15\x4d\xee\x0e\x64\x0b\xa4\x05\xa5\x63\xd6\x5d\x19\xcc\x26\x1f\xfb\xce\x7d\x07\xa3\xcf\x94\x7b\x30\x92\xcf\xe3\x64\xfa\xab\xf0\x0c\x5d\x37\xc2\xd4\xe4\xe6\x47\xa1\x0a\xac\xf4\x55\x45\x77\xf9\xf9\xf0\xf8\x38\xa1\xcf\x9b\xcd\xa7\x13\x1f\x18\x3d\x3e\x4e\xac\xae\x4c\x8a\x9b\xcd\x28\x9c\xfe\xc0\x86\x70\x72\x01\x22\x9c\x95\x45\x77\x1c\xae\x5a\x3c\x43\xd8\xb6\xe4\x48\x2c\xd6\x3f\x1c\xcf\x67\x29\xe7\xab\x44\x70\x41\x38\x71\xfa\x01\xd5\x20\xcb\xb4\x03\xfc\x0e\xe0\x1d\xc7\x31\x5f\xa9\x42\x18\xbb\x10\x79\x92\xeb\x54\xe4\x9d\x69\x52\x58\xd5\x8a\x6c\x83\x29\x0c\x11\x2f\xef\x0e\xd7\x73\x24\x42\x85\x8e\xb2\x83\xa3\x51\x4a\xe5\xd0\x28\x74\x20\x1c\xb1\x5b\x99\x7c\x80\xd7\x26\x6e\x48\x52\xa1\x52\xcc\xf3\x4e\xaf\x7d\xfd\xcb\x04\x5e\xfa\x35\x4d\xc1\x88\xf3\xa0\x91\x08\x66\x42\x76\x43\x6f\x15\xa4\x33\x99\x85\xbb\x58\x94\x39\x3a\x04\x5b\xd1\x91\xce\xaa\x3c\x5f\x4f\xe0\xb6\x52\xf0\xf9\x69\xc6\xf5\x99\x13\x04\xce\x58\xc9\x36\x3a\x29\xf2\x7c\xdd\xa4\xa7\x3e\x13\x19\x4b\xa9\xaf\x96\x25\xd6\x09\x57\x75\x45\x8b\xa7\xa7\xa7\xa7\x2f\x5e\xbc\x78\xb1\xbf\xa8\x7e\xc7\x5b\x81\x16\xd0\xc2\x51\x58\xb9\x37\x82\xd9\x18\x11\x45\xd1\x64\x10\x1a\x2a\x5e\x38\xfd\x4a\x76\xfc\x59\xb7\xf7\x8e\x47\xd2\x7b\xde\xef\xdb\x21\x6b\xef\x89\x8f\xc6\x37\x24\xbf\x2d\x94\x47\x48\x30\xf4\x3a\x12\x2e\x62\xb1\xb7\x26\x2b\x97\x08\x97\x50\xbc\xd5\x81\xf4\xf1\x71\x92\x16\xd9\x66\x13\x4a\x5f\x8f\x8f\x13\xda\xe8\xd6\x25\x6e\x36\x6c\x29\x69\xef\x66\xf3\x69\x32\xe9\xc5\xcd\x41\xf2\x3a\x89\xfa\x3c\xd0\x47\x7b\x7c\xa4\x90\x3d\x20\x20\x22\x37\x9b\x4f\xb0\x10\x16\xa6\x88\x6a\x8b\xe1\xfa\x86\x8c\xc7\xde\xdd\x78\x7b\x15\x9f\xc3\x5e\x02\x26\x93\x9e\x92\x65\x40\xd1\x54\x9f\xbf\x1d\x8b\x0d\xcc\x31\x4c\xc6\xd5\xdd\x6c\xbe\x6f\x56\xec\x65\xb4\x97\xcf\x0c\x4b\x54\x19\xaa\xf4\x10\x71\x36\x9b\x8e\xc7\xd3\x5c\x91\x4e\x99\xbe\xda\x8b\xe6\x6b\x14\x67\x3f\x15\x64\x18\x2a\xd3\x15\x97\xbd\xda\xaa\x39\xef\x67\xfd\xff\xd0\x47\x44\x7e\x0e\xd3\x93\xaf\x3b\xc1\xa7\x66\xee\xdb\x9c\xe1\xc8\x9b\xd1\x45\x49\xff\x39\xbe\xdf\xe9\x1e\x1c\x73\x92\x7d\x54\x85\x0a\xc1\xb1\x3e\x87\x29\xf2\x1e\xa0\xae\x40\xf4\xd1\x02\x59\x65\xe8\x24\x63\x8d\xb3\xe5\x11\xff\x3a\x7d\x8b\x3c\xce\x74\xa5\xb2\x24\xd0\x1b\x2c\x55\xa7\x02\x84\xaa\xfa\x5e\x0b\x19\x4a\xf7\x3c\x80\x40\x74\xb5\x0a\xf7\xb1\xb9\xbe\x5b\xc4\x65\x27\xe5\x3f\x13\x04\x61\x99\x17\x6e\x8f\x8f\x0d\x0b\x42\x4d\x2d\x09\x6d\xa3\xae\xce\x9b\x7f\xca\xc9\x04\xb4\xea\x7d\x06\xb9\x8e\x91\x9d\x70\x1f\xb6\x09\xb7\xea\x63\x23\x3a\x4c\xbd\x23\x20\x01\xd1\x6a\x4f\xb4\xbb\x9a\x7e\x78\x20\x68\xbf\xf1\x7d\xb7\xa1\x49\x8b\xcb\xdb\xdb\xeb\xdb\xbb\x0e\xba\x5f\xec\xfe\x03\xbf\x1c\x9e\x3c\x78\xf1\xa2\xc7\xfd\x18\xb3\x7d\xd1\x1e\x94\x5e\xa9\x84\x22\x85\xe1\xab\x4e\xab\x48\x54\x61\xd7\x04\x5a\xc5\x71\xee\x39\xd8\xaa\xf4\x25\xfa\x33\x2e\x2b\x4f\xec\xda\x3a\x2c\x60\x2a\x55\x26\xd5\xdc\x82\x36\x30\x97\x6e\x51\x4d\x27\xa9\x2e\xea\xf6\x5e\xbf\xbf\x34\x26\xfa\xcc\xd4\xa0\x70\x5d\x64\xf2\x60\x11\xf0\x92\x2d\xb5\xe4\xf1\x12\x9e\x48\x8a\xb3\x18\xe7\xf4\x10\x8d\xd9\x6c\xb8\x2f\xe0\x9f\xa5\x3a\xf3\x0f\xe8\xc3\x40\x36\xd3\x22\xc9\xdf\x95\x5e\x92\xb2\x27\x37\xe5\x2f\x22\x69\x86\x98\x25\x52\x2d\xf5\x43\x17\x41\xaf\xd9\x6c\x91\xb9\xf0\xcb\xf8\x42\xd2\x36\x58\x2d\xb0\xd5\x29\x73\x7e\xae\x28\x3c\xfa\x6b\xa8\x7d\xc0\x75\x5d\x43\xa1\x78\x57\x38\x6d\xfa\xea\x43\xf5\x1a\x2e\x37\x7c\x88\xc2\xfc\x44\xfa\x18\xe0\x0c\xe2\x8c\xa5\xd4\x44\x69\xe7\x8d\x5d\x07\xc2\xb7\xed\x9a\x2b\xdb\x6a\x5e\x4d\xf9\x2e\x17\x3d\xdb\x11\xf5\x10\x52\x8e\xde\x0b\x69\x0b\xe1\xd2\xae\xf0\x9d\x18\xac\xd5\x83\x36\x64\x8c\x22\x8b\xf6\x54\xaa\xdd\xe2\xbe\x7f\x1e\x68\xe0\xf9\x24\x26\x93\x91\xf0\xb1\xb2\x79\xa3\x45\x45\x0b\xc8\x56\x2d\xd9\x3f\x8d\x6c\xf4\x33\x11\xf2\x7f\x52\x2f\x91\xcb\x2e\xb1\x5d\xf9\xa7\x3c\x54\xe5\x8f\xa4\x2e\xdb\x12\xae\xf0\x99\x68\xd9\x3b\x91\xc5\xcd\x4a\xa2\x5d\xf8\x46\x1d\xed\xf1\x1f\xc7\xc8\x39\x92\x38\x20\xea\xdb\x43\x08\xda\x91\x2b\x5f\x05\x4f\xd1\x73\x0b\xbe\xca\xe3\x45\x89\x5f\x1c\x2a\x1b\x89\xc6\x2f\xec\xc3\x88\x9d\xaf\x61\xc5\x26\x73\xec\x2a\x60\x36\x57\x79\x8e\x7e\x8e\x24\xd8\xde\xa6\x54\xfe\xa4\x23\x4a\xfe\x4d\xa6\xad\xeb\x3b\x5a\xa6\x9e\xf4\xc4\x73\xcc\xb7\xa7\xc6\xd6\x41\xdf\x16\xc3\x1c\x17\x92\x18\x1b\x29\x0b\xb5\xae\x75\x83\x8c\x48\xeb\xd8\x07\xe5\x1a\x8a\xa8\x35\x09\x83\x6c\x54\x26\x3f\x5c\x73\x7d\x61\x2b\xa4\xd0\xef\x6f\xdf\x30\x05\x5c\xea\xe2\xab\xf4\x61\x2b\xc7\xfe\xe4\x87\x83\xc6\x10\x52\x88\x7c\xa6\x4d\xd1\x29\xb9\xb7\xf1\x79\x1f\x05\x13\xb8\x37\x6b\x10\x73\x21\xd5\x50\x4a\x6f\x4c\xf2\x2f\xab\x55\x6d\x6c\xd3\x22\xeb\xe9\xdc\x72\x71\x5f\xaa\xb2\x72\x90\x09\x27\xe0\x6d\x90\xc6\xf3\xb4\xc8\x9e\x93\xe9\xed\xc7\x24\x4a\xd9\x54\xe0\xbd\xd2\x68\x93\x58\xfc\xa3\x42\xd5\x59\x22\xf7\xf3\xac\x67\x77\x61\xd5\xf6\x65\x69\xd9\x77\xaf\xcf\x3b\xc3\x1a\x17\x37\x57\x7e\x43\x29\x69\x75\x2a\x94\x0f\x45\xa6\xe8\x83\x81\xf6\x80\x59\xa3\x64\x67\x91\xa4\x3d\x30\x27\x70\x93\xa3\xb0\x08\x55\x99\x09\xb7\x33\x1d\xe2\x9d\x67\x9a\x57\xd9\x2e\x9d\xc2\x82\x80\x15\x4e\x77\x31\x0c\x9e\x4e\x90\x53\xbf\x82\x5e\xec\xb1\x23\x24\x9a\xb0\x6b\x02\x57\xce\x67\x5f\xda\x2d\xd8\x17\x6f\xcf\x3c\xd4\x17\xef\xc4\x4b\x47\x2b\x0c\x6d\xd7\x82\xa0\xe0\x97\x12\xd3\x31\x37\x29\xd0\x1a\x8f\x38\xda\x07\x32\x8c\x09\x61\xfd\x4a\xea\x99\xf0\xc6\x48\x10\x58\x5d\xb9\xb6\xb1\x98\xc0\x6f\x8d\x11\x8e\xa6\x82\xb6\x9d\xd4\xe6\x44\xda\x26\x58\x18\x70\x6b\x81\x9d\x28\xa6\x84\xb2\x15\x87\x49\x26\xcd\x28\x23\xb7\x97\x2d\xe2\xa3\x96\x7b\xa9\xa5\xf2\x21\x95\x4f\xd1\x1c\xb6\xa6\x8a\x9b\xeb\x7c\x42\x29\x60\xe4\x8a\xa7\x7a\x77\x2c\x5c\x3f\x1b\xa9\xa0\x84\x5d\x2c\x31\xc9\x74\xfa\x80\x5d\xb3\xf7\x2f\x85\x62\xa8\x62\x89\xf0\x8a\x17\x82\x2c\x38\x00\x1f\x08\x2c\x65\x8e\x89\xc8\x0d\x8a\x6c\x9d\xe0\x17\x69\x3b\x67\x1b\x5e\xd3\x0d\x09\x2b\xc1\xaf\x1c\x80\x9d\xc5\xd9\xbc\x26\x2b\x91\x68\xbd\x42\x59\x8a\x9c\x72\x31\xc5\xae\xe6\xc8\xb5\x42\x20\x3d\xcc\x71\x37\xed\x6f\xbe\xc6\x23\x71\x2b\x0d\x35\x32\x6e\x9a\x78\x59\xd3\xea\xf8\xcd\x1b\xd6\x85\xb4\xf0\x20\x55\x46\x17\x24\xe8\x62\x68\x4a\x3e\x71\x3c\x3b\x96\x82\xec\x4b\x8b\x10\x26\x7d\x0f\x39\x61\x02\xff\x89\x5d\x61\x65\xe1\x86\x3a\xc5\x6e\x91\x28\x88\x69\x0d\x32\x0f\x16\x4b\x61\xe8\x0b\x43\xf7\x03\x5e\x1d\xbc\x8d\x53\xfe\x70\xc9\x12\x62\xf9\x50\x3d\x57\xda\x4b\xca\xa2\x3b\x0c\xd9\xa1\xb6\x22\x20\x6b\xdd\xf7\x01\x7c\xd1\xfa\x26\x0b\xb1\x24\x4b\xc5\xba\xe4\x0b\xe9\x36\x10\xd3\xf5\x76\x48\xdb\x0d\x45\x30\xc1\x5e\x45\xd5\x8e\x43\x09\x64\xf3\x55\x34\x46\x3e\xd1\xe7\x50\x8c\xce\x2f\x64\xb7\x93\xf8\xba\x46\x98\xa9\xf5\xf0\x2c\x3b\x2a\x52\x26\x7e\xa7\x80\x37\x70\xc4\x2e\x15\x88\xa8\xd3\x11\xc2\xc0\xe5\xd7\x6a\x96\xcb\x94\xac\x4c\x12\x12\x37\xe2\xd0\x68\x6b\x63\x25\xa4\xeb\xba\xb6\xee\x4f\x4c\xf9\x88\xe9\xf0\x39\xf0\x1c\x79\xe5\xe0\xb7\xa8\x72\x27\xcb\xdc\x67\x8d\xfe\xf2\xd0\xa7\x10\x91\x78\xe4\x6c\xbe\xa2\xef\xdd\x29\x83\xb8\x76\x17\xf7\x04\xa4\xf3\x37\xaa\xd4\xd6\xca\xa9\xbf\x05\x2c\x90\xc8\x88\xc7\xda\x88\x67\x4a\x71\x49\xad\xe9\x4c\xc4\x93\x4b\x18\x38\x61\x34\x4f\x92\x9e\x03\x84\x69\xaa\x1c\x8f\x90\x24\x6d\x0b\xd9\x45\x8e\xfb\x64\xd8\xd0\x1f\xed\xfd\x4e\x20\xe1\x5f\xfa\xa8\x45\xb0\x7d\x24\x13\xff\xae\xcf\xb7\x10\x32\x33\xb8\x4f\xc2\xc2\x5a\x9d\x4a\x06\xbd\x9f\xe2\xb3\x48\xdc\xae\xf0\x99\xf9\xa3\x24\x2f\x4c\x33\x53\xc1\xcd\xec\xce\x59\xf2\xd0\x20\x83\x5c\x2a\x04\x61\xe6\x15\x27\xc5\x24\x42\x33\xdf\x6c\xda\xf1\x22\xc3\x39\x81\xd2\x93\x18\x5f\xb3\x20\x79\xf0\x93\x03\x28\x7a\xc0\xf5\x37\xa3\xea\x01\xd7\x67\x0c\x0b\x4a\x21\xcd\x13\xf2\xb6\x1f\xb3\x7d\xc7\x2f\xa2\x28\x29\xd8\xad\xc1\x3d\xe0\x7a\x14\x0f\x21\xc0\x1a\x1e\xfd\xe9\x62\xe0\xfb\x88\xf2\x07\xb6\xc1\x01\x9e\x9f\x0b\xf2\x8e\xab\x2e\x85\x9c\xf8\x82\x64\x2b\xbd\x8c\xca\x51\xbf\xe0\x02\x7e\x37\x27\x19\x0d\x88\xa1\xda\x03\xfe\x51\x49\xc3\xb5\xad\xb2\x72\x76\x94\x96\xdc\x86\x3d\x3e\x95\xf1\xb7\x65\x4b\x2b\x2c\xe0\x12\x15\x88\x99\x43\x03\xa2\x2c\x73\xee\x9f\xf0\x60\x43\xa9\x3d\x9c\xd0\x4b\x45\xb5\x9c\xc0\x52\x18\x29\xa6\x39\x36\x0a\x6f\xd1\xd5\x10\xb7\x97\xc4\x0b\xec\xb3\xa8\x66\x6e\x6a\xdf\xeb\x2d\xfe\x55\x22\x13\x5e\xf8\xe1\xc3\x9e\xe9\x3c\xd7\x2b\x4f\x0d\xd1\xce\xf2\xf4\x1f\x37\x9b\xe1\xec\x6b\x2e\x1c\xae\xc4\x3a\xa1\xa4\x87\x3b\xc6\x43\x89\xc5\xcd\x15\xfc\xec\xf7\x70\xa2\xd4\x14\xb8\x44\x29\xe9\x87\x58\x63\xda\x13\xae\xf3\xd2\x7a\x44\x2c\x4e\xec\xef\x46\x49\x21\xe5\x30\x48\x48\x97\x01\x41\x5d\x29\xde\x81\x31\xb2\x0e\x55\x0a\x63\xd1\xf4\xbe\x69\xda\x54\x48\x0c\x3a\x23\x91\x0d\x5e\x28\x8c\xd4\x1a\xba\x1f\xdb\x6f\x17\xb7\xef\xae\xde\xfd\x3c\xbe\x12\x1f\x37\x1c\x56\x8b\x5f\x09\xa3\xea\x76\x3f\x11\xd9\x95\x94\xdf\xd2\x33\xd2\x88\x0f\xb1\xcf\xff\x29\x68\x2e\x0b\xe0\xdc\x17\x47\x88\xa1\x4f\x7d\x09\x5c\xc0\xc7\x73\x4f\x07\x97\x43\xda\x63\xd2\xad\xf2\x27\x64\xe8\x86\x53\x47\xc6\x4c\x36\x34\xc3\xd2\x60\x4a\x9e\x25\x31\x58\xe6\x22\xed\xcc\xad\xee\x17\x1e\x8f\xce\xb3\x50\xe8\xe5\x31\x33\x1f\x3a\x6f\xcf\x37\xf0\xbb\x9f\x56\x6b\x45\x49\x7f\x83\xa1\xb6\xac\x95\xf5\xa1\x39\x77\xa8\x70\xb5\x05\xce\x3a\x14\x23\x69\x0f\x92\x38\xa6\x46\x6d\x17\xba\xca\x33\x22\x8f\x22\x65\x78\x6f\x7d\xb3\xd6\x77\x92\xbc\xb1\xa7\xd5\xfc\x69\x78\x4a\xa3\xa6\x88\xd7\x0f\x1c\x25\xd1\xe5\x31\x90\x71\x79\x5a\x3b\xa7\xab\xea\x6f\xf5\x01\x28\x39\x39\x16\xcb\xde\xc3\x1b\x42\xca\xfb\xe3\x81\xc6\xae\x60\x7c\x19\xae\xfd\x16\xdc\x30\x61\xb9\x2c\xa4\x4b\xe4\x5c\x69\xd3\x49\x52\x54\xe9\x10\xac\xf3\x16\x9f\xfc\xd1\xa7\xdd\xfa\x38\x19\x3b\x0f\x6e\x2c\xf6\x74\x21\xd4\x1c\xc9\x01\x74\x10\xf0\xa6\xc6\x58\x17\xe4\x6d\xe4\x3b\x5f\xfb\x86\x70\x0d\x63\x02\x57\x84\x5e\xaa\xf9\x18\x5d\x60\x0a\x6c\x92\xeb\x79\x62\xe5\x9f\x5d\x04\xe4\x7a\x7e\x27\xff\xe4\xba\x8f\xdf\xb0\xc5\x71\xa3\xa2\x42\xb1\x1f\xa4\x18\x3a\xbe\x15\xf8\x23\x27\x2f\x3f\xfd\x38\x9a\x94\x02\x0b\x6d\xd6\x7d\xd4\xf8\x15\xc7\x12\xf4\xd3\xdf\xff\x83\x49\xfa\xf7\x9f\xfe\x3e\x9a\x26\x32\xfd\xba\xea\x2a\xa8\x87\xa7\x47\x11\xf3\xa3\x97\xcf\xbf\xfd\x48\xff\x86\xe9\xe1\xde\x68\x52\x1a\x5d\xa2\x71\xb2\x33\xa7\x88\x16\xb0\x65\xaf\x7c\x47\xdd\x7b\xb3\xd0\x53\xf7\x8d\xd6\x06\x58\xec\xbd\xef\xb7\x89\xd1\x24\x66\x9a\x15\x8e\x2c\xa3\x74\xa0\x2b\x67\x65\xc6\x07\x71\x6f\xc4\x52\x5a\x98\x56\x32\xcf\xfa\x1b\xb3\xcc\x8a\x37\x07\x86\xd4\x76\x94\x29\xa8\xb5\x7f\xcb\x20\xa8\x1d\x83\x1e\xa4\xcd\xed\x66\x4a\x7e\xfc\xaf\x51\xdc\x8f\x8f\x93\x42\xaa\xd0\x7c\xa4\x2f\x22\x1d\x68\x65\x30\xa9\x31\x74\xf0\x97\xac\xcb\x4c\xc4\xf6\x50\x58\x45\xe1\xc3\x4e\xa7\x68\x4f\x35\xb9\xb3\x19\x74\x54\x07\x88\xa9\x0d\xfd\x65\xae\x58\xf4\x96\xdc\x9e\xb4\x0e\xb7\x4c\xcc\x4e\x2d\xae\x09\x5e\x73\x7e\x71\x4e\x69\xb7\x08\xa9\xf2\x30\x49\x31\x05\x1e\xec\x9e\xde\x3f\x29\x6e\xb5\x03\x86\xf0\x76\x01\x66\xa0\xf4\xb8\x11\x00\xc6\xde\x9a\xbe\x61\xa1\x8c\x21\x62\xef\x6c\x4a\xf0\x38\xbb\x41\xf8\x2a\xb4\xa8\x7c\xa3\x77\x5f\x89\x6e\x84\x84\x5a\xef\x08\x25\x7a\x89\xc6\xc8\x2c\xc3\xae\x42\x13\x51\xd8\x7e\x65\xa8\x99\x9e\x6a\xb6\xc6\x58\xa1\x3d\x1c\x33\xf6\xa0\x12\x69\x93\xb2\x9a\xe6\xb2\xeb\xb5\x6c\x7f\x2a\xbc\x36\x36\x5a\xfc\x5b\x51\x14\xda\xf3\xc6\x27\x49\xfc\x09\x99\x0b\xb6\x2d\x53\x84\xa5\xf4\xf5\x04\xba\x87\xa9\x60\x4b\xe3\xc7\xe2\x31\x83\xe9\x1a\x84\x5a\x6b\xd5\xf3\x96\x11\xd3\x1a\xeb\x82\x38\x0d\xef\x7e\x0e\xb8\xf1\xa7\x65\x41\xee\x78\x70\xdf\x45\x65\xf4\xff\x69\x78\x4d\x73\xb7\xe5\x41\x17\x81\xff\xce\x06\x4e\x4f\xbc\x73\x0f\xdf\xc2\x86\x9e\xcc\xc3\x53\xda\x6a\x6d\x11\xb9\xbd\x45\xc4\xae\x86\x07\x69\x58\xbb\x4b\x34\xaa\x7f\x15\xfe\x3e\x48\xbd\x69\x02\x2f\xb5\x5a\x92\xb9\x0f\x29\x41\x83\xc2\xe9\x2d\xf0\xc3\x2a\xbb\xcb\xd5\x40\xab\xae\xaf\x38\xda\xf0\x16\x1f\x1c\xc8\x5d\xdd\x31\xdb\xe5\xaf\x8d\xa8\xe6\x70\x54\x7f\xad\xe6\x31\x16\x42\x0c\xda\x52\x2b\x8b\x7d\x13\x4f\x3b\x44\x73\x09\x6c\x37\xd5\x0d\xcf\x63\x52\xdb\x4a\x92\x63\xb9\xa2\x2e\xb3\x2d\x9c\x2b\xfd\xdf\xe2\xf1\xa8\xd9\xaf\x4d\xe0\x25\x79\x18\x1e\x91\x68\xff\xee\x9d\x3a\xbb\x9c\xf0\x73\x60\x9a\xa1\x90\x3f\x69\x28\x1b\xd2\xd8\x78\xae\xa8\x96\xd2\x68\xc5\xb6\x33\x56\x29\xba\x9a\xcf\x21\xdb\xbb\x6c\xb6\xc0\xaf\x61\xcb\x76\x8a\xb2\x1f\xf7\xab\xcb\xff\x7e\xff\xf3\xe8\xb4\x99\x57\x1f\x96\x33\x67\xd3\x79\x62\x51\x98\x74\x41\x9c\x45\x83\x5b\xf7\xd4\x3a\xd5\x36\xec\xa8\x0d\xee\x76\x17\x2e\x1e\x5f\x94\xaf\x0f\x4c\x06\x42\x6f\x22\x65\xd7\x2b\x7d\x6b\x8f\x74\xa4\x37\x22\xd2\x6a\x77\xed\xa7\x3a\x7b\xfe\x34\xca\xab\x3d\xa3\x45\x41\x22\xe7\xf0\x9a\x29\x68\xfe\x12\x07\x57\x98\x09\xd8\xa1\x04\xf4\xbf\x4b\x7a\x38\x0d\xed\xc1\xd1\x38\xe8\x7c\xd8\xfb\x81\x3b\x2f\x7e\x1d\xfc\xce\xd7\x01\x6f\xf2\x85\x97\x43\x93\x3f\x65\x99\xe0\x17\x1e\x1f\xf0\x6d\xd5\x9e\x77\x3a\x2e\x79\x1d\x29\xed\x8d\x70\x8b\xf3\xb6\x48\xc6\xa2\x12\x59\x16\x5f\x22\xe9\xc3\x74\xc1\xcb\xb6\x6e\x82\xd3\xf0\x3f\xb2\x84\xd7\x43\x9a\xd6\xc6\x16\xe6\x22\xe2\x98\x50\x0f\xc2\xd7\x61\xd0\xeb\xce\x47\xcd\x47\xf3\xb7\x07\x63\x92\xa1\x75\x52\x31\xaa\xaf\x21\x81\xc3\x89\x57\x0d\xac\xd6\x8a\x16\x86\x91\xb4\x46\xef\x13\xe9\x45\xd5\x5d\xec\x8b\x89\x3f\x5c\x85\x31\x93\x4b\x5a\x4c\x0e\x44\xba\x56\x11\x96\x29\x09\xf0\xb8\x2d\x14\x97\x33\x6c\xf6\xb4\x28\x39\xba\x67\x27\xf4\xc1\xf3\xf9\x09\xc8\xc2\xf9\xcf\x27\x6d\xf6\xfa\xef\x4e\xe4\x23\x8e\xd7\xb2\xf0\x7b\xba\x09\x2f\xe3\x18\x2e\x49\x38\xea\xd1\xc1\x27\x9c\x4b\xeb\x12\x3d\x63\x44\x36\xe1\x11\x3c\x36\xfa\xc2\x39\x34\x5d\xd7\xd5\xdb\x0a\x1e\x6c\xad\x0b\xe9\xfe\xaf\x02\xf9\x06\x66\x80\x12\xcf\x9d\x27\x16\x6e\xbc\x73\x67\xb0\x51\x0e\xcf\x3e\x3d\xfb\xdf\x00\x00\x00\xff\xff\x44\x65\x23\x35\xe4\x50\x00\x00") 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: 19741, mode: os.FileMode(420), modTime: time.Unix(1537092250, 0)} + info := bindataFileInfo{name: "wski18n/resources/en_US.all.json", size: 20708, mode: os.FileMode(420), modTime: time.Unix(1539294171, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/es_ES.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/fr_FR.all.json", size: 101, mode: os.FileMode(420), modTime: time.Unix(1520374115, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/it_IT.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/ja_JA.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/ko_KR.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/pt_BR.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/zh_Hans.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 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(1537087727, 0)} + info := bindataFileInfo{name: "wski18n/resources/zh_Hant.all.json", size: 0, mode: os.FileMode(420), modTime: time.Unix(1520374115, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -329,14 +329,14 @@ func AssetNames() []string { // _bindata is a table, holding each asset generator, mapped to its name. var _bindata = map[string]func() (*asset, error){ - "wski18n/resources/de_DE.all.json": wski18nResourcesDe_deAllJson, - "wski18n/resources/en_US.all.json": wski18nResourcesEn_usAllJson, - "wski18n/resources/es_ES.all.json": wski18nResourcesEs_esAllJson, - "wski18n/resources/fr_FR.all.json": wski18nResourcesFr_frAllJson, - "wski18n/resources/it_IT.all.json": wski18nResourcesIt_itAllJson, - "wski18n/resources/ja_JA.all.json": wski18nResourcesJa_jaAllJson, - "wski18n/resources/ko_KR.all.json": wski18nResourcesKo_krAllJson, - "wski18n/resources/pt_BR.all.json": wski18nResourcesPt_brAllJson, + "wski18n/resources/de_DE.all.json": wski18nResourcesDe_deAllJson, + "wski18n/resources/en_US.all.json": wski18nResourcesEn_usAllJson, + "wski18n/resources/es_ES.all.json": wski18nResourcesEs_esAllJson, + "wski18n/resources/fr_FR.all.json": wski18nResourcesFr_frAllJson, + "wski18n/resources/it_IT.all.json": wski18nResourcesIt_itAllJson, + "wski18n/resources/ja_JA.all.json": wski18nResourcesJa_jaAllJson, + "wski18n/resources/ko_KR.all.json": wski18nResourcesKo_krAllJson, + "wski18n/resources/pt_BR.all.json": wski18nResourcesPt_brAllJson, "wski18n/resources/zh_Hans.all.json": wski18nResourcesZh_hansAllJson, "wski18n/resources/zh_Hant.all.json": wski18nResourcesZh_hantAllJson, } @@ -380,17 +380,18 @@ type bintree struct { Func func() (*asset, error) Children map[string]*bintree } + var _bintree = &bintree{nil, map[string]*bintree{ "wski18n": &bintree{nil, map[string]*bintree{ "resources": &bintree{nil, map[string]*bintree{ - "de_DE.all.json": &bintree{wski18nResourcesDe_deAllJson, map[string]*bintree{}}, - "en_US.all.json": &bintree{wski18nResourcesEn_usAllJson, map[string]*bintree{}}, - "es_ES.all.json": &bintree{wski18nResourcesEs_esAllJson, map[string]*bintree{}}, - "fr_FR.all.json": &bintree{wski18nResourcesFr_frAllJson, map[string]*bintree{}}, - "it_IT.all.json": &bintree{wski18nResourcesIt_itAllJson, map[string]*bintree{}}, - "ja_JA.all.json": &bintree{wski18nResourcesJa_jaAllJson, map[string]*bintree{}}, - "ko_KR.all.json": &bintree{wski18nResourcesKo_krAllJson, map[string]*bintree{}}, - "pt_BR.all.json": &bintree{wski18nResourcesPt_brAllJson, map[string]*bintree{}}, + "de_DE.all.json": &bintree{wski18nResourcesDe_deAllJson, map[string]*bintree{}}, + "en_US.all.json": &bintree{wski18nResourcesEn_usAllJson, map[string]*bintree{}}, + "es_ES.all.json": &bintree{wski18nResourcesEs_esAllJson, map[string]*bintree{}}, + "fr_FR.all.json": &bintree{wski18nResourcesFr_frAllJson, map[string]*bintree{}}, + "it_IT.all.json": &bintree{wski18nResourcesIt_itAllJson, map[string]*bintree{}}, + "ja_JA.all.json": &bintree{wski18nResourcesJa_jaAllJson, map[string]*bintree{}}, + "ko_KR.all.json": &bintree{wski18nResourcesKo_krAllJson, map[string]*bintree{}}, + "pt_BR.all.json": &bintree{wski18nResourcesPt_brAllJson, map[string]*bintree{}}, "zh_Hans.all.json": &bintree{wski18nResourcesZh_hansAllJson, map[string]*bintree{}}, "zh_Hant.all.json": &bintree{wski18nResourcesZh_hantAllJson, map[string]*bintree{}}, }}, @@ -443,4 +444,3 @@ func _filePath(dir, name string) string { cannonicalName := strings.Replace(name, "\\", "/", -1) return filepath.Join(append([]string{dir}, strings.Split(cannonicalName, "/")...)...) } - diff --git a/wski18n/resources/en_US.all.json b/wski18n/resources/en_US.all.json index 06e4ed51c..9e78b706d 100644 --- a/wski18n/resources/en_US.all.json +++ b/wski18n/resources/en_US.all.json @@ -510,5 +510,33 @@ { "id": "msg_config_missing_apigw_access_token", "translation": "The apigw access token is not configured.\n" + }, + { + "id": "msg_verbose_zip_exclude_file_path", + "translation": "Excluding Path: [{{.path}}]\n" + }, + { + "id": "msg_verbose_zip_adding_file_path", + "translation": "Adding [{{.path}}] to Zip File.\n" + }, + { + "id": "msg_verbose_zip_include_source_path", + "translation": "For the Source Path: [{{.path}}]\n" + }, + { + "id": "msg_verbose_zip_include_source_path_destination_path", + "translation": "For the Source Path: [{{.path}}] and Destination Path: [{{.destination}}]\n" + }, + { + "id": "msg_verbose_invalid_include_entry", + "translation": "Ignoring Include Entry as it is invalid [{{.include}}]. Include entry can either have [Source] or [Source, Destination].\n" + }, + { + "id": "msg_verbose_creating_zip_file", + "translation": "Creating the Zip File: [{{.path}}]\n" + }, + { + "id": "msg_verbose_list_of_files_matching_pattern", + "translation": "Found the following files with matching Source File Path pattern.\n" } ]