├── .gitignore ├── .travis.yml ├── CODE_OF_CONDUCT.md ├── CONTRIBUTING.md ├── Dockerfile ├── ISSUE_TEMPLATE └── minor-version-bump.md ├── LICENSE ├── Makefile ├── PUBLISHING.md ├── README.md ├── contrib └── etc │ └── install_node.sh ├── hooks ├── build └── post_push ├── imagestreams ├── nodejs-centos7.json └── nodejs-rhel7.json ├── s2i ├── assemble ├── env ├── generate-container-user ├── run ├── save-artifacts └── usage ├── templates └── nodejs-rest-http.json ├── test ├── make-plus-booster-test.sh ├── run.sh └── test-app │ ├── README.md │ ├── addon │ ├── binding.gyp │ └── hello.cc │ ├── greeting.ts │ ├── package-lock.json │ ├── package.json │ ├── public │ └── index.html │ ├── server.js │ └── tsconfig.json └── versions.mk /.gitignore: -------------------------------------------------------------------------------- 1 | greeting.js -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | before_script: 2 | - wget https://github.com/openshift/source-to-image/releases/download/v1.1.10/source-to-image-v1.1.10-27f0729d-linux-amd64.tar.gz 3 | - tar xvzOf source-to-image-v1.1.10-27f0729d-linux-amd64.tar.gz > s2i.bin 4 | - sudo mv s2i.bin /usr/bin/s2i 5 | - sudo chmod 755 /usr/bin/s2i 6 | 7 | script: 8 | - make all 9 | 10 | notifications: 11 | irc: "chat.freenode.net#bucharest-gold" 12 | 13 | branches: 14 | only: 15 | - master 16 | - /^[8-9]+.*$/ 17 | -------------------------------------------------------------------------------- /CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | # Contributor Covenant Code of Conduct 2 | 3 | ## Our Pledge 4 | 5 | In the interest of fostering an open and welcoming environment, we as 6 | contributors and maintainers pledge to making participation in our project and 7 | our community a harassment-free experience for everyone, regardless of age, body 8 | size, disability, ethnicity, sex characteristics, gender identity and expression, 9 | level of experience, education, socio-economic status, nationality, personal 10 | appearance, race, religion, or sexual identity and orientation. 11 | 12 | ## Our Standards 13 | 14 | Examples of behavior that contributes to creating a positive environment 15 | include: 16 | 17 | * Using welcoming and inclusive language 18 | * Being respectful of differing viewpoints and experiences 19 | * Gracefully accepting constructive criticism 20 | * Focusing on what is best for the community 21 | * Showing empathy towards other community members 22 | 23 | Examples of unacceptable behavior by participants include: 24 | 25 | * The use of sexualized language or imagery and unwelcome sexual attention or 26 | advances 27 | * Trolling, insulting/derogatory comments, and personal or political attacks 28 | * Public or private harassment 29 | * Publishing others' private information, such as a physical or electronic 30 | address, without explicit permission 31 | * Other conduct which could reasonably be considered inappropriate in a 32 | professional setting 33 | 34 | ## Our Responsibilities 35 | 36 | Project maintainers are responsible for clarifying the standards of acceptable 37 | behavior and are expected to take appropriate and fair corrective action in 38 | response to any instances of unacceptable behavior. 39 | 40 | Project maintainers have the right and responsibility to remove, edit, or 41 | reject comments, commits, code, wiki edits, issues, and other contributions 42 | that are not aligned to this Code of Conduct, or to ban temporarily or 43 | permanently any contributor for other behaviors that they deem inappropriate, 44 | threatening, offensive, or harmful. 45 | 46 | ## Scope 47 | 48 | This Code of Conduct applies both within project spaces and in public spaces 49 | when an individual is representing the project or its community. Examples of 50 | representing a project or community include using an official project e-mail 51 | address, posting via an official social media account, or acting as an appointed 52 | representative at an online or offline event. Representation of a project may be 53 | further defined and clarified by project maintainers. 54 | 55 | ## Enforcement 56 | 57 | Instances of abusive, harassing, or otherwise unacceptable behavior may be 58 | reported by contacting the project team at nodeshift@redhat.com. All 59 | complaints will be reviewed and investigated and will result in a response that 60 | is deemed necessary and appropriate to the circumstances. The project team is 61 | obligated to maintain confidentiality with regard to the reporter of an incident. 62 | Further details of specific enforcement policies may be posted separately. 63 | 64 | Project maintainers who do not follow or enforce the Code of Conduct in good 65 | faith may face temporary or permanent repercussions as determined by other 66 | members of the project's leadership. 67 | 68 | ## Attribution 69 | 70 | This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, 71 | available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html 72 | 73 | [homepage]: https://www.contributor-covenant.org 74 | 75 | For answers to common questions about this code of conduct, see 76 | https://www.contributor-covenant.org/faq 77 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing to `centos7-s2i-nodejs` 2 | 3 | We are a community-driven, open source project and we welcome 4 | contributions! 5 | 6 | ## Development Requirements 7 | 8 | To run builds of this project locally, you will need to have the 9 | following tools. 10 | 11 | * Node.js https://nodejs.org/en/download 12 | * Docker https://www.docker.com/get-docker 13 | 14 | ## Building 15 | 16 | To build the project, run 17 | 18 | ``` 19 | make build 20 | ``` 21 | 22 | ## Contributions 23 | 24 | Clone a copy of this repository 25 | 26 | ``` 27 | git clone https://github.com/nodeshift/centos7-s2i-nodejs.git 28 | cd centos7-s2i-nodejs 29 | ``` 30 | 31 | Make your changes, and be sure that all tests pass. 32 | 33 | ``` 34 | make test 35 | ``` 36 | 37 | Then open a [pull request](https://github.com/nodeshift/centos7-s2i-nodejs/compare). 38 | 39 | -------------------------------------------------------------------------------- /Dockerfile: -------------------------------------------------------------------------------- 1 | FROM centos/s2i-base-centos7 2 | # This image provides a Node.JS environment you can use to run your 3 | # Node.JS applications. 4 | 5 | EXPOSE 8080 6 | 7 | # This image will be initialized with "npm run $NPM_RUN" 8 | # See https://docs.npmjs.com/misc/scripts, and your repo's package.json 9 | # file for possible values of NPM_RUN 10 | ARG NODE_VERSION 11 | ARG NPM_VERSION 12 | 13 | ENV NPM_RUN=start \ 14 | NODE_VERSION=${NODE_VERSION} \ 15 | NPM_VERSION=${NPM_VERSION} \ 16 | NODE_LTS=false \ 17 | NPM_CONFIG_LOGLEVEL=info \ 18 | NPM_CONFIG_PREFIX=$HOME/.npm-global \ 19 | NPM_CONFIG_TARBALL=/usr/share/node/node-v${NODE_VERSION}-headers.tar.gz \ 20 | PATH=$HOME/node_modules/.bin/:$HOME/.npm-global/bin/:$PATH \ 21 | DEBUG_PORT=5858 \ 22 | SUMMARY="Platform for building and running Node.js ${NODE_VERSION} applications" \ 23 | DESCRIPTION="Node.js $NODEJS_VERSION available as docker container is a base platform for \ 24 | building and running various Node.js $NODEJS_VERSION applications and frameworks. \ 25 | Node.js is a platform built on Chrome's JavaScript runtime for easily building \ 26 | fast, scalable network applications. Node.js uses an event-driven, non-blocking I/O model \ 27 | that makes it lightweight and efficient, perfect for data-intensive real-time applications \ 28 | that run across distributed devices." \ 29 | LD_LIBRARY_PATH=/opt/rh/httpd24/root/usr/lib64 30 | 31 | LABEL io.k8s.description="$DESCRIPTION" \ 32 | io.k8s.display-name="Node.js $NODE_VERSION" \ 33 | io.openshift.expose-services="8080:http" \ 34 | io.openshift.tags="builder,nodejs,nodejs-$NODE_VERSION" \ 35 | com.redhat.deployments-dir="/opt/app-root/src" \ 36 | com.redhat.dev-mode="DEV_MODE:false" \ 37 | com.redhat.dev-mode.port="DEBUG_PORT:5858" \ 38 | maintainer="Lance Ball " \ 39 | summary="$SUMMARY" \ 40 | description="$DESCRIPTION" \ 41 | version="$NODE_VERSION" \ 42 | name="nodeshift/centos7-s2i-nodejs" \ 43 | usage="s2i build . nodeshift/centos7-s2i-nodejs myapp" 44 | 45 | COPY ./s2i/ $STI_SCRIPTS_PATH 46 | COPY ./contrib/ /opt/app-root 47 | 48 | RUN /opt/app-root/etc/install_node.sh 49 | 50 | USER 1001 51 | 52 | # Set the default CMD to print the usage 53 | CMD ${STI_SCRIPTS_PATH}/usage 54 | -------------------------------------------------------------------------------- /ISSUE_TEMPLATE/minor-version-bump.md: -------------------------------------------------------------------------------- 1 | ## New Node.js minor version bump 2 | 3 | Use this issue template to report a minor version bump in Node.js. 4 | 5 | New Node.js version number: 6 | 7 | ### Tasks 8 | 9 | Check out the branch for whatever version is being updated. E.g. 10 | 11 | ``` 12 | git checkout v8.x 13 | ``` 14 | 15 | All of the following tasks occur on this branch. 16 | 17 | - [ ] Ensure a [published node-rpm](https://github.com/nodeshift/node-rpm/releases) for this version exists. 18 | - [ ] Update versions.mk with the correct version number for `NODE_VERSION` and `NPM_VERSION`. 19 | - [ ] Update releases.json and image-streams.centos7.json with new version information. 20 | 21 | ``` 22 | node-metadata -i | jq '.' > releases.json 23 | node-image-stream -f releases.json -i nodeshift/centos7-s2i-nodejs > image-streams.centos7.json 24 | ``` 25 | 26 | - [ ] Ensure that `make all` passes successfully. 27 | - [ ] Tag the new release: `git tag -s -m 'Update to Node.js version 8.10.0' v8.10.0` 28 | - [ ] Publish the release to docker hub (you will need to have `DOCKER_USER` and `DOCKER_PASS` in your environment). 29 | 30 | ``` 31 | make tag publish 32 | ``` 33 | 34 | - [ ] Finally, push your changes to github: `git push origin --follow-tags`. 35 | 36 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | 2 | Apache License 3 | Version 2.0, January 2004 4 | http://www.apache.org/licenses/ 5 | 6 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 7 | 8 | 1. Definitions. 9 | 10 | "License" shall mean the terms and conditions for use, reproduction, 11 | and distribution as defined by Sections 1 through 9 of this document. 12 | 13 | "Licensor" shall mean the copyright owner or entity authorized by 14 | the copyright owner that is granting the License. 15 | 16 | "Legal Entity" shall mean the union of the acting entity and all 17 | other entities that control, are controlled by, or are under common 18 | control with that entity. For the purposes of this definition, 19 | "control" means (i) the power, direct or indirect, to cause the 20 | direction or management of such entity, whether by contract or 21 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 22 | outstanding shares, or (iii) beneficial ownership of such entity. 23 | 24 | "You" (or "Your") shall mean an individual or Legal Entity 25 | exercising permissions granted by this License. 26 | 27 | "Source" form shall mean the preferred form for making modifications, 28 | including but not limited to software source code, documentation 29 | source, and configuration files. 30 | 31 | "Object" form shall mean any form resulting from mechanical 32 | transformation or translation of a Source form, including but 33 | not limited to compiled object code, generated documentation, 34 | and conversions to other media types. 35 | 36 | "Work" shall mean the work of authorship, whether in Source or 37 | Object form, made available under the License, as indicated by a 38 | copyright notice that is included in or attached to the work 39 | (an example is provided in the Appendix below). 40 | 41 | "Derivative Works" shall mean any work, whether in Source or Object 42 | form, that is based on (or derived from) the Work and for which the 43 | editorial revisions, annotations, elaborations, or other modifications 44 | represent, as a whole, an original work of authorship. For the purposes 45 | of this License, Derivative Works shall not include works that remain 46 | separable from, or merely link (or bind by name) to the interfaces of, 47 | the Work and Derivative Works thereof. 48 | 49 | "Contribution" shall mean any work of authorship, including 50 | the original version of the Work and any modifications or additions 51 | to that Work or Derivative Works thereof, that is intentionally 52 | submitted to Licensor for inclusion in the Work by the copyright owner 53 | or by an individual or Legal Entity authorized to submit on behalf of 54 | the copyright owner. For the purposes of this definition, "submitted" 55 | means any form of electronic, verbal, or written communication sent 56 | to the Licensor or its representatives, including but not limited to 57 | communication on electronic mailing lists, source code control systems, 58 | and issue tracking systems that are managed by, or on behalf of, the 59 | Licensor for the purpose of discussing and improving the Work, but 60 | excluding communication that is conspicuously marked or otherwise 61 | designated in writing by the copyright owner as "Not a Contribution." 62 | 63 | "Contributor" shall mean Licensor and any individual or Legal Entity 64 | on behalf of whom a Contribution has been received by Licensor and 65 | subsequently incorporated within the Work. 66 | 67 | 2. Grant of Copyright License. Subject to the terms and conditions of 68 | this License, each Contributor hereby grants to You a perpetual, 69 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 70 | copyright license to reproduce, prepare Derivative Works of, 71 | publicly display, publicly perform, sublicense, and distribute the 72 | Work and such Derivative Works in Source or Object form. 73 | 74 | 3. Grant of Patent License. Subject to the terms and conditions of 75 | this License, each Contributor hereby grants to You a perpetual, 76 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 77 | (except as stated in this section) patent license to make, have made, 78 | use, offer to sell, sell, import, and otherwise transfer the Work, 79 | where such license applies only to those patent claims licensable 80 | by such Contributor that are necessarily infringed by their 81 | Contribution(s) alone or by combination of their Contribution(s) 82 | with the Work to which such Contribution(s) was submitted. If You 83 | institute patent litigation against any entity (including a 84 | cross-claim or counterclaim in a lawsuit) alleging that the Work 85 | or a Contribution incorporated within the Work constitutes direct 86 | or contributory patent infringement, then any patent licenses 87 | granted to You under this License for that Work shall terminate 88 | as of the date such litigation is filed. 89 | 90 | 4. Redistribution. You may reproduce and distribute copies of the 91 | Work or Derivative Works thereof in any medium, with or without 92 | modifications, and in Source or Object form, provided that You 93 | meet the following conditions: 94 | 95 | (a) You must give any other recipients of the Work or 96 | Derivative Works a copy of this License; and 97 | 98 | (b) You must cause any modified files to carry prominent notices 99 | stating that You changed the files; and 100 | 101 | (c) You must retain, in the Source form of any Derivative Works 102 | that You distribute, all copyright, patent, trademark, and 103 | attribution notices from the Source form of the Work, 104 | excluding those notices that do not pertain to any part of 105 | the Derivative Works; and 106 | 107 | (d) If the Work includes a "NOTICE" text file as part of its 108 | distribution, then any Derivative Works that You distribute must 109 | include a readable copy of the attribution notices contained 110 | within such NOTICE file, excluding those notices that do not 111 | pertain to any part of the Derivative Works, in at least one 112 | of the following places: within a NOTICE text file distributed 113 | as part of the Derivative Works; within the Source form or 114 | documentation, if provided along with the Derivative Works; or, 115 | within a display generated by the Derivative Works, if and 116 | wherever such third-party notices normally appear. The contents 117 | of the NOTICE file are for informational purposes only and 118 | do not modify the License. You may add Your own attribution 119 | notices within Derivative Works that You distribute, alongside 120 | or as an addendum to the NOTICE text from the Work, provided 121 | that such additional attribution notices cannot be construed 122 | as modifying the License. 123 | 124 | You may add Your own copyright statement to Your modifications and 125 | may provide additional or different license terms and conditions 126 | for use, reproduction, or distribution of Your modifications, or 127 | for any such Derivative Works as a whole, provided Your use, 128 | reproduction, and distribution of the Work otherwise complies with 129 | the conditions stated in this License. 130 | 131 | 5. Submission of Contributions. Unless You explicitly state otherwise, 132 | any Contribution intentionally submitted for inclusion in the Work 133 | by You to the Licensor shall be under the terms and conditions of 134 | this License, without any additional terms or conditions. 135 | Notwithstanding the above, nothing herein shall supersede or modify 136 | the terms of any separate license agreement you may have executed 137 | with Licensor regarding such Contributions. 138 | 139 | 6. Trademarks. This License does not grant permission to use the trade 140 | names, trademarks, service marks, or product names of the Licensor, 141 | except as required for reasonable and customary use in describing the 142 | origin of the Work and reproducing the content of the NOTICE file. 143 | 144 | 7. Disclaimer of Warranty. Unless required by applicable law or 145 | agreed to in writing, Licensor provides the Work (and each 146 | Contributor provides its Contributions) on an "AS IS" BASIS, 147 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 148 | implied, including, without limitation, any warranties or conditions 149 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 150 | PARTICULAR PURPOSE. You are solely responsible for determining the 151 | appropriateness of using or redistributing the Work and assume any 152 | risks associated with Your exercise of permissions under this License. 153 | 154 | 8. Limitation of Liability. In no event and under no legal theory, 155 | whether in tort (including negligence), contract, or otherwise, 156 | unless required by applicable law (such as deliberate and grossly 157 | negligent acts) or agreed to in writing, shall any Contributor be 158 | liable to You for damages, including any direct, indirect, special, 159 | incidental, or consequential damages of any character arising as a 160 | result of this License or out of the use or inability to use the 161 | Work (including but not limited to damages for loss of goodwill, 162 | work stoppage, computer failure or malfunction, or any and all 163 | other commercial damages or losses), even if such Contributor 164 | has been advised of the possibility of such damages. 165 | 166 | 9. Accepting Warranty or Additional Liability. While redistributing 167 | the Work or Derivative Works thereof, You may choose to offer, 168 | and charge a fee for, acceptance of support, warranty, indemnity, 169 | or other liability obligations and/or rights consistent with this 170 | License. However, in accepting such obligations, You may act only 171 | on Your own behalf and on Your sole responsibility, not on behalf 172 | of any other Contributor, and only if You agree to indemnify, 173 | defend, and hold each Contributor harmless for any liability 174 | incurred by, or claims asserted against, such Contributor by reason 175 | of your accepting any such warranty or additional liability. 176 | 177 | END OF TERMS AND CONDITIONS 178 | 179 | Copyright 2014 Red Hat, Inc. 180 | 181 | Licensed under the Apache License, Version 2.0 (the "License"); 182 | you may not use this file except in compliance with the License. 183 | You may obtain a copy of the License at 184 | 185 | http://www.apache.org/licenses/LICENSE-2.0 186 | 187 | Unless required by applicable law or agreed to in writing, software 188 | distributed under the License is distributed on an "AS IS" BASIS, 189 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 190 | See the License for the specific language governing permissions and 191 | limitations under the License. 192 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | FROM=centos/s2i-base-centos7 2 | IMAGE_NAME=nodeshift/centos7-s2i-nodejs 3 | 4 | # These values are changed in each version branch 5 | # This is the only place they need to be changed 6 | # other than the README.md file. 7 | include versions.mk 8 | 9 | TARGET=$(IMAGE_NAME):$(IMAGE_TAG) 10 | 11 | .PHONY: all 12 | all: build test 13 | 14 | build: Dockerfile s2i contrib 15 | docker build \ 16 | --build-arg NODE_VERSION=$(NODE_VERSION) \ 17 | --build-arg NPM_VERSION=$(NPM_VERSION) \ 18 | --pull -t $(TARGET) . 19 | 20 | .PHONY: test 21 | test: build 22 | BUILDER=$(TARGET) NODE_VERSION=$(NODE_VERSION) ./test/run.sh 23 | 24 | .PHONY: clean 25 | clean: 26 | docker rmi `docker images $(TARGET) -q` 27 | 28 | .PHONY: tag 29 | tag: 30 | if [ ! -z $(LTS_TAG) ]; then docker tag $(TARGET) $(IMAGE_NAME):$(LTS_TAG); fi 31 | docker tag $(TARGET) $(IMAGE_NAME):$(NODE_VERSION) 32 | 33 | .PHONY: publish 34 | publish: all 35 | echo $(DOCKER_PASS) | docker login -u $(DOCKER_USER) --password-stdin 36 | docker push $(TARGET) 37 | docker push $(IMAGE_NAME):$(NODE_VERSION) 38 | if [ ! -z $(LTS_TAG) ]; then docker push $(IMAGE_NAME):$(LTS_TAG); fi 39 | -------------------------------------------------------------------------------- /PUBLISHING.md: -------------------------------------------------------------------------------- 1 | # Publishing the `centos7-s2i-nodejs` images to Docker Hub 2 | 3 | There are a couple of different scenarios that would require newly 4 | published images. The obvious case is when there is a new Node.js 5 | version released. But sometimes we need to push a new image because 6 | there was a bug fix in the builder image. Or we changed something 7 | in the `node-rpm` distribution. 8 | 9 | Follow these steps to publish. In all cases, you should have `DOCKER_USER` 10 | and `DOCKER_PASS` defined in your environment. 11 | 12 | ```sh 13 | $ export DOCKER_USER=lanceball 14 | $ export DOCKER_PASS=xxxxxxxxx 15 | ``` 16 | 17 | ## Bug fixes to the builder image 18 | 19 | When we need to publish new images because the underlying builder 20 | (and not Node.js itself) has changed. The process is pretty simple. 21 | 22 | Check out the master branch and be sure you are up to date. 23 | 24 | ```sh 25 | $ git fetch upstream 26 | $ git rebase upstream/master master 27 | ``` 28 | 29 | Make your code changes, then test and commit them. The `master` branch 30 | can be published without a tag since it does not track a specific release. 31 | 32 | ```sh 33 | $ git push upstream master 34 | $ make tag publish 35 | ``` 36 | 37 | Now you need to update all of the versions we are supporting with these 38 | changes. Currently, that means the `8.x` and `9.x` branches. Check out 39 | each branch, apply the changes, test, commit and publish. 40 | 41 | ```sh 42 | $ git checkout 8.x 43 | $ git cherry-pick # get the commit that you applied in master 44 | ``` 45 | 46 | If the cherry-picking fails, you'll need to figure out what went wrong 47 | and fix it. You can run `git status` to see where there were problems. 48 | If you need to, then, make these fixes, then use `git add` and 49 | `git cherry-pick --continue` to finish applying them. 50 | 51 | Each of these branches should be tagged with the Node.js version number 52 | and a suffix signifying the update for this release. For example, if the 53 | current 9.x release is `9.4.0` and you are making updates to the `9.x` 54 | branch, you should look for the most current 9.x tag and increment it. 55 | 56 | ```sh 57 | $ git tag | grep node-9.4.0 # Find the most recent release (e.g. node-9.4.0-2) 58 | $ git tag node-9.4.0-3 # Increment the version suffix 59 | $ git push upstream 9.x --follow-tags # Push the tag upstream 60 | ``` 61 | 62 | ## New minor or patch-level release 63 | 64 | Let's say that Node.js version 9.10.1 is released and we are currently 65 | publishing 9.10.0. This is a patch level version bump. Note that these 66 | steps will be the same for a minor release, for example, in 67 | this case, if Node.js 9.11.0 is released. 68 | 69 | Take the following steps to publish the latest version. 70 | 71 | ```sh 72 | # switch to the branch being published 73 | git checkout 9.x 74 | 75 | # update with any changes not present locally 76 | git pull upstream 9.x 77 | git rebase upstream/9.x 9.x 78 | 79 | # Change the version numbers in versions.mk 80 | # NODE_VERSION=9.10.1 81 | # NPM_VERSION=5.6.0 82 | 83 | # Make sure nothing broke 84 | make all 85 | 86 | # Then make the docker image tags and publish 87 | make tag publish 88 | 89 | # If everything looks good, commit, tag and push to github 90 | git commit -a -m "chore: update to Node.js 9.10.1" 91 | git tag -s -m "Node.js 9.10.1 release" node-9.10.1 92 | git push upstream 9.x --follow-tags 93 | ``` 94 | 95 | ## New major version 96 | 97 | If there is a new major version released, we'll need to create 98 | a new branch for it. The `master` branch is always tracking the 99 | latest Node.js version, so let's start there. Node 10 is released. 100 | 101 | ```sh 102 | # update with any changes not present locally 103 | git pull upstream master 104 | 105 | # Create a new branch for the version 106 | git checkout -b v10.x 107 | 108 | # Add the new version number in versions.mk and Makefile 109 | # and commit your changes on this new branch 110 | 111 | # Make sure nothing broke 112 | make all 113 | 114 | # Then make the docker image tags and publish 115 | make tag publish 116 | 117 | # The 10.x branch has all the commits we need. 118 | # Tag it with the node version and push. 119 | git tag -s -m "Node.js 10.0.0 release" node-10.0.0 120 | git push upstream 10.x --follow-tags 121 | 122 | ``` 123 | 124 | Don't forget the git tags. These are important and allow us to roll back 125 | to any previously published version if necessary! 126 | 127 | Don't forget to update the [table](https://github.com/helio-frota/centos7-s2i-nodejs#versions) with the new version published and send a pull request 128 | to update the `README.md` on the master branch. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # DEPRECATED 2 | 3 | This is no longer supported, please consider using [ubi8/nodejs-10](https://access.redhat.com/containers/?tab=overview#/registry.access.redhat.com/ubi8/nodejs-10) instead. 4 | 5 | [![Build Status](https://travis-ci.org/nodeshift/centos7-s2i-nodejs.svg?branch=master)](https://travis-ci.org/nodeshift/centos7-s2i-nodejs) 6 | [![](https://images.microbadger.com/badges/image/nodeshift/centos7-s2i-nodejs.svg)](https://microbadger.com/images/nodeshift/centos7-s2i-nodejs "Get your own image badge on microbadger.com") 7 | 8 | This repository contains sources for an [s2i](https://github.com/openshift/source-to-image) builder image, based on CentOS7 and Node.js RPM releases from https://github.com/nodeshift/node-rpm. The RPMs and this builder image are the upstream 9 | sources for the [Red Hat OpenShift Application Runtimes](https://developers.redhat.com/products/rhoar/overview/) Node.js 10 | distribution. 11 | 12 | [![docker hub stats](http://dockeri.co/image/nodeshift/centos7-s2i-nodejs)](https://hub.docker.com/r/nodeshift/centos7-s2i-nodejs/) 13 | 14 | ## Versions 15 | 16 | Node.js versions [currently provided](https://hub.docker.com/r/nodeshift/centos7-s2i-nodejs/tags). 17 | 18 | Version | Tag 19 | -------- | ----- 20 | `12.11.1` | (12.x, latest) 21 | `10.16.3`| (10.x, Dubnium) 22 | `8.16.2` | (8.x, Carbon) 23 | 24 | 25 | ## Usage 26 | 27 | Using this image with OpenShift `oc` command line tool, or with `s2i` directly, will 28 | assemble your application source with its required dependencies, creating a new 29 | container image. This image contains your Node.js application and all required dependencies, 30 | and can be run either on OpenShift or directly on Docker. 31 | 32 | ### OpenShift 33 | 34 | The [`oc` command-line tool](https://github.com/openshift/origin/releases) can be 35 | used to start a build, layering your desired nodejs `REPO_URL` sources into a centos7 36 | image with your selected `RELEASE` of Node.js via the following command format: 37 | 38 | ``` 39 | oc new-app nodeshift/centos7-s2i-nodejs:latest~https://github.com/nodeshift/nodejs-rest-http 40 | ``` 41 | 42 | #### OpenShift Catalog 43 | 44 | With OpenShift, it is also possible to import this builder image into the 45 | online Catalog, so that applications can be created and deployed using this Node.js 46 | image through the web-based user interface. To import the images, run the following 47 | openshift command. 48 | 49 | ``` 50 | oc create -f imagestreams/nodejs-centos7.json 51 | ``` 52 | 53 | ### Docker 54 | 55 | The [Source2Image cli tools](https://github.com/openshift/source-to-image/releases) 56 | are available as a standalone project, allowing you to run your application directly 57 | in Docker. 58 | 59 | This example will produce a new Docker image named `webapp`: 60 | 61 | ``` 62 | s2i build https://github.com/nodeshift-starters/nodejs-rest-http nodeshift/centos7-s2i-nodejs:latest webapp 63 | ``` 64 | 65 | Then you can run the application image like this. 66 | 67 | ``` 68 | docker run -p 8080:8080 --rm -it webapp 69 | ``` 70 | 71 | ## Configuration 72 | 73 | Use the following environment variables to configure the runtime behavior of the 74 | application image created from this builder image. 75 | 76 | NAME | Description 77 | ------------|------------- 78 | NPM_RUN | Select an alternate / custom runtime mode, defined in your `package.json` file's [`scripts`](https://docs.npmjs.com/misc/scripts) section (default: npm run "start") 79 | NPM_MIRROR | Sets the npm registry URL 80 | NODE_ENV | Node.js runtime mode (default: "production") 81 | HTTP_PROXY | use an npm proxy during assembly 82 | HTTPS_PROXY | use an npm proxy during assembly 83 | NO_PROXY | set URLs that should be excluded from proxying during assembly 84 | 85 | One way to define a set of environment variables is to include them as key value pairs 86 | in a `.s2i/environment` file in your source repository. 87 | 88 | Example: `DATABASE_USER=sampleUser` 89 | 90 | ### Debug Mode 91 | 92 | When `NODE_ENV` is set to `development` or `DEV_MODE` is set to true, your Node.js application 93 | will be started using `nodemon`. 94 | 95 | ``` 96 | npx nodemon --inspect="$DEBUG_PORT" 97 | ``` 98 | 99 | ### Using Docker's exec 100 | 101 | To change your source code in a running container, use Docker's [exec](http://docker.io) command: 102 | 103 | ``` 104 | docker exec -it /bin/bash 105 | ``` 106 | 107 | After you [Docker exec](http://docker.io) into the running container, your current directory is set 108 | to `/opt/app-root/src`, where the source code for your application is located. 109 | 110 | ### Using OpenShift's rsync 111 | 112 | If you have deployed your application to OpenShift, you can use 113 | [oc rsync](https://docs.okd.io/latest/dev_guide/copy_files_to_container.html) to copy local 114 | files to a remote container running in an OpenShift pod. 115 | -------------------------------------------------------------------------------- /contrib/etc/install_node.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | set -ex 4 | INSTALL_PKGS="centos-release-scl-rh nss_wrapper rh-git218" 5 | 6 | yum remove -y rh-nodejs8 rh-nodejs8-npm rh-nodejs8-nodejs-nodemon rh-nodejs8-runtime rh-nodejs10 rh-nodejs10-npm rh-nodejs10-nodejs-nodemon rh-nodejs10-runtime 7 | 8 | yum install -y --setopt=tsflags=nodocs $INSTALL_PKGS 9 | ln -fs /opt/rh/rh-git218/root/usr/bin/git /usr/bin/git 10 | 11 | # Ensure git uses https instead of ssh for NPM install 12 | # See: https://github.com/npm/npm/issues/5257 13 | echo -e "Setting git config rules" 14 | git config --system url."https://github.com".insteadOf git@github.com: 15 | git config --global url."https://github.com".insteadOf ssh://git@github.com 16 | git config --system url."https://".insteadOf git:// 17 | git config --system url."https://".insteadOf ssh:// 18 | git config --list 19 | 20 | yum install -y https://github.com/nodeshift/node-rpm/releases/download/v${NODE_VERSION}/rhoar-nodejs-${NODE_VERSION}-1.el7.centos.x86_64.rpm 21 | yum install -y https://github.com/nodeshift/node-rpm/releases/download/v${NODE_VERSION}/npm-${NPM_VERSION}-1.${NODE_VERSION}.1.el7.centos.x86_64.rpm 22 | 23 | rpm -V $INSTALL_PKGS 24 | yum clean all -y 25 | ldconfig 26 | 27 | # Make sure npx is available 28 | if [ ! -h /usr/bin/npx ] ; then 29 | ln -s /usr/lib/node_modules/npm/bin/npx-cli.js /usr/bin/npx 30 | fi 31 | 32 | echo "---> Setting directory write permissions" 33 | fix-permissions /opt/app-root 34 | 35 | # Delete NPM things that we don't really need (like tests) from node_modules 36 | find /usr/local/lib/node_modules/npm -name test -o -name .bin -type d | xargs rm -rf 37 | 38 | # Clean up the stuff we downloaded 39 | yum clean all -y 40 | -------------------------------------------------------------------------------- /hooks/build: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | eval $(cat versions.mk) 4 | 5 | echo "Building image with versions..." 6 | echo "NODE_VERSION ${NODE_VERSION}" 7 | echo "NPM_VERSION ${NPM_VERSION}" 8 | echo "V8_VERSION ${V8_VERSION}" 9 | 10 | docker build \ 11 | --build-arg NODE_VERSION=${NODE_VERSION} \ 12 | --build-arg NPM_VERSION=${NPM_VERSION} \ 13 | --build-arg V8_VERSION=${V8_VERSION} \ 14 | -t ${IMAGE_NAME} . -------------------------------------------------------------------------------- /hooks/post_push: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | eval $(cat versions.mk) 4 | 5 | if [ ! -z ${LTS_TAG} ] ; then 6 | echo "Tagging with ${LTS_TAG}" 7 | docker tag $IMAGE_NAME $DOCKER_REPO:$LTS_TAG 8 | docker push $DOCKER_REPO:$LTS_TAG 9 | else 10 | echo "No LTS tag." 11 | fi 12 | 13 | -------------------------------------------------------------------------------- /imagestreams/nodejs-centos7.json: -------------------------------------------------------------------------------- 1 | { 2 | "kind": "ImageStream", 3 | "apiVersion": "v1", 4 | "metadata": { 5 | "name": "nodejs", 6 | "annotations": { 7 | "openshift.io/display-name": "Node.js" 8 | } 9 | }, 10 | "spec": { 11 | "tags": [ 12 | { 13 | "name": "latest", 14 | "annotations": { 15 | "openshift.io/display-name": "Node.js (Latest)", 16 | "openshift.io/provider-display-name": "Red Hat, Inc.", 17 | "description": "Build and run Node.js applications on CentOS 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.\n\nWARNING: By selecting this tag, your application will automatically update to use the latest version of Node.js available on OpenShift, including major versions updates.", 18 | "iconClass": "icon-nodejs", 19 | "tags": "builder,nodejs", 20 | "supports": "nodejs", 21 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 22 | }, 23 | "from": { 24 | "kind": "ImageStreamTag", 25 | "name": "12" 26 | }, 27 | "referencePolicy": { 28 | "type": "Local" 29 | } 30 | }, 31 | { 32 | "name": "8", 33 | "annotations": { 34 | "openshift.io/display-name": "Node.js 8", 35 | "openshift.io/provider-display-name": "Red Hat, Inc.", 36 | "description": "Build and run Node.js 8 applications on CentOS 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/sclorg/s2i-nodejs-container/blob/master/8/README.md.", 37 | "iconClass": "icon-nodejs", 38 | "tags": "builder,nodejs", 39 | "version": "8", 40 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 41 | }, 42 | "from": { 43 | "kind": "DockerImage", 44 | "name": "docker.io/centos/nodejs-8-centos7:latest" 45 | }, 46 | "referencePolicy": { 47 | "type": "Local" 48 | } 49 | }, 50 | { 51 | "name": "8-RHOAR", 52 | "annotations": { 53 | "openshift.io/display-name": "Node.js 8 (RHOAR)", 54 | "openshift.io/provider-display-name": "Red Hat, Inc.", 55 | "description": "Build and run Node.js 8 applications on CentOS 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.", 56 | "iconClass": "icon-nodejs", 57 | "tags": "builder,nodejs", 58 | "version": "8", 59 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 60 | }, 61 | "from": { 62 | "kind": "DockerImage", 63 | "name": "docker.io/nodeshift/centos7-s2i-nodejs:8.x" 64 | }, 65 | "referencePolicy": { 66 | "type": "Local" 67 | } 68 | }, 69 | { 70 | "name": "10", 71 | "annotations": { 72 | "openshift.io/display-name": "Node.js 10", 73 | "openshift.io/provider-display-name": "Red Hat, Inc.", 74 | "description": "Build and run Node.js 10 applications on CentOS 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.", 75 | "iconClass": "icon-nodejs", 76 | "tags": "builder,nodejs", 77 | "version": "10", 78 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 79 | }, 80 | "from": { 81 | "kind": "DockerImage", 82 | "name": "docker.io/nodeshift/centos7-s2i-nodejs:10.x" 83 | }, 84 | "referencePolicy": { 85 | "type": "Local" 86 | } 87 | }, 88 | { 89 | "name": "11", 90 | "annotations": { 91 | "openshift.io/display-name": "Node.js 11", 92 | "openshift.io/provider-display-name": "Red Hat, Inc.", 93 | "description": "Build and run Node.js 11 applications on CentOS 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.", 94 | "iconClass": "icon-nodejs", 95 | "tags": "builder,nodejs", 96 | "version": "11", 97 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 98 | }, 99 | "from": { 100 | "kind": "DockerImage", 101 | "name": "docker.io/nodeshift/centos7-s2i-nodejs:11.x" 102 | }, 103 | "referencePolicy": { 104 | "type": "Local" 105 | } 106 | }, 107 | { 108 | "name": "12", 109 | "annotations": { 110 | "openshift.io/display-name": "Node.js 12", 111 | "openshift.io/provider-display-name": "Red Hat, Inc.", 112 | "description": "Build and run Node.js 12 applications on CentOS 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.", 113 | "iconClass": "icon-nodejs", 114 | "tags": "builder,nodejs", 115 | "version": "12", 116 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 117 | }, 118 | "from": { 119 | "kind": "DockerImage", 120 | "name": "docker.io/nodeshift/centos7-s2i-nodejs:12.x" 121 | }, 122 | "referencePolicy": { 123 | "type": "Local" 124 | } 125 | } 126 | ] 127 | } 128 | } 129 | -------------------------------------------------------------------------------- /imagestreams/nodejs-rhel7.json: -------------------------------------------------------------------------------- 1 | { 2 | "kind": "ImageStream", 3 | "apiVersion": "v1", 4 | "metadata": { 5 | "name": "nodejs", 6 | "annotations": { 7 | "openshift.io/display-name": "Node.js" 8 | } 9 | }, 10 | "spec": { 11 | "tags": [ 12 | { 13 | "name": "latest", 14 | "annotations": { 15 | "openshift.io/display-name": "Node.js (Latest)", 16 | "openshift.io/provider-display-name": "Red Hat, Inc.", 17 | "description": "Build and run Node.js 10 applications on RHEL 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.\n\nWARNING: By selecting this tag, your application will automatically update to use the latest version of Node.js available on OpenShift, including major versions updates.", 18 | "iconClass": "icon-nodejs", 19 | "tags": "builder,nodejs", 20 | "supports":"nodejs", 21 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 22 | }, 23 | "from": { 24 | "kind": "ImageStreamTag", 25 | "name": "10-SCL" 26 | }, 27 | "referencePolicy": { 28 | "type": "Local" 29 | } 30 | }, 31 | { 32 | "name": "8", 33 | "annotations": { 34 | "openshift.io/display-name": "Node.js 8", 35 | "openshift.io/provider-display-name": "Red Hat, Inc.", 36 | "description": "Build and run Node.js 8 applications on RHEL 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/sclorg/s2i-nodejs-container.", 37 | "iconClass": "icon-nodejs", 38 | "tags": "builder,nodejs", 39 | "version": "8", 40 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 41 | }, 42 | "from": { 43 | "kind": "DockerImage", 44 | "name": "registry.redhat.io/rhscl/nodejs-8-rhel7:latest" 45 | }, 46 | "referencePolicy": { 47 | "type": "Local" 48 | } 49 | }, 50 | { 51 | "name": "8-RHOAR", 52 | "annotations": { 53 | "openshift.io/display-name": "OpenShift Application Runtimes Node.js 8", 54 | "openshift.io/provider-display-name": "Red Hat, Inc.", 55 | "description": "Build and run Node.js 8 applications on RHEL 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.", 56 | "iconClass": "icon-nodejs", 57 | "tags": "builder,nodejs", 58 | "version": "8", 59 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 60 | }, 61 | "from": { 62 | "kind": "DockerImage", 63 | "name": "registry.redhat.io/rhoar-nodejs/nodejs-8" 64 | }, 65 | "referencePolicy": { 66 | "type": "Local" 67 | } 68 | }, 69 | { 70 | "name": "10", 71 | "annotations": { 72 | "openshift.io/display-name": "OpenShift Application Runtimes Node.js 10", 73 | "openshift.io/provider-display-name": "Red Hat, Inc.", 74 | "description": "Build and run Node.js 10 applications on RHEL 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.", 75 | "iconClass": "icon-nodejs", 76 | "tags": "builder,nodejs,hidden", 77 | "version": "10", 78 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 79 | }, 80 | "from": { 81 | "kind": "DockerImage", 82 | "name": "registry.redhat.io/rhoar-nodejs/nodejs-10" 83 | }, 84 | "referencePolicy": { 85 | "type": "Local" 86 | } 87 | }, 88 | { 89 | "name": "10-SCL", 90 | "annotations": { 91 | "openshift.io/display-name": "Node.js 10", 92 | "openshift.io/provider-display-name": "Red Hat, Inc.", 93 | "description": "Build and run Node.js 10 applications on RHEL 7. For more information about using this builder image, including OpenShift considerations, see https://github.com/nodeshift/centos7-s2i-nodejs.", 94 | "iconClass": "icon-nodejs", 95 | "tags": "builder,nodejs", 96 | "version": "10", 97 | "sampleRepo": "https://github.com/sclorg/nodejs-ex.git" 98 | }, 99 | "from": { 100 | "kind": "DockerImage", 101 | "name": "registry.redhat.io/rhscl/nodejs-10-rhel7" 102 | }, 103 | "referencePolicy": { 104 | "type": "Local" 105 | } 106 | } 107 | ] 108 | } 109 | } 110 | -------------------------------------------------------------------------------- /s2i/assemble: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | set -e 4 | 5 | source /usr/libexec/s2i/env 6 | 7 | if [ "$DEV_MODE" == true ] ; then 8 | set -x 9 | fi 10 | 11 | echo "---> Installing application source" 12 | cp -Rfp /tmp/src/. ./ 13 | 14 | if [ ! -z $HTTP_PROXY ]; then 15 | echo "---> Setting npm http proxy to $HTTP_PROXY" 16 | npm config set proxy $HTTP_PROXY 17 | fi 18 | 19 | if [ ! -z $http_proxy ]; then 20 | echo "---> Setting npm http proxy to $http_proxy" 21 | npm config set proxy $http_proxy 22 | fi 23 | 24 | if [ ! -z $HTTPS_PROXY ]; then 25 | echo "---> Setting npm https proxy to $HTTPS_PROXY" 26 | npm config set https-proxy $HTTPS_PROXY 27 | fi 28 | 29 | if [ ! -z $https_proxy ]; then 30 | echo "---> Setting npm https proxy to $https_proxy" 31 | npm config set https-proxy $https_proxy 32 | fi 33 | 34 | if [ ! -z $NO_PROXY ]; then 35 | echo "---> Setting npm no proxy config to $NO_PROXY" 36 | npm config set no-proxy $NO_PROXY 37 | fi 38 | 39 | if [ ! -z $no_proxy ]; then 40 | echo "---> Setting npm no proxy config to $no_proxy" 41 | npm config set no-proxy $no_proxy 42 | fi 43 | 44 | # Change the npm registry mirror if provided 45 | if [ ! -z "$NPM_MIRROR" ]; then 46 | echo "---> Setting the npm package mirror to $NPM_MIRROR" 47 | npm config set registry $NPM_MIRROR 48 | fi 49 | 50 | echo "---> Building your Node application from source" 51 | echo -e "Current git config" 52 | git config --list 53 | 54 | if [ ! -z "$YARN_ENABLED" ]; then 55 | echo "---> Using 'yarn install' with YARN_ARGS" 56 | npx yarn install $YARN_ARGS 57 | else 58 | echo "---> Installing dependencies" 59 | if [ "$DEV_MODE" == true ]; then 60 | echo "---> Using 'npm install'" 61 | npm install 62 | 63 | #do not fail when there is no build script 64 | echo "---> Building in development mode" 65 | npm run build --if-present 66 | else 67 | HAS_BUILD=$(node -e "console.log(require('./package.json').scripts.build ? true : false)") 68 | 69 | # check to see if there is a build script by inspecting the package.json 70 | if [ "$HAS_BUILD" == true ]; then 71 | # Do a npm install to get the dev depdencies 72 | echo "---> Installing dev dependencies" 73 | NODE_ENV=development npm install 74 | #do not fail when there is no build script 75 | echo "---> Building in production mode" 76 | npm run build --if-present 77 | else 78 | echo "---> Using 'npm install -s --only=production'" 79 | npm install -s --only=production 80 | fi 81 | 82 | echo "---> Pruning the development dependencies" 83 | npm prune 84 | fi 85 | fi 86 | 87 | echo "---> Cleaning up npm cache" 88 | rm -rf .npm 89 | 90 | echo "---> Fix permissions on app-root" 91 | fix-permissions /opt/app-root 92 | -------------------------------------------------------------------------------- /s2i/env: -------------------------------------------------------------------------------- 1 | # If NODE_ENV is not set by the user, then default to production. 2 | # User may also set DEV_MODE=true 3 | if [ -z "$NODE_ENV" ]; then 4 | if [ "$DEV_MODE" == true ]; then 5 | export NODE_ENV=development 6 | else 7 | export NODE_ENV=production 8 | fi 9 | fi 10 | 11 | # Set the environment for this build configuration to production by default. 12 | if [ "$NODE_ENV" == "production" ]; then 13 | export DEV_MODE=false 14 | else 15 | export DEV_MODE=true 16 | fi 17 | -------------------------------------------------------------------------------- /s2i/generate-container-user: -------------------------------------------------------------------------------- 1 | # Set current user in nss_wrapper 2 | USER_ID=$(id -u) 3 | GROUP_ID=$(id -g) 4 | 5 | if [ x"$USER_ID" != x"0" -a x"$USER_ID" != x"1001" ]; then 6 | 7 | NSS_WRAPPER_PASSWD=/opt/app-root/etc/passwd 8 | NSS_WRAPPER_GROUP=/etc/group 9 | 10 | cat /etc/passwd | sed -e 's/^default:/builder:/' > $NSS_WRAPPER_PASSWD 11 | 12 | echo "default:x:${USER_ID}:${GROUP_ID}:Default Application User:${HOME}:/sbin/nologin" >> $NSS_WRAPPER_PASSWD 13 | 14 | export NSS_WRAPPER_PASSWD 15 | export NSS_WRAPPER_GROUP 16 | 17 | LD_PRELOAD=libnss_wrapper.so 18 | export LD_PRELOAD 19 | fi 20 | -------------------------------------------------------------------------------- /s2i/run: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | set -e 3 | 4 | source /usr/libexec/s2i/env 5 | source /usr/libexec/s2i/generate-container-user 6 | 7 | # Set the environment for this build configuration to production by default. 8 | if [ "$NODE_ENV" == "production" ]; then 9 | export DEV_MODE=false 10 | else 11 | export DEV_MODE=true 12 | set -x 13 | fi 14 | 15 | export GIT_COMMITTER_NAME="unknown" 16 | export and GIT_COMMITTER_EMAIL="unknown@localhost.com" 17 | git --version 18 | 19 | # Runs the nodejs application server. 20 | run_node() { 21 | echo -e "Using Node.js version: $(node --version)" 22 | echo -e "Environment: \n\tDEV_MODE=${DEV_MODE}\n\tNODE_ENV=${NODE_ENV}\n\tDEBUG_PORT=${DEBUG_PORT}" 23 | echo -e "Running as user $(id)" 24 | if [ "$DEV_MODE" == true ]; then 25 | echo "Installing dev dependencies..." 26 | npm install 27 | echo "Launching via nodemon..." 28 | exec npx nodemon --inspect="$DEBUG_PORT" 29 | else 30 | echo "Launching via npm..." 31 | exec npm run -d $NPM_RUN 32 | fi 33 | } 34 | 35 | # Allow debugging the builder image itself, by using: 36 | # $ docker run -it nodeshift/centos-s2i-nodejs --debug 37 | # 38 | [ "$1" == "--debug" ] && exec /bin/bash 39 | 40 | run_node 41 | -------------------------------------------------------------------------------- /s2i/save-artifacts: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | if [ "$(ls ${HOME}/node_modules 2>/dev/null)" ]; then 4 | tar -C ${HOME} -cf - node_modules 5 | fi 6 | -------------------------------------------------------------------------------- /s2i/usage: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | cat </dev/null 27 | } 28 | 29 | container_exists() { 30 | image_exists $(cat $cid_file) 31 | } 32 | 33 | container_ip() { 34 | docker inspect --format="{{ .NetworkSettings.IPAddress }}" $(cat $cid_file) 35 | } 36 | 37 | container_logs() { 38 | docker logs $(cat $cid_file) 39 | } 40 | 41 | run_s2i_build() { 42 | echo "Running s2i build ${s2i_args} ${test_dir}/test-app ${BUILDER} ${APP_IMAGE}" 43 | s2i build ${s2i_args} --exclude "(^|/)node_modules(/|$)" ${test_dir}/test-app ${BUILDER} ${APP_IMAGE} 44 | } 45 | 46 | run_s2i_build_incremental() { 47 | echo "Running s2i build ${s2i_args} ${test_dir}/test-app ${BUILDER} ${APP_IMAGE} --incremental=true" 48 | s2i build ${s2i_args} --exclude "(^|/)node_modules(/|$)" ${test_dir}/test-app ${BUILDER} ${APP_IMAGE} --incremental=true 49 | } 50 | 51 | prepare() { 52 | if ! image_exists ${BUILDER}; then 53 | echo "ERROR: The image ${BUILDER} must exist before this script is executed." 54 | exit 1 55 | fi 56 | } 57 | 58 | run_test_application() { 59 | echo "Starting test application ${APP_IMAGE}..." 60 | docker run --cidfile=${cid_file} -p ${test_port}:${test_port} $1 ${APP_IMAGE} 61 | } 62 | 63 | cleanup() { 64 | if [ -f $cid_file ]; then 65 | if container_exists; then 66 | cid=$(cat $cid_file) 67 | docker stop $cid 68 | exit_code=`docker inspect --format="{{ .State.ExitCode }}" $cid` 69 | echo "Container exit code = $exit_code" 70 | # Only check the exist status for non DEV_MODE 71 | if [ "$1" == "false" ] && [ "$exit_code" != "222" ] ; then 72 | echo "ERROR: The exist status should have been 222." 73 | exit 1 74 | fi 75 | fi 76 | fi 77 | cids=`ls -1 *.cid 2>/dev/null | wc -l` 78 | if [ $cids != 0 ] 79 | then 80 | rm *.cid 81 | fi 82 | } 83 | 84 | check_result() { 85 | local result="$1" 86 | if [[ "$result" != "0" ]]; then 87 | echo "STI image '${BUILDER}' test FAILED (exit code: ${result})" 88 | cleanup 89 | exit $result 90 | fi 91 | } 92 | 93 | wait_for_cid() { 94 | local max_attempts=10 95 | local sleep_time=1 96 | local attempt=1 97 | local result=1 98 | while [ $attempt -le $max_attempts ]; do 99 | [ -f $cid_file ] && [ -s $cid_file ] && break 100 | echo "Waiting for container start..." 101 | attempt=$(( $attempt + 1 )) 102 | sleep $sleep_time 103 | done 104 | } 105 | 106 | test_s2i_usage() { 107 | echo "Testing 's2i usage'..." 108 | s2i usage ${s2i_args} ${BUILDER} &>/dev/null 109 | } 110 | 111 | test_docker_run_usage() { 112 | echo "Testing 'docker run' usage..." 113 | docker run ${BUILDER} &>/dev/null 114 | } 115 | 116 | test_connection() { 117 | echo "Testing HTTP connection..." 118 | local max_attempts=10 119 | local sleep_time=1 120 | local attempt=1 121 | local result=1 122 | while [ $attempt -le $max_attempts ]; do 123 | echo "Sending GET request to http://localhost:${test_port}/" 124 | response_code=$(curl -s -w %{http_code} -o /dev/null http://localhost:${test_port}/) 125 | status=$? 126 | if [ $status -eq 0 ]; then 127 | if [ $response_code -eq 200 ]; then 128 | result=0 129 | fi 130 | break 131 | fi 132 | attempt=$(( $attempt + 1 )) 133 | sleep $sleep_time 134 | done 135 | return $result 136 | } 137 | 138 | test_builder_node_version() { 139 | local run_cmd="node --version" 140 | local expected_version="v${NODE_VERSION}" 141 | 142 | echo "Checking nodejs runtime version ..." 143 | out=$(docker run ${BUILDER} /bin/bash -c "${run_cmd}") 144 | if ! echo "${out}" | grep -q "${expected_version}"; then 145 | echo "ERROR[/bin/bash -c "${run_cmd}"] Expected '${expected_version}', got '${out}'" 146 | return 1 147 | fi 148 | 149 | echo "Checking NPM_CONFIG_TARBALL environment variable" 150 | out=$(docker run ${BUILDER} /bin/bash -c 'echo $NPM_CONFIG_TARBALL') 151 | local expected_var="/usr/share/node/node-v${NODE_VERSION}-headers.tar.gz" 152 | if ! echo "${out}" | grep -q "${expected_var}"; then 153 | echo "ERROR[/bin/bash -c "${run_cmd}"] Expected '${expected_var}', got '${out}'" 154 | return 1 155 | fi 156 | } 157 | 158 | test_nss_wrapper() { 159 | read -d '' run_cmd <<-"HERE" 160 | echo 'danbev:x:1000:1000:danbev test:/home/danbev:/bin/false' > passwd && 161 | LD_PRELOAD=libnss_wrapper.so NSS_WRAPPER_PASSWD=passwd NSS_WRAPPER_GROUP=group getent passwd danbev 162 | HERE 163 | echo "Checking nss_wrapper ..." 164 | out=$(docker run ${BUILDER} /bin/bash -c "${run_cmd}" 2>&1) 165 | if echo "${out}" | grep -q "ERROR"; then 166 | echo "ERROR[/bin/bash -c "${run_cmd}"] '${out}'" 167 | return 1 168 | fi 169 | } 170 | 171 | test_node_version() { 172 | local run_cmd="node --version" 173 | local expected="v${NODE_VERSION}" 174 | 175 | echo "Checking nodejs runtime version ..." 176 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}" 2>&1) 177 | if ! echo "${out}" | grep -q "${expected}"; then 178 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 179 | return 1 180 | fi 181 | out=$(docker exec $(cat ${cid_file}) /bin/sh -ic "${run_cmd}" 2>&1) 182 | if ! echo "${out}" | grep -q "${expected}"; then 183 | echo "ERROR[exec /bin/sh -ic "${run_cmd}"] Expected '${expected}', got '${out}'" 184 | return 1 185 | fi 186 | } 187 | 188 | test_directory_permissions() { 189 | local run_cmd="echo 'hello world' > public/index.html && cat public/index.html" 190 | local expected="hello world" 191 | 192 | echo "Checking directory writability ..." 193 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}") 194 | if ! echo "${out}" | grep -q "${expected}"; then 195 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 196 | return 1 197 | fi 198 | } 199 | 200 | test_post_install() { 201 | local run_cmd="ls greeting.js" 202 | local expected="greeting.js" 203 | 204 | echo "Checking post install ..." 205 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}") 206 | if ! echo "${out}" | grep -q "${expected}"; then 207 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 208 | return 1 209 | fi 210 | } 211 | 212 | test_development_dependencies() { 213 | local run_cmd="ls -d node_modules/tape" 214 | local expected="tape" 215 | 216 | echo "Checking development dependencies ..." 217 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}") 218 | if ! echo "${out}" | grep -q "${expected}"; then 219 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 220 | return 1 221 | fi 222 | } 223 | 224 | test_no_development_dependencies() { 225 | local run_cmd="if [ -d node_modules/nodemon ] ; then echo 'exists' ; else echo 'not exists' ; fi" 226 | local expected="not exists" 227 | 228 | echo "Checking development dependencies not installed ..." 229 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}") 230 | if ! echo "${out}" | grep -q "${expected}"; then 231 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 232 | return 1 233 | fi 234 | } 235 | 236 | test_symlinks() { 237 | local run_cmd="test -h node_modules/.bin/tape; echo $?" 238 | local expected="0" 239 | 240 | echo "Checking symlinks ..." 241 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}") 242 | if ! echo "${out}" | grep -q "${expected}"; then 243 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 244 | return 1 245 | fi 246 | } 247 | 248 | test_git_configuration() { 249 | local run_cmd="git config -l" 250 | local expected="url.https://github.com.insteadof=git@github.com: 251 | url.https://.insteadof=ssh:// 252 | url.https://github.com.insteadof=ssh://git@github.com" 253 | 254 | echo "Checking git configuration ..." 255 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}") 256 | if ! echo "${out}" | grep -q "${expected}"; then 257 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 258 | return 1 259 | fi 260 | } 261 | 262 | test_git_clone() { 263 | local run_cmd="git clone https://github.com/nodeshift/world && ls world/index.js" 264 | local expected="world/index.js" 265 | 266 | echo "Checking git clone ..." 267 | out=$(docker exec $(cat ${cid_file}) /bin/bash -c "${run_cmd}") 268 | if ! echo "${out}" | grep -q "${expected}"; then 269 | echo "ERROR[exec /bin/bash -c "${run_cmd}"] Expected '${expected}', got '${out}'" 270 | return 1 271 | fi 272 | } 273 | 274 | test_image_usage_label() { 275 | local expected="s2i build . nodeshift/centos7-s2i-nodejs myapp" 276 | echo "Checking image usage label ..." 277 | out=$(docker inspect --format '{{ index .Config.Labels "usage" }}' $BUILDER) 278 | if ! echo "${out}" | grep -q "${expected}"; then 279 | echo "ERROR[docker inspect --format \"{{ index .Config.Labels \"usage\" }}\"] Expected '${expected}', got '${out}'" 280 | return 1 281 | fi 282 | } 283 | 284 | prepare 285 | test_image_usage_label 286 | check_result $? 287 | 288 | test_builder_node_version 289 | check_result $? 290 | 291 | test_nss_wrapper 292 | check_result $? 293 | 294 | # Build the application image twice to ensure the 'save-artifacts' and 295 | # 'restore-artifacts' scripts are working properly 296 | prepare 297 | run_s2i_build 298 | check_result $? 299 | 300 | run_s2i_build_incremental 301 | check_result $? 302 | 303 | # Verify the 'usage' script is working properly when running the base image with 's2i usage ...' 304 | test_s2i_usage 305 | check_result $? 306 | 307 | # Verify the 'usage' script is working properly when running the base image with 'docker run ...' 308 | test_docker_run_usage 309 | check_result $? 310 | 311 | # Verify that the HTTP connection can be established to test application container 312 | run_test_application & 313 | 314 | # Wait for the container to write it's CID file 315 | wait_for_cid 316 | 317 | test_directory_permissions 318 | check_result $? 319 | 320 | test_post_install 321 | check_result $? 322 | 323 | test_node_version 324 | check_result $? 325 | 326 | test_connection 327 | check_result $? 328 | 329 | test_git_configuration 330 | check_result $? 331 | 332 | test_git_clone 333 | check_result $? 334 | 335 | echo "Testing DEV_MODE=false (default)" 336 | logs=$(container_logs) 337 | echo ${logs} | grep -q DEV_MODE=false 338 | check_result $? 339 | echo ${logs} | grep -q NODE_ENV=production 340 | check_result $? 341 | echo ${logs} | grep -q DEBUG_PORT=5858 342 | check_result $? 343 | test_no_development_dependencies 344 | check_result $? 345 | # The argument to clean up is the DEV_MODE 346 | cleanup false 347 | 348 | run_test_application "-e DEV_MODE=true" & 349 | wait_for_cid 350 | echo "$(cat ${cid_file}) running" 351 | echo "Testing DEV_MODE=true" 352 | logs=$(container_logs) 353 | echo ${logs} | grep -q DEV_MODE=true 354 | check_result $? 355 | echo "Testing NODE_ENV=development" 356 | echo ${logs} | grep -q NODE_ENV=development 357 | check_result $? 358 | echo "Testing DEBUG_PORT=5858" 359 | echo ${logs} | grep -q DEBUG_PORT=5858 360 | check_result $? 361 | # # Ensure that we install dev dependencies in dev mode 362 | sleep 10 363 | echo "Testing dev dependencies" 364 | test_development_dependencies 365 | check_result $? 366 | echo "Testing symlinks" 367 | test_symlinks 368 | check_result $? 369 | 370 | # The argument to clean up is the DEV_MODE 371 | cleanup true 372 | if image_exists ${APP_IMAGE}; then 373 | docker rmi -f ${APP_IMAGE} 374 | # echo "<><><><><><><><><><><> NOT CLEANING UP åå<><><><><><><><><><><>" 375 | fi 376 | 377 | echo "Success!" 378 | -------------------------------------------------------------------------------- /test/test-app/README.md: -------------------------------------------------------------------------------- 1 | node-echo 2 | ========= 3 | 4 | node.js echo server, returns request data to response 5 | 6 | > Based on: https://github.com/bettiolo/node-echo/ 7 | -------------------------------------------------------------------------------- /test/test-app/addon/binding.gyp: -------------------------------------------------------------------------------- 1 | { 2 | "targets": [ 3 | { 4 | "target_name": "addon", 5 | "sources": [ "hello.cc" ] 6 | } 7 | ] 8 | } 9 | -------------------------------------------------------------------------------- /test/test-app/addon/hello.cc: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | namespace demo { 4 | 5 | using v8::FunctionCallbackInfo; 6 | using v8::Isolate; 7 | using v8::Local; 8 | using v8::Object; 9 | using v8::String; 10 | using v8::Value; 11 | 12 | void Method(const FunctionCallbackInfo& args) { 13 | Isolate* isolate = args.GetIsolate(); 14 | args.GetReturnValue().Set(String::NewFromUtf8(isolate, "Hello at")); 15 | } 16 | 17 | void init(Local exports) { 18 | NODE_SET_METHOD(exports, "hello", Method); 19 | } 20 | 21 | NODE_MODULE(NODE_GYP_MODULE_NAME, init) 22 | 23 | } 24 | -------------------------------------------------------------------------------- /test/test-app/greeting.ts: -------------------------------------------------------------------------------- 1 | const addon = require('./addon/build/Release/addon'); 2 | function greeting() { 3 | return `${addon.hello()} ${Date.now()}!` 4 | } 5 | -------------------------------------------------------------------------------- /test/test-app/package-lock.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "node-echo", 3 | "version": "0.0.1", 4 | "lockfileVersion": 1, 5 | "requires": true, 6 | "dependencies": { 7 | "@types/node": { 8 | "version": "9.4.6", 9 | "resolved": "https://registry.npmjs.org/@types/node/-/node-9.4.6.tgz", 10 | "integrity": "sha512-CTUtLb6WqCCgp6P59QintjHWqzf4VL1uPA27bipLAPxFqrtK1gEYllePzTICGqQ8rYsCbpnsNypXjjDzGAAjEQ==" 11 | }, 12 | "abbrev": { 13 | "version": "1.1.1", 14 | "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", 15 | "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==" 16 | }, 17 | "ajv": { 18 | "version": "6.10.0", 19 | "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz", 20 | "integrity": "sha512-nffhOpkymDECQyR0mnsUtoCE8RlX38G0rYP+wgLWFyZuUyuuojSSvi/+euOiQBIn63whYwYVIIH1TvE3tu4OEg==", 21 | "requires": { 22 | "fast-deep-equal": "^2.0.1", 23 | "fast-json-stable-stringify": "^2.0.0", 24 | "json-schema-traverse": "^0.4.1", 25 | "uri-js": "^4.2.2" 26 | } 27 | }, 28 | "ansi-regex": { 29 | "version": "2.1.1", 30 | "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", 31 | "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" 32 | }, 33 | "aproba": { 34 | "version": "1.2.0", 35 | "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", 36 | "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==" 37 | }, 38 | "are-we-there-yet": { 39 | "version": "1.1.5", 40 | "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.5.tgz", 41 | "integrity": "sha512-5hYdAkZlcG8tOLujVDTgCT+uPX0VnpAH28gWsLfzpXYm7wP6mp5Q/gYyR7YQ0cKVJcXJnl3j2kpBan13PtQf6w==", 42 | "requires": { 43 | "delegates": "^1.0.0", 44 | "readable-stream": "^2.0.6" 45 | } 46 | }, 47 | "asn1": { 48 | "version": "0.2.4", 49 | "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", 50 | "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", 51 | "requires": { 52 | "safer-buffer": "~2.1.0" 53 | } 54 | }, 55 | "assert-plus": { 56 | "version": "1.0.0", 57 | "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", 58 | "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" 59 | }, 60 | "asynckit": { 61 | "version": "0.4.0", 62 | "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", 63 | "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" 64 | }, 65 | "aws-sign2": { 66 | "version": "0.7.0", 67 | "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", 68 | "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" 69 | }, 70 | "aws4": { 71 | "version": "1.8.0", 72 | "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", 73 | "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" 74 | }, 75 | "balanced-match": { 76 | "version": "1.0.0", 77 | "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", 78 | "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" 79 | }, 80 | "bcrypt-pbkdf": { 81 | "version": "1.0.2", 82 | "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", 83 | "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", 84 | "requires": { 85 | "tweetnacl": "^0.14.3" 86 | } 87 | }, 88 | "brace-expansion": { 89 | "version": "1.1.11", 90 | "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", 91 | "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", 92 | "requires": { 93 | "balanced-match": "^1.0.0", 94 | "concat-map": "0.0.1" 95 | } 96 | }, 97 | "caseless": { 98 | "version": "0.12.0", 99 | "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", 100 | "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" 101 | }, 102 | "chownr": { 103 | "version": "1.1.1", 104 | "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.1.tgz", 105 | "integrity": "sha512-j38EvO5+LHX84jlo6h4UzmOwi0UgW61WRyPtJz4qaadK5eY3BTS5TY/S1Stc3Uk2lIM6TPevAlULiEJwie860g==" 106 | }, 107 | "code-point-at": { 108 | "version": "1.1.0", 109 | "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", 110 | "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" 111 | }, 112 | "combined-stream": { 113 | "version": "1.0.7", 114 | "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", 115 | "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", 116 | "requires": { 117 | "delayed-stream": "~1.0.0" 118 | } 119 | }, 120 | "concat-map": { 121 | "version": "0.0.1", 122 | "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", 123 | "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" 124 | }, 125 | "console-control-strings": { 126 | "version": "1.1.0", 127 | "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", 128 | "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=" 129 | }, 130 | "core-util-is": { 131 | "version": "1.0.2", 132 | "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", 133 | "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" 134 | }, 135 | "dashdash": { 136 | "version": "1.14.1", 137 | "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", 138 | "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", 139 | "requires": { 140 | "assert-plus": "^1.0.0" 141 | } 142 | }, 143 | "deep-equal": { 144 | "version": "1.0.1", 145 | "resolved": "https://registry.npmjs.org/deep-equal/-/deep-equal-1.0.1.tgz", 146 | "integrity": "sha1-9dJgKStmDghO/0zbyfCK0yR0SLU=", 147 | "dev": true 148 | }, 149 | "define-properties": { 150 | "version": "1.1.2", 151 | "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.2.tgz", 152 | "integrity": "sha1-g6c/L+pWmJj7c3GTyPhzyvbUXJQ=", 153 | "dev": true, 154 | "requires": { 155 | "foreach": "^2.0.5", 156 | "object-keys": "^1.0.8" 157 | } 158 | }, 159 | "defined": { 160 | "version": "1.0.0", 161 | "resolved": "https://registry.npmjs.org/defined/-/defined-1.0.0.tgz", 162 | "integrity": "sha1-yY2bzvdWdBiOEQlpFRGZ45sfppM=", 163 | "dev": true 164 | }, 165 | "delayed-stream": { 166 | "version": "1.0.0", 167 | "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", 168 | "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" 169 | }, 170 | "delegates": { 171 | "version": "1.0.0", 172 | "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", 173 | "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=" 174 | }, 175 | "ecc-jsbn": { 176 | "version": "0.1.2", 177 | "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", 178 | "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", 179 | "requires": { 180 | "jsbn": "~0.1.0", 181 | "safer-buffer": "^2.1.0" 182 | } 183 | }, 184 | "es-abstract": { 185 | "version": "1.10.0", 186 | "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.10.0.tgz", 187 | "integrity": "sha512-/uh/DhdqIOSkAWifU+8nG78vlQxdLckUdI/sPgy0VhuXi2qJ7T8czBmqIYtLQVpCIFYafChnsRsB5pyb1JdmCQ==", 188 | "dev": true, 189 | "requires": { 190 | "es-to-primitive": "^1.1.1", 191 | "function-bind": "^1.1.1", 192 | "has": "^1.0.1", 193 | "is-callable": "^1.1.3", 194 | "is-regex": "^1.0.4" 195 | } 196 | }, 197 | "es-to-primitive": { 198 | "version": "1.1.1", 199 | "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.1.1.tgz", 200 | "integrity": "sha1-RTVSSKiJeQNLZ5Lhm7gfK3l13Q0=", 201 | "dev": true, 202 | "requires": { 203 | "is-callable": "^1.1.1", 204 | "is-date-object": "^1.0.1", 205 | "is-symbol": "^1.0.1" 206 | } 207 | }, 208 | "extend": { 209 | "version": "3.0.2", 210 | "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", 211 | "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" 212 | }, 213 | "extsprintf": { 214 | "version": "1.3.0", 215 | "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", 216 | "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" 217 | }, 218 | "fast-deep-equal": { 219 | "version": "2.0.1", 220 | "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", 221 | "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=" 222 | }, 223 | "fast-json-stable-stringify": { 224 | "version": "2.0.0", 225 | "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", 226 | "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=" 227 | }, 228 | "for-each": { 229 | "version": "0.3.2", 230 | "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", 231 | "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", 232 | "dev": true, 233 | "requires": { 234 | "is-function": "~1.0.0" 235 | } 236 | }, 237 | "foreach": { 238 | "version": "2.0.5", 239 | "resolved": "https://registry.npmjs.org/foreach/-/foreach-2.0.5.tgz", 240 | "integrity": "sha1-C+4AUBiusmDQo6865ljdATbsG5k=", 241 | "dev": true 242 | }, 243 | "forever-agent": { 244 | "version": "0.6.1", 245 | "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", 246 | "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" 247 | }, 248 | "form-data": { 249 | "version": "2.3.3", 250 | "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", 251 | "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", 252 | "requires": { 253 | "asynckit": "^0.4.0", 254 | "combined-stream": "^1.0.6", 255 | "mime-types": "^2.1.12" 256 | } 257 | }, 258 | "fs-minipass": { 259 | "version": "1.2.5", 260 | "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-1.2.5.tgz", 261 | "integrity": "sha512-JhBl0skXjUPCFH7x6x61gQxrKyXsxB5gcgePLZCwfyCGGsTISMoIeObbrvVeP6Xmyaudw4TT43qV2Gz+iyd2oQ==", 262 | "requires": { 263 | "minipass": "^2.2.1" 264 | } 265 | }, 266 | "fs.realpath": { 267 | "version": "1.0.0", 268 | "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", 269 | "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" 270 | }, 271 | "function-bind": { 272 | "version": "1.1.1", 273 | "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", 274 | "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", 275 | "dev": true 276 | }, 277 | "gauge": { 278 | "version": "2.7.4", 279 | "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", 280 | "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", 281 | "requires": { 282 | "aproba": "^1.0.3", 283 | "console-control-strings": "^1.0.0", 284 | "has-unicode": "^2.0.0", 285 | "object-assign": "^4.1.0", 286 | "signal-exit": "^3.0.0", 287 | "string-width": "^1.0.1", 288 | "strip-ansi": "^3.0.1", 289 | "wide-align": "^1.1.0" 290 | } 291 | }, 292 | "getpass": { 293 | "version": "0.1.7", 294 | "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", 295 | "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", 296 | "requires": { 297 | "assert-plus": "^1.0.0" 298 | } 299 | }, 300 | "glob": { 301 | "version": "7.1.2", 302 | "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", 303 | "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", 304 | "requires": { 305 | "fs.realpath": "^1.0.0", 306 | "inflight": "^1.0.4", 307 | "inherits": "2", 308 | "minimatch": "^3.0.4", 309 | "once": "^1.3.0", 310 | "path-is-absolute": "^1.0.0" 311 | } 312 | }, 313 | "graceful-fs": { 314 | "version": "4.1.15", 315 | "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.15.tgz", 316 | "integrity": "sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA==" 317 | }, 318 | "har-schema": { 319 | "version": "2.0.0", 320 | "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", 321 | "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" 322 | }, 323 | "har-validator": { 324 | "version": "5.1.3", 325 | "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", 326 | "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", 327 | "requires": { 328 | "ajv": "^6.5.5", 329 | "har-schema": "^2.0.0" 330 | } 331 | }, 332 | "has": { 333 | "version": "1.0.1", 334 | "resolved": "https://registry.npmjs.org/has/-/has-1.0.1.tgz", 335 | "integrity": "sha1-hGFzP1OLCDfJNh45qauelwTcLyg=", 336 | "dev": true, 337 | "requires": { 338 | "function-bind": "^1.0.2" 339 | } 340 | }, 341 | "has-unicode": { 342 | "version": "2.0.1", 343 | "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", 344 | "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=" 345 | }, 346 | "http-signature": { 347 | "version": "1.2.0", 348 | "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", 349 | "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", 350 | "requires": { 351 | "assert-plus": "^1.0.0", 352 | "jsprim": "^1.2.2", 353 | "sshpk": "^1.7.0" 354 | } 355 | }, 356 | "inflight": { 357 | "version": "1.0.6", 358 | "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", 359 | "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", 360 | "requires": { 361 | "once": "^1.3.0", 362 | "wrappy": "1" 363 | } 364 | }, 365 | "inherits": { 366 | "version": "2.0.3", 367 | "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", 368 | "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" 369 | }, 370 | "is-callable": { 371 | "version": "1.1.3", 372 | "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.3.tgz", 373 | "integrity": "sha1-hut1OSgF3cM69xySoO7fdO52BLI=", 374 | "dev": true 375 | }, 376 | "is-date-object": { 377 | "version": "1.0.1", 378 | "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.1.tgz", 379 | "integrity": "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=", 380 | "dev": true 381 | }, 382 | "is-fullwidth-code-point": { 383 | "version": "1.0.0", 384 | "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", 385 | "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", 386 | "requires": { 387 | "number-is-nan": "^1.0.0" 388 | } 389 | }, 390 | "is-function": { 391 | "version": "1.0.1", 392 | "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", 393 | "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=", 394 | "dev": true 395 | }, 396 | "is-regex": { 397 | "version": "1.0.4", 398 | "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.0.4.tgz", 399 | "integrity": "sha1-VRdIm1RwkbCTDglWVM7SXul+lJE=", 400 | "dev": true, 401 | "requires": { 402 | "has": "^1.0.1" 403 | } 404 | }, 405 | "is-symbol": { 406 | "version": "1.0.1", 407 | "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.1.tgz", 408 | "integrity": "sha1-PMWfAAJRlLarLjjbrmaJJWtmBXI=", 409 | "dev": true 410 | }, 411 | "is-typedarray": { 412 | "version": "1.0.0", 413 | "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", 414 | "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" 415 | }, 416 | "isarray": { 417 | "version": "1.0.0", 418 | "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", 419 | "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" 420 | }, 421 | "isexe": { 422 | "version": "2.0.0", 423 | "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", 424 | "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" 425 | }, 426 | "isstream": { 427 | "version": "0.1.2", 428 | "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", 429 | "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=" 430 | }, 431 | "jsbn": { 432 | "version": "0.1.1", 433 | "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", 434 | "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=" 435 | }, 436 | "json-schema": { 437 | "version": "0.2.3", 438 | "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", 439 | "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" 440 | }, 441 | "json-schema-traverse": { 442 | "version": "0.4.1", 443 | "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", 444 | "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" 445 | }, 446 | "json-stringify-safe": { 447 | "version": "5.0.1", 448 | "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", 449 | "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" 450 | }, 451 | "jsprim": { 452 | "version": "1.4.1", 453 | "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", 454 | "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", 455 | "requires": { 456 | "assert-plus": "1.0.0", 457 | "extsprintf": "1.3.0", 458 | "json-schema": "0.2.3", 459 | "verror": "1.10.0" 460 | } 461 | }, 462 | "mime-db": { 463 | "version": "1.40.0", 464 | "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.40.0.tgz", 465 | "integrity": "sha512-jYdeOMPy9vnxEqFRRo6ZvTZ8d9oPb+k18PKoYNYUe2stVEBPPwsln/qWzdbmaIvnhZ9v2P+CuecK+fpUfsV2mA==" 466 | }, 467 | "mime-types": { 468 | "version": "2.1.24", 469 | "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.24.tgz", 470 | "integrity": "sha512-WaFHS3MCl5fapm3oLxU4eYDw77IQM2ACcxQ9RIxfaC3ooc6PFuBMGZZsYpvoXS5D5QTWPieo1jjLdAm3TBP3cQ==", 471 | "requires": { 472 | "mime-db": "1.40.0" 473 | } 474 | }, 475 | "minimatch": { 476 | "version": "3.0.4", 477 | "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", 478 | "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", 479 | "requires": { 480 | "brace-expansion": "^1.1.7" 481 | } 482 | }, 483 | "minimist": { 484 | "version": "1.2.0", 485 | "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", 486 | "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", 487 | "dev": true 488 | }, 489 | "minipass": { 490 | "version": "2.3.5", 491 | "resolved": "https://registry.npmjs.org/minipass/-/minipass-2.3.5.tgz", 492 | "integrity": "sha512-Gi1W4k059gyRbyVUZQ4mEqLm0YIUiGYfvxhF6SIlk3ui1WVxMTGfGdQ2SInh3PDrRTVvPKgULkpJtT4RH10+VA==", 493 | "requires": { 494 | "safe-buffer": "^5.1.2", 495 | "yallist": "^3.0.0" 496 | } 497 | }, 498 | "minizlib": { 499 | "version": "1.2.1", 500 | "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-1.2.1.tgz", 501 | "integrity": "sha512-7+4oTUOWKg7AuL3vloEWekXY2/D20cevzsrNT2kGWm+39J9hGTCBv8VI5Pm5lXZ/o3/mdR4f8rflAPhnQb8mPA==", 502 | "requires": { 503 | "minipass": "^2.2.1" 504 | } 505 | }, 506 | "mkdirp": { 507 | "version": "0.5.1", 508 | "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", 509 | "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", 510 | "requires": { 511 | "minimist": "0.0.8" 512 | }, 513 | "dependencies": { 514 | "minimist": { 515 | "version": "0.0.8", 516 | "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", 517 | "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" 518 | } 519 | } 520 | }, 521 | "node-gyp": { 522 | "version": "4.0.0", 523 | "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-4.0.0.tgz", 524 | "integrity": "sha512-2XiryJ8sICNo6ej8d0idXDEMKfVfFK7kekGCtJAuelGsYHQxhj13KTf95swTCN2dZ/4lTfZ84Fu31jqJEEgjWA==", 525 | "requires": { 526 | "glob": "^7.0.3", 527 | "graceful-fs": "^4.1.2", 528 | "mkdirp": "^0.5.0", 529 | "nopt": "2 || 3", 530 | "npmlog": "0 || 1 || 2 || 3 || 4", 531 | "osenv": "0", 532 | "request": "^2.87.0", 533 | "rimraf": "2", 534 | "semver": "~5.3.0", 535 | "tar": "^4.4.8", 536 | "which": "1" 537 | } 538 | }, 539 | "nopt": { 540 | "version": "3.0.6", 541 | "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz", 542 | "integrity": "sha1-xkZdvwirzU2zWTF/eaxopkayj/k=", 543 | "requires": { 544 | "abbrev": "1" 545 | } 546 | }, 547 | "npmlog": { 548 | "version": "4.1.2", 549 | "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", 550 | "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", 551 | "requires": { 552 | "are-we-there-yet": "~1.1.2", 553 | "console-control-strings": "~1.1.0", 554 | "gauge": "~2.7.3", 555 | "set-blocking": "~2.0.0" 556 | } 557 | }, 558 | "number-is-nan": { 559 | "version": "1.0.1", 560 | "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", 561 | "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" 562 | }, 563 | "oauth-sign": { 564 | "version": "0.9.0", 565 | "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", 566 | "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" 567 | }, 568 | "object-assign": { 569 | "version": "4.1.1", 570 | "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", 571 | "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" 572 | }, 573 | "object-inspect": { 574 | "version": "1.5.0", 575 | "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.5.0.tgz", 576 | "integrity": "sha512-UmOFbHbwvv+XHj7BerrhVq+knjceBdkvU5AriwLMvhv2qi+e7DJzxfBeFpILEjVzCp+xA+W/pIf06RGPWlZNfw==", 577 | "dev": true 578 | }, 579 | "object-keys": { 580 | "version": "1.0.11", 581 | "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.0.11.tgz", 582 | "integrity": "sha1-xUYBd4rVYPEULODgG8yotW0TQm0=", 583 | "dev": true 584 | }, 585 | "once": { 586 | "version": "1.4.0", 587 | "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", 588 | "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", 589 | "requires": { 590 | "wrappy": "1" 591 | } 592 | }, 593 | "os-homedir": { 594 | "version": "1.0.2", 595 | "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", 596 | "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" 597 | }, 598 | "os-tmpdir": { 599 | "version": "1.0.2", 600 | "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", 601 | "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" 602 | }, 603 | "osenv": { 604 | "version": "0.1.5", 605 | "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.5.tgz", 606 | "integrity": "sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==", 607 | "requires": { 608 | "os-homedir": "^1.0.0", 609 | "os-tmpdir": "^1.0.0" 610 | } 611 | }, 612 | "path-is-absolute": { 613 | "version": "1.0.1", 614 | "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", 615 | "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" 616 | }, 617 | "path-parse": { 618 | "version": "1.0.5", 619 | "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", 620 | "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=", 621 | "dev": true 622 | }, 623 | "performance-now": { 624 | "version": "2.1.0", 625 | "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", 626 | "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" 627 | }, 628 | "process-nextick-args": { 629 | "version": "2.0.0", 630 | "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", 631 | "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" 632 | }, 633 | "psl": { 634 | "version": "1.1.31", 635 | "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", 636 | "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==" 637 | }, 638 | "punycode": { 639 | "version": "2.1.1", 640 | "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", 641 | "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" 642 | }, 643 | "qs": { 644 | "version": "6.5.2", 645 | "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", 646 | "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==" 647 | }, 648 | "readable-stream": { 649 | "version": "2.3.6", 650 | "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", 651 | "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==", 652 | "requires": { 653 | "core-util-is": "~1.0.0", 654 | "inherits": "~2.0.3", 655 | "isarray": "~1.0.0", 656 | "process-nextick-args": "~2.0.0", 657 | "safe-buffer": "~5.1.1", 658 | "string_decoder": "~1.1.1", 659 | "util-deprecate": "~1.0.1" 660 | } 661 | }, 662 | "request": { 663 | "version": "2.88.0", 664 | "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", 665 | "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", 666 | "requires": { 667 | "aws-sign2": "~0.7.0", 668 | "aws4": "^1.8.0", 669 | "caseless": "~0.12.0", 670 | "combined-stream": "~1.0.6", 671 | "extend": "~3.0.2", 672 | "forever-agent": "~0.6.1", 673 | "form-data": "~2.3.2", 674 | "har-validator": "~5.1.0", 675 | "http-signature": "~1.2.0", 676 | "is-typedarray": "~1.0.0", 677 | "isstream": "~0.1.2", 678 | "json-stringify-safe": "~5.0.1", 679 | "mime-types": "~2.1.19", 680 | "oauth-sign": "~0.9.0", 681 | "performance-now": "^2.1.0", 682 | "qs": "~6.5.2", 683 | "safe-buffer": "^5.1.2", 684 | "tough-cookie": "~2.4.3", 685 | "tunnel-agent": "^0.6.0", 686 | "uuid": "^3.3.2" 687 | } 688 | }, 689 | "resolve": { 690 | "version": "1.5.0", 691 | "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.5.0.tgz", 692 | "integrity": "sha512-hgoSGrc3pjzAPHNBg+KnFcK2HwlHTs/YrAGUr6qgTVUZmXv1UEXXl0bZNBKMA9fud6lRYFdPGz0xXxycPzmmiw==", 693 | "dev": true, 694 | "requires": { 695 | "path-parse": "^1.0.5" 696 | } 697 | }, 698 | "resumer": { 699 | "version": "0.0.0", 700 | "resolved": "https://registry.npmjs.org/resumer/-/resumer-0.0.0.tgz", 701 | "integrity": "sha1-8ej0YeQGS6Oegq883CqMiT0HZ1k=", 702 | "dev": true, 703 | "requires": { 704 | "through": "~2.3.4" 705 | } 706 | }, 707 | "rimraf": { 708 | "version": "2.6.3", 709 | "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.3.tgz", 710 | "integrity": "sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==", 711 | "requires": { 712 | "glob": "^7.1.3" 713 | }, 714 | "dependencies": { 715 | "glob": { 716 | "version": "7.1.3", 717 | "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", 718 | "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", 719 | "requires": { 720 | "fs.realpath": "^1.0.0", 721 | "inflight": "^1.0.4", 722 | "inherits": "2", 723 | "minimatch": "^3.0.4", 724 | "once": "^1.3.0", 725 | "path-is-absolute": "^1.0.0" 726 | } 727 | } 728 | } 729 | }, 730 | "safe-buffer": { 731 | "version": "5.1.2", 732 | "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", 733 | "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" 734 | }, 735 | "safer-buffer": { 736 | "version": "2.1.2", 737 | "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", 738 | "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" 739 | }, 740 | "semver": { 741 | "version": "5.3.0", 742 | "resolved": "https://registry.npmjs.org/semver/-/semver-5.3.0.tgz", 743 | "integrity": "sha1-myzl094C0XxgEq0yaqa00M9U+U8=" 744 | }, 745 | "set-blocking": { 746 | "version": "2.0.0", 747 | "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", 748 | "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" 749 | }, 750 | "signal-exit": { 751 | "version": "3.0.2", 752 | "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", 753 | "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" 754 | }, 755 | "sshpk": { 756 | "version": "1.16.1", 757 | "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", 758 | "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", 759 | "requires": { 760 | "asn1": "~0.2.3", 761 | "assert-plus": "^1.0.0", 762 | "bcrypt-pbkdf": "^1.0.0", 763 | "dashdash": "^1.12.0", 764 | "ecc-jsbn": "~0.1.1", 765 | "getpass": "^0.1.1", 766 | "jsbn": "~0.1.0", 767 | "safer-buffer": "^2.0.2", 768 | "tweetnacl": "~0.14.0" 769 | } 770 | }, 771 | "string-width": { 772 | "version": "1.0.2", 773 | "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", 774 | "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", 775 | "requires": { 776 | "code-point-at": "^1.0.0", 777 | "is-fullwidth-code-point": "^1.0.0", 778 | "strip-ansi": "^3.0.0" 779 | } 780 | }, 781 | "string.prototype.trim": { 782 | "version": "1.1.2", 783 | "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.1.2.tgz", 784 | "integrity": "sha1-0E3iyJ4Tf019IG8Ia17S+ua+jOo=", 785 | "dev": true, 786 | "requires": { 787 | "define-properties": "^1.1.2", 788 | "es-abstract": "^1.5.0", 789 | "function-bind": "^1.0.2" 790 | } 791 | }, 792 | "string_decoder": { 793 | "version": "1.1.1", 794 | "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", 795 | "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", 796 | "requires": { 797 | "safe-buffer": "~5.1.0" 798 | } 799 | }, 800 | "strip-ansi": { 801 | "version": "3.0.1", 802 | "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", 803 | "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", 804 | "requires": { 805 | "ansi-regex": "^2.0.0" 806 | } 807 | }, 808 | "tape": { 809 | "version": "4.9.0", 810 | "resolved": "https://registry.npmjs.org/tape/-/tape-4.9.0.tgz", 811 | "integrity": "sha512-j0jO9BiScfqtPBb9QmPLL0qvxXMz98xjkMb7x8lKipFlJZwNJkqkWPou+NU4V6T9RnVh1kuSthLE8gLrN8bBfw==", 812 | "dev": true, 813 | "requires": { 814 | "deep-equal": "~1.0.1", 815 | "defined": "~1.0.0", 816 | "for-each": "~0.3.2", 817 | "function-bind": "~1.1.1", 818 | "glob": "~7.1.2", 819 | "has": "~1.0.1", 820 | "inherits": "~2.0.3", 821 | "minimist": "~1.2.0", 822 | "object-inspect": "~1.5.0", 823 | "resolve": "~1.5.0", 824 | "resumer": "~0.0.0", 825 | "string.prototype.trim": "~1.1.2", 826 | "through": "~2.3.8" 827 | } 828 | }, 829 | "tar": { 830 | "version": "4.4.8", 831 | "resolved": "https://registry.npmjs.org/tar/-/tar-4.4.8.tgz", 832 | "integrity": "sha512-LzHF64s5chPQQS0IYBn9IN5h3i98c12bo4NCO7e0sGM2llXQ3p2FGC5sdENN4cTW48O915Sh+x+EXx7XW96xYQ==", 833 | "requires": { 834 | "chownr": "^1.1.1", 835 | "fs-minipass": "^1.2.5", 836 | "minipass": "^2.3.4", 837 | "minizlib": "^1.1.1", 838 | "mkdirp": "^0.5.0", 839 | "safe-buffer": "^5.1.2", 840 | "yallist": "^3.0.2" 841 | } 842 | }, 843 | "through": { 844 | "version": "2.3.8", 845 | "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", 846 | "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", 847 | "dev": true 848 | }, 849 | "tough-cookie": { 850 | "version": "2.4.3", 851 | "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", 852 | "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", 853 | "requires": { 854 | "psl": "^1.1.24", 855 | "punycode": "^1.4.1" 856 | }, 857 | "dependencies": { 858 | "punycode": { 859 | "version": "1.4.1", 860 | "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", 861 | "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" 862 | } 863 | } 864 | }, 865 | "tunnel-agent": { 866 | "version": "0.6.0", 867 | "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", 868 | "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", 869 | "requires": { 870 | "safe-buffer": "^5.0.1" 871 | } 872 | }, 873 | "tweetnacl": { 874 | "version": "0.14.5", 875 | "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", 876 | "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=" 877 | }, 878 | "typescript": { 879 | "version": "2.7.2", 880 | "resolved": "https://registry.npmjs.org/typescript/-/typescript-2.7.2.tgz", 881 | "integrity": "sha512-p5TCYZDAO0m4G344hD+wx/LATebLWZNkkh2asWUFqSsD2OrDNhbAHuSjobrmsUmdzjJjEeZVU9g1h3O6vpstnw==" 882 | }, 883 | "uri-js": { 884 | "version": "4.2.2", 885 | "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", 886 | "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", 887 | "requires": { 888 | "punycode": "^2.1.0" 889 | } 890 | }, 891 | "util-deprecate": { 892 | "version": "1.0.2", 893 | "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", 894 | "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" 895 | }, 896 | "uuid": { 897 | "version": "3.3.2", 898 | "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", 899 | "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==" 900 | }, 901 | "verror": { 902 | "version": "1.10.0", 903 | "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", 904 | "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", 905 | "requires": { 906 | "assert-plus": "^1.0.0", 907 | "core-util-is": "1.0.2", 908 | "extsprintf": "^1.2.0" 909 | } 910 | }, 911 | "which": { 912 | "version": "1.3.1", 913 | "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", 914 | "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", 915 | "requires": { 916 | "isexe": "^2.0.0" 917 | } 918 | }, 919 | "wide-align": { 920 | "version": "1.1.3", 921 | "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.3.tgz", 922 | "integrity": "sha512-QGkOQc8XL6Bt5PwnsExKBPuMKBxnGxWWW3fU55Xt4feHozMUhdUMaBCk290qpm/wG5u/RSKzwdAC4i51YigihA==", 923 | "requires": { 924 | "string-width": "^1.0.2 || 2" 925 | } 926 | }, 927 | "world": { 928 | "version": "github:nodeshift/world#d741b5a61ee3457aed40cc76789812d70435291e", 929 | "from": "github:nodeshift/world" 930 | }, 931 | "wrappy": { 932 | "version": "1.0.2", 933 | "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", 934 | "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" 935 | }, 936 | "yallist": { 937 | "version": "3.0.3", 938 | "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.0.3.tgz", 939 | "integrity": "sha512-S+Zk8DEWE6oKpV+vI3qWkaK+jSbIK86pCwe2IF/xwIpQ8jEuxpw9NyaGjmp9+BoJv5FV2piqCDcoCtStppiq2A==" 940 | } 941 | } 942 | } 943 | -------------------------------------------------------------------------------- /test/test-app/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "node-echo", 3 | "version": "0.0.1", 4 | "main": "server.js", 5 | "author": "Helio Frota", 6 | "license": "MIT", 7 | "scripts": { 8 | "dev": "nodemon --ignore node_modules/ server.js", 9 | "postinstall": "tsc greeting.ts && node-gyp -C addon configure build", 10 | "start": "node server.js" 11 | }, 12 | "devDependencies": { 13 | "tape": "*" 14 | }, 15 | "dependencies": { 16 | "@types/node": "~9.4.0", 17 | "node-gyp": "^4.0.0", 18 | "typescript": "~2.7.1", 19 | "world": "github:nodeshift/world" 20 | }, 21 | "gypfile": true 22 | } 23 | -------------------------------------------------------------------------------- /test/test-app/public/index.html: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/nodeshift-archived/centos7-s2i-nodejs/dae2ec55bc76e093b6af8281b2024fc0b47fe6d7/test/test-app/public/index.html -------------------------------------------------------------------------------- /test/test-app/server.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | const util = require('util'); 4 | const http = require('http'); 5 | const qs = require('querystring'); 6 | const os = require('os'); 7 | 8 | const port = process.env.PORT || process.env.port || process.env.OPENSHIFT_NODEJS_PORT || 8080; 9 | const ip = process.env.OPENSHIFT_NODEJS_IP || '0.0.0.0'; 10 | 11 | process.on('SIGTERM', function(signal) { 12 | console.log('Server recieved SIGTERM'); 13 | process.exit(222); 14 | }); 15 | 16 | let nodeEnv = process.env.NODE_ENV || 'unknown'; 17 | 18 | const server = http.createServer((req, res) => { 19 | const query = require('url').parse(req.url, true).query; 20 | 21 | let body = ''; 22 | 23 | req.on('data', data => { 24 | body += data; 25 | }); 26 | 27 | req.on('end', () => { 28 | const formattedBody = qs.parse(body); 29 | 30 | res.writeHead(200, { 'Content-Type': 'text/plain' }); 31 | 32 | let out = `This is a node.js echo service 33 | Host: ${req.headers.host} 34 | 35 | node.js Production Mode: ${nodeEnv == 'production' ? 'yes' : 'no'} 36 | 37 | HTTP/${req.httpVersion} 38 | Request headers: 39 | ${util.inspect(req.headers, null)} 40 | Request query: 41 | ${util.inspect(query, null)} 42 | Request body: 43 | ${util.inspect(formattedBody, null)} 44 | Host: ${os.hostname()} 45 | OS Type: ${os.type()} 46 | OS Platform: ${os.platform()} 47 | OS Arch: ${os.arch()} 48 | OS Release: ${os.release()} 49 | OS Uptime: ${os.uptime()} 50 | OS Free memory: ${os.freemem() / 1024 / 1024}mb 51 | OS Total memory: ${os.totalmem() / 1024 / 1024}mb 52 | OS CPU count: ${os.cpus().length} 53 | OS CPU model: ${os.cpus()[0].model} 54 | OS CPU speed: ${os.cpus()[0].speed}mhz 55 | `; 56 | 57 | res.end(out); 58 | }); 59 | }); 60 | 61 | server.listen(port); 62 | 63 | console.log(`Server running on ${ip}:${port}`); 64 | -------------------------------------------------------------------------------- /test/test-app/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | /* Basic Options */ 4 | "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017','ES2018' or 'ESNEXT'. */ 5 | "module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */ 6 | // "lib": [], /* Specify library files to be included in the compilation. */ 7 | // "allowJs": true, /* Allow javascript files to be compiled. */ 8 | // "checkJs": true, /* Report errors in .js files. */ 9 | // "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */ 10 | // "declaration": true, /* Generates corresponding '.d.ts' file. */ 11 | // "sourceMap": true, /* Generates corresponding '.map' file. */ 12 | // "outFile": "./", /* Concatenate and emit output to single file. */ 13 | // "outDir": "./", /* Redirect output structure to the directory. */ 14 | // "rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */ 15 | // "removeComments": true, /* Do not emit comments to output. */ 16 | // "noEmit": true, /* Do not emit outputs. */ 17 | // "importHelpers": true, /* Import emit helpers from 'tslib'. */ 18 | // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ 19 | // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ 20 | 21 | /* Strict Type-Checking Options */ 22 | "strict": true, /* Enable all strict type-checking options. */ 23 | // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ 24 | // "strictNullChecks": true, /* Enable strict null checks. */ 25 | // "strictFunctionTypes": true, /* Enable strict checking of function types. */ 26 | // "strictPropertyInitialization": true, /* Enable strict checking of property initialization in classes. */ 27 | // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ 28 | // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ 29 | 30 | /* Additional Checks */ 31 | // "noUnusedLocals": true, /* Report errors on unused locals. */ 32 | // "noUnusedParameters": true, /* Report errors on unused parameters. */ 33 | // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ 34 | // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ 35 | 36 | /* Module Resolution Options */ 37 | // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ 38 | // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ 39 | // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ 40 | // "rootDirs": [], /* List of root folders whose combined content represents the structure of the project at runtime. */ 41 | // "typeRoots": [], /* List of folders to include type definitions from. */ 42 | // "types": [], /* Type declaration files to be included in compilation. */ 43 | // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ 44 | "esModuleInterop": true /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */ 45 | // "preserveSymlinks": true, /* Do not resolve the real path of symlinks. */ 46 | 47 | /* Source Map Options */ 48 | // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ 49 | // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ 50 | // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ 51 | // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ 52 | 53 | /* Experimental Options */ 54 | // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ 55 | // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ 56 | } 57 | } -------------------------------------------------------------------------------- /versions.mk: -------------------------------------------------------------------------------- 1 | NODE_VERSION=12.10.0 2 | NPM_VERSION=6.10.3 3 | IMAGE_TAG=latest 4 | LTS_TAG= 5 | --------------------------------------------------------------------------------