├── .github ├── ISSUE_TEMPLATE │ ├── bug_report.md │ └── feature_request.md ├── codeql │ └── codeql-config.yml └── workflows │ ├── amplify-plugin-npm-publish.yml │ ├── amplify-plugin-pull-request.yml │ ├── host-plugin-npm-publish.yml │ └── host-plugin-pull-request.yml ├── .vscode └── launch.json ├── CODE_OF_CONDUCT.md ├── CONTRIBUTING.md ├── LICENSE ├── NOTICE ├── README.md ├── THIRD-PARTY-LICENSES.md ├── aws-amplify-publisher-plugin ├── .eslintignore ├── .eslintrc.json ├── .gitignore ├── .prettierignore ├── .prettierrc ├── CONTRIBUTING.md ├── LICENSE ├── NOTICE ├── README.md ├── jest.config.js ├── package-lock.json ├── package.json ├── src │ ├── amplifyPublishDialog.tsx │ ├── amplifyUtils.tsx │ ├── constants.tsx │ ├── failureDialog.tsx │ ├── index.tsx │ ├── inputDialog.tsx │ ├── overwriteDialog.tsx │ ├── preferences.tsx │ ├── progressDialog.tsx │ ├── successDialog.tsx │ ├── toolbar.tsx │ └── utils.tsx ├── test │ └── amplifyUtils.test.ts └── tsconfig.json └── open-source-hosts-plugin ├── .eslintignore ├── .eslintrc.json ├── .gitignore ├── .npmignore ├── CONTRIBUTING.md ├── LICENSE ├── NOTICE ├── README.md ├── config └── SceneRequirements.json ├── jest.config.js ├── package-lock.json ├── package.json ├── scripts └── AwsTools │ ├── AwsCognitoIdConnectorScript.ts │ ├── HelloWorldScript.ts │ ├── IAwsConnector.ts │ └── SumerianHostScript.ts ├── src ├── hostAdder.ts ├── hostMenu.tsx ├── index.tsx ├── toolbar.tsx └── workspace.ts ├── test └── workspace.test.ts ├── tools ├── copyConfig.js └── retrieveHostAssets.js └── tsconfig.json /.github/ISSUE_TEMPLATE/bug_report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Bug report 3 | about: Create a report to help us improve 4 | title: '' 5 | labels: '' 6 | assignees: '' 7 | 8 | --- 9 | 10 | **Describe the bug** 11 | A clear and concise description of what the bug is. 12 | 13 | **To Reproduce** 14 | Steps to reproduce the behavior: 15 | 1. Go to '...' 16 | 2. Click on '....' 17 | 3. Scroll down to '....' 18 | 4. See error 19 | 20 | **Expected behavior** 21 | A clear and concise description of what you expected to happen. 22 | 23 | **Screenshots** 24 | If applicable, add screenshots to help explain your problem. 25 | 26 | **Desktop (please complete the following information):** 27 | - OS: [e.g. iOS] 28 | - Browser [e.g. chrome, safari] 29 | - Version [e.g. 22] 30 | 31 | **Smartphone (please complete the following information):** 32 | - Device: [e.g. iPhone6] 33 | - OS: [e.g. iOS8.1] 34 | - Browser [e.g. stock browser, safari] 35 | - Version [e.g. 22] 36 | 37 | **Additional context** 38 | Add any other context about the problem here. 39 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/feature_request.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Feature request 3 | about: Suggest an idea for this project 4 | title: '' 5 | labels: '' 6 | assignees: '' 7 | 8 | --- 9 | 10 | **Is your feature request related to a problem? Please describe.** 11 | A clear and concise description of what the problem is. Ex. I'm always frustrated when [...] 12 | 13 | **Describe the solution you'd like** 14 | A clear and concise description of what you want to happen. 15 | 16 | **Describe alternatives you've considered** 17 | A clear and concise description of any alternative solutions or features you've considered. 18 | 19 | **Additional context** 20 | Add any other context or screenshots about the feature request here. 21 | -------------------------------------------------------------------------------- /.github/codeql/codeql-config.yml: -------------------------------------------------------------------------------- 1 | paths-ignore: 2 | - '**/packages/**/dist' 3 | - '**/docs_template' -------------------------------------------------------------------------------- /.github/workflows/amplify-plugin-npm-publish.yml: -------------------------------------------------------------------------------- 1 | name: AWS Amplify Publisher NPM Publish 2 | 3 | on: 4 | release: 5 | types: [created] 6 | 7 | defaults: 8 | run: 9 | working-directory: "./aws-amplify-publisher-plugin" 10 | 11 | jobs: 12 | build: 13 | runs-on: ubuntu-latest 14 | steps: 15 | - uses: actions/checkout@v3 16 | # Setup .npmrc file to publish to npm 17 | - uses: actions/setup-node@v3 18 | with: 19 | node-version: '16.x' 20 | registry-url: 'https://registry.npmjs.org' 21 | - run: npm install 22 | - name: "Set version number" 23 | run: | 24 | perl -i -p -e "s/PLUGIN_VERSION = .*/PLUGIN_VERSION = '${{ github.sha }}';/" ${{ github.workspace }}/aws-amplify-publisher-plugin/src/constants.tsx 25 | - run: npm run release 26 | - run: npm publish --access public 27 | env: 28 | NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} -------------------------------------------------------------------------------- /.github/workflows/amplify-plugin-pull-request.yml: -------------------------------------------------------------------------------- 1 | name: Build/test/lint/CodeQL Publish Plugin 2 | 3 | on: 4 | pull_request: 5 | 6 | defaults: 7 | run: 8 | working-directory: "./aws-amplify-publisher-plugin" 9 | jobs: 10 | build: 11 | runs-on: ${{ matrix.os }} 12 | strategy: 13 | matrix: 14 | os: [ubuntu-latest, windows-latest, macos-latest] 15 | fail-fast: false # continue testing on all platforms even if one fails 16 | steps: 17 | - uses: actions/checkout@v3 18 | - name: Initialize CodeQL 19 | uses: github/codeql-action/init@v1 20 | with: 21 | config-file: ./.github/codeql/codeql-config.yml 22 | - uses: actions/setup-node@v1 23 | with: 24 | node-version: "16.x" 25 | registry-url: "https://registry.npmjs.org" 26 | - run: npm install 27 | # Write the commit hash into the constants file, so we get the git hash in the built artifacts 28 | # Believe it or not, the following perl statement works on ubuntu/windows/macos 29 | - name: "Set version number" 30 | run: | 31 | perl -i -p -e "s/PLUGIN_VERSION = .*/PLUGIN_VERSION = '${{ github.sha }}';/" ${{ github.workspace }}/aws-amplify-publisher-plugin/src/constants.tsx 32 | - run: npm run release 33 | - name: Perform CodeQL Analysis 34 | if: matrix.os == 'ubuntu-latest' # we only need to run this check on one platform 35 | uses: github/codeql-action/analyze@v1 36 | -------------------------------------------------------------------------------- /.github/workflows/host-plugin-npm-publish.yml: -------------------------------------------------------------------------------- 1 | name: Open Source Host NPM Publish 2 | 3 | on: 4 | release: 5 | types: [created] 6 | 7 | defaults: 8 | run: 9 | working-directory: "./open-source-hosts-plugin" 10 | 11 | jobs: 12 | build: 13 | runs-on: ubuntu-latest 14 | steps: 15 | - uses: actions/checkout@v3 16 | # Setup .npmrc file to publish to npm 17 | - uses: actions/setup-node@v3 18 | with: 19 | node-version: '16.x' 20 | registry-url: 'https://registry.npmjs.org' 21 | - run: npm install 22 | - name: "Set version number" 23 | run: | 24 | perl -i -p -e "s/PLUGIN_VERSION = .*/PLUGIN_VERSION = '${{ github.sha }}';/" ${{ github.workspace }}/open-source-hosts-plugin/scripts/sumerianhost.ts 25 | - run: npm run release 26 | - run: npm publish --access public 27 | env: 28 | NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} -------------------------------------------------------------------------------- /.github/workflows/host-plugin-pull-request.yml: -------------------------------------------------------------------------------- 1 | name: Build/test/lint/CodeQL Host Plugin 2 | 3 | on: 4 | pull_request: 5 | 6 | jobs: 7 | build: 8 | runs-on: ${{ matrix.os }} 9 | strategy: 10 | matrix: 11 | os: [ubuntu-latest, windows-latest, macos-latest] 12 | fail-fast: false # continue testing on all platforms even if one fails 13 | steps: 14 | - uses: actions/checkout@v3 15 | - name: Initialize CodeQL 16 | uses: github/codeql-action/init@v1 17 | with: 18 | config-file: ./.github/codeql/codeql-config.yml 19 | # Write the commit hash into the script file, so we get the git hash in the built artifacts 20 | # Believe it or not, the following perl statement works on ubuntu/windows/macos 21 | - name: "Set version number" 22 | run: | 23 | perl -i -p -e "s/PLUGIN_VERSION = .*/PLUGIN_VERSION = '${{ github.sha }}';/" ${{ github.workspace }}/open-source-hosts-plugin/scripts/AwsTools/SumerianHostScript.ts 24 | - run: npm install 25 | working-directory: "./open-source-hosts-plugin" 26 | - run: npm run release 27 | working-directory: "./open-source-hosts-plugin" 28 | - name: Perform CodeQL Analysis 29 | if: matrix.os == 'ubuntu-latest' # we only need to run this check on one platform 30 | uses: github/codeql-action/analyze@v1 31 | -------------------------------------------------------------------------------- /.vscode/launch.json: -------------------------------------------------------------------------------- 1 | { 2 | // Use IntelliSense to learn about possible attributes. 3 | // Hover to view descriptions of existing attributes. 4 | // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 5 | "version": "0.2.0", 6 | "configurations": [ 7 | { 8 | "type": "pwa-chrome", 9 | "request": "launch", 10 | "name": "Launch Chrome against localhost", 11 | "url": "http://localhost:1338/", 12 | "webRoot": "${workspaceFolder}" 13 | } 14 | ] 15 | } -------------------------------------------------------------------------------- /CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | ## Code of Conduct 2 | This project has adopted the [Amazon Open Source Code of Conduct](https://aws.github.io/code-of-conduct). 3 | For more information see the [Code of Conduct FAQ](https://aws.github.io/code-of-conduct-faq) or contact 4 | opensource-codeofconduct@amazon.com with any additional questions or comments. 5 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing Guidelines and Workflow 2 | 3 | Thank you for your interest in contributing to our project. Whether it's a bug report, new feature, correction, or additional documentation, we greatly value feedback and contributions from our community. 4 | 5 | Please read through this document before editing the code base, submitting any issues, or submitting pull requests to ensure we have all the necessary information to effectively respond to your bug report or contribution. 6 | 7 | **In this document:** 8 | 9 | - [Contributor Guidelines](#contributor-guidelines) 10 | - [Contributor Workflow](#contributor-workflow) 11 | - [Maintainer Workflow](#maintainer-workflow) 12 | 13 | --- 14 | 15 | ## [Contributor Guidelines](#contributor-guidelines) 16 | 17 | ### Reporting Bugs or Feature Requests 18 | 19 | We welcome you to use the GitHub issue tracker to report bugs or suggest features. 20 | 21 | When filing an issue, please check existing open, or recently closed, issues to make sure somebody else hasn't already reported the issue. Please try to include as much information as you can. Details like these are incredibly useful: 22 | 23 | - A reproducible test case or series of steps 24 | - The version of our code being used 25 | - Any modifications you've made relevant to the bug 26 | - Anything unusual about your environment or deployment 27 | 28 | ### Reporting Security Issues 29 | 30 | If you discover a potential security issue in this project we ask that you notify AWS/Amazon Security via our [vulnerability reporting page](http://aws.amazon.com/security/vulnerability-reporting/). Please do **not** create a public GitHub issue. 31 | 32 | ### Finding Contributions to Work On 33 | 34 | Looking at the existing issues is a great way to find something to contribute on. As our projects, by default, use the default GitHub issue labels (enhancement/bug/duplicate/help wanted/invalid/question/wontfix), looking at any 'help wanted' issues is a great place to start. 35 | 36 | ### Code of Conduct 37 | 38 | This project has adopted the [Amazon Open Source Code of Conduct](https://aws.github.io/code-of-conduct). For more information see the [Code of Conduct FAQ](https://aws.github.io/code-of-conduct-faq) or contact opensource-codeofconduct@amazon.com with any additional questions or comments. 39 | 40 | ### Licensing 41 | 42 | See the [LICENSE](LICENSE) file for our project's licensing. We will ask you to confirm the licensing of your contribution. 43 | 44 | We may ask you to sign a [Contributor License Agreement (CLA)](http://en.wikipedia.org/wiki/Contributor_License_Agreement) for larger changes. 45 | 46 | --- 47 | 48 | ## [Contributor Workflow](#contributor-workflow) 49 | 50 | ### Prerequisites 51 | 52 | - Read through [CONTRIBUTING](CONTRIBUTING.md) 53 | - Install [Babylon.JS Editor](http://editor.babylonjs.com/) 54 | - Install [Git](https://git-scm.com/book/en/v2/Getting-Started-Installing-Git) 55 | - Git 2.26 or above recommended 56 | - Install [Node.js and npm](https://docs.npmjs.com/downloading-and-installing-node-js-and-npm) 57 | - Recommended: Node.js 16 and npm 8. 58 | 59 | ### Initial Setup 60 | 61 | 1. Clone the primary repository 62 | 63 | ``` 64 | git clone https://github.com/aws-samples/aws-tools-for-babylonjs-editor.git 65 | ``` 66 | 67 | From here, you will have access to all of the packages that are in the repository. 68 | 69 | ### Building and Testing 70 | 71 | AWS Tools for Babylon.JS Editor is divided into multiple packages, where the root directory does not actually compile or build itself. Refer to the individual folder's CONTRIBUTING for further instructions on how to build and test. 72 | 73 | - [AWS Tools: AWS Amplify Publisher Plugin](aws-amplify-publisher-plugin/CONTRIBUTING.md#contributor-workflow) 74 | - [AWS Tools: Open Source Hosts Plugin](open-source-hosts-plugin/CONTRIBUTING.md#contributor-workflow) 75 | 76 | ### Submitting Pull Requests 77 | 78 | Contributions via pull requests are much appreciated. Before sending us a pull request, please ensure that: 79 | 80 | 1. You are working against the latest source on the _main_ branch. 81 | 2. You check existing open and recently merged pull requests to make sure someone else hasn't addressed the problem already. 82 | 3. You open an issue to discuss any significant work - we would hate for your time to be wasted. 83 | 84 | To send us a pull request, please: 85 | 86 | 1. Fork the repository. 87 | 2. Modify the source; please focus on the specific change you are contributing. If you also reformat all the code, it will be hard for us to focus on your change. 88 | 3. Ensure local tests pass. 89 | 4. Commit to your fork using clear commit messages. 90 | 5. Send us a pull request, answering any default questions in the pull request interface. 91 | 6. Pay attention to any automated CI failures reported in the pull request, and stay involved in the conversation. 92 | 93 | GitHub provides additional documentation on [forking a repository](https://help.github.com/articles/fork-a-repo/) and [creating a pull request](https://help.github.com/articles/creating-a-pull-request/). 94 | 95 | --- 96 | 97 | ## [Maintainer Workflow](#maintainer-workflow) 98 | 99 | ### Publishing to NPM 100 | 101 | All packages are all published and distributed via the [npmjs.com](https://www.npmjs.com/) registry. To publish a new version of the packages to the NPM registry, follow these steps... 102 | 103 | 1. Update the package.json for each package with new version number using [semantic versioning](https://semver.org/). All packages should always share the same version number. 104 | 2. Create a new release using the GitHub.com console. See [previous releases](https://github.com/aws-samples/aws-tools-for-babylonjs-editor/releases) for reference. 105 | 1. In the release creation form, create a new repository tag labeling it using the package version number prefixed with "v". _Example: "v2.1.3"_ 106 | 2. Set the target of the release to the `main` branch. 107 | 3. Set the title of the release to match the tag name. _Example: "v2.1.3"_ 108 | 4. In the release description field, add a heading in the form **"AWS Tools for Babylon.JS Editor Release _{version number}_ - _{Reason for Release}_"**. Example: _"AWS Tools for Babylon.JS Editor Release 1.3.1 - Bug Fixes"_ 109 | 5. Append all significant changes as bullet points. 110 | 3. Click "Publish release". This will automatically trigger a GitHub Action that publishes the release to the NPM registry. 111 | 4. Validate the GitHub properly releases to NPM through Actions tab. 112 | -------------------------------------------------------------------------------- /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 | -------------------------------------------------------------------------------- /NOTICE: -------------------------------------------------------------------------------- 1 | Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # AWS Tools for Babylon.JS Editor 2 | 3 | AWS Tools for Babylon.JS Editor is a suite of tools meant to interact with [Babylon.JS Editor](http://editor.babylonjs.com/) by utilizing the capabilities of AWS products. 4 | 5 | This repository contains a number of useful packages to achieve this: 6 | 7 | - [AWS Tools for Babylon.JS Editor: AWS Amplify Publisher Plugin (AWS Tools: AWS Amplify Publisher Plugin)](aws-amplify-publisher-plugin) - A plugin that enables one-click publishing to AWS Amplify from Babylon.JS Editor. 8 | - [AWS Tools for Babylon.JS Editor: Open Source Hosts Plugin (AWS Tools: Open Source Hosts Plugin)](open-source-hosts-plugin) - A plugin that enables BabylonJS Editor workflows with Amazon Sumerian Hosts. 9 | 10 | Each of these packages can be utilized individually to enhance the Babylon.JS Editor in its own way. For more detailed information on the what each package does, click their link above. 11 | 12 | ## Security 13 | 14 | See [CONTRIBUTING](CONTRIBUTING.md#security-issue-notifications) for more information. 15 | 16 | ## License 17 | 18 | This project is licensed under the Apache-2.0 License. See the [LICENSE](LICENSE) file. 19 | 20 | ## Installation 21 | 22 | AWS Tools for Babylon.JS Editor is divided into multiple packages, and each package has its own installation instructions. Refer to their README for further instructions on how to install 23 | 24 | - [AWS Tools: AWS Amplify Publisher Plugin](aws-amplify-publisher-plugin/README.md#installation) 25 | - [AWS Tools: Open Source Hosts Plugin](open-source-hosts-plugin/README.md#installation) 26 | 27 | -------------------------------------------------------------------------------- /THIRD-PARTY-LICENSES.md: -------------------------------------------------------------------------------- 1 | \*\* AWS SDK for Javascript; version 2.1096.0 -- https://github.com/aws/aws-sdk-js 2 | 3 | Apache License 4 | Version 2.0, January 2004 5 | http://www.apache.org/licenses/ 6 | 7 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 8 | 9 | 1. Definitions. 10 | 11 | "License" shall mean the terms and conditions for use, reproduction, 12 | and distribution as defined by Sections 1 through 9 of this document. 13 | 14 | "Licensor" shall mean the copyright owner or entity authorized by 15 | the copyright owner that is granting the License. 16 | 17 | "Legal Entity" shall mean the union of the acting entity and all 18 | other entities that control, are controlled by, or are under common 19 | control with that entity. For the purposes of this definition, 20 | "control" means (i) the power, direct or indirect, to cause the 21 | direction or management of such entity, whether by contract or 22 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 23 | outstanding shares, or (iii) beneficial ownership of such entity. 24 | 25 | "You" (or "Your") shall mean an individual or Legal Entity 26 | exercising permissions granted by this License. 27 | 28 | "Source" form shall mean the preferred form for making modifications, 29 | including but not limited to software source code, documentation 30 | source, and configuration files. 31 | 32 | "Object" form shall mean any form resulting from mechanical 33 | transformation or translation of a Source form, including but 34 | not limited to compiled object code, generated documentation, 35 | and conversions to other media types. 36 | 37 | "Work" shall mean the work of authorship, whether in Source or 38 | Object form, made available under the License, as indicated by a 39 | copyright notice that is included in or attached to the work 40 | (an example is provided in the Appendix below). 41 | 42 | "Derivative Works" shall mean any work, whether in Source or Object 43 | form, that is based on (or derived from) the Work and for which the 44 | editorial revisions, annotations, elaborations, or other modifications 45 | represent, as a whole, an original work of authorship. For the purposes 46 | of this License, Derivative Works shall not include works that remain 47 | separable from, or merely link (or bind by name) to the interfaces of, 48 | the Work and Derivative Works thereof. 49 | 50 | "Contribution" shall mean any work of authorship, including 51 | the original version of the Work and any modifications or additions 52 | to that Work or Derivative Works thereof, that is intentionally 53 | submitted to Licensor for inclusion in the Work by the copyright owner 54 | or by an individual or Legal Entity authorized to submit on behalf of 55 | the copyright owner. For the purposes of this definition, "submitted" 56 | means any form of electronic, verbal, or written communication sent 57 | to the Licensor or its representatives, including but not limited to 58 | communication on electronic mailing lists, source code control systems, 59 | and issue tracking systems that are managed by, or on behalf of, the 60 | Licensor for the purpose of discussing and improving the Work, but 61 | excluding communication that is conspicuously marked or otherwise 62 | designated in writing by the copyright owner as "Not a Contribution." 63 | 64 | "Contributor" shall mean Licensor and any individual or Legal Entity 65 | on behalf of whom a Contribution has been received by Licensor and 66 | subsequently incorporated within the Work. 67 | 68 | 2. Grant of Copyright License. Subject to the terms and conditions of 69 | this License, each Contributor hereby grants to You a perpetual, 70 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 71 | copyright license to reproduce, prepare Derivative Works of, 72 | publicly display, publicly perform, sublicense, and distribute the 73 | Work and such Derivative Works in Source or Object form. 74 | 75 | 3. Grant of Patent License. Subject to the terms and conditions of 76 | this License, each Contributor hereby grants to You a perpetual, 77 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 78 | (except as stated in this section) patent license to make, have made, 79 | use, offer to sell, sell, import, and otherwise transfer the Work, 80 | where such license applies only to those patent claims licensable 81 | by such Contributor that are necessarily infringed by their 82 | Contribution(s) alone or by combination of their Contribution(s) 83 | with the Work to which such Contribution(s) was submitted. If You 84 | institute patent litigation against any entity (including a 85 | cross-claim or counterclaim in a lawsuit) alleging that the Work 86 | or a Contribution incorporated within the Work constitutes direct 87 | or contributory patent infringement, then any patent licenses 88 | granted to You under this License for that Work shall terminate 89 | as of the date such litigation is filed. 90 | 91 | 4. Redistribution. You may reproduce and distribute copies of the 92 | Work or Derivative Works thereof in any medium, with or without 93 | modifications, and in Source or Object form, provided that You 94 | meet the following conditions: 95 | 96 | (a) You must give any other recipients of the Work or 97 | Derivative Works a copy of this License; and 98 | 99 | (b) You must cause any modified files to carry prominent notices 100 | stating that You changed the files; and 101 | 102 | (c) You must retain, in the Source form of any Derivative Works 103 | that You distribute, all copyright, patent, trademark, and 104 | attribution notices from the Source form of the Work, 105 | excluding those notices that do not pertain to any part of 106 | the Derivative Works; and 107 | 108 | (d) If the Work includes a "NOTICE" text file as part of its 109 | distribution, then any Derivative Works that You distribute must 110 | include a readable copy of the attribution notices contained 111 | within such NOTICE file, excluding those notices that do not 112 | pertain to any part of the Derivative Works, in at least one 113 | of the following places: within a NOTICE text file distributed 114 | as part of the Derivative Works; within the Source form or 115 | documentation, if provided along with the Derivative Works; or, 116 | within a display generated by the Derivative Works, if and 117 | wherever such third-party notices normally appear. The contents 118 | of the NOTICE file are for informational purposes only and 119 | do not modify the License. You may add Your own attribution 120 | notices within Derivative Works that You distribute, alongside 121 | or as an addendum to the NOTICE text from the Work, provided 122 | that such additional attribution notices cannot be construed 123 | as modifying the License. 124 | 125 | You may add Your own copyright statement to Your modifications and 126 | may provide additional or different license terms and conditions 127 | for use, reproduction, or distribution of Your modifications, or 128 | for any such Derivative Works as a whole, provided Your use, 129 | reproduction, and distribution of the Work otherwise complies with 130 | the conditions stated in this License. 131 | 132 | 5. Submission of Contributions. Unless You explicitly state otherwise, 133 | any Contribution intentionally submitted for inclusion in the Work 134 | by You to the Licensor shall be under the terms and conditions of 135 | this License, without any additional terms or conditions. 136 | Notwithstanding the above, nothing herein shall supersede or modify 137 | the terms of any separate license agreement you may have executed 138 | with Licensor regarding such Contributions. 139 | 140 | 6. Trademarks. This License does not grant permission to use the trade 141 | names, trademarks, service marks, or product names of the Licensor, 142 | except as required for reasonable and customary use in describing the 143 | origin of the Work and reproducing the content of the NOTICE file. 144 | 145 | 7. Disclaimer of Warranty. Unless required by applicable law or 146 | agreed to in writing, Licensor provides the Work (and each 147 | Contributor provides its Contributions) on an "AS IS" BASIS, 148 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 149 | implied, including, without limitation, any warranties or conditions 150 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 151 | PARTICULAR PURPOSE. You are solely responsible for determining the 152 | appropriateness of using or redistributing the Work and assume any 153 | risks associated with Your exercise of permissions under this License. 154 | 155 | 8. Limitation of Liability. In no event and under no legal theory, 156 | whether in tort (including negligence), contract, or otherwise, 157 | unless required by applicable law (such as deliberate and grossly 158 | negligent acts) or agreed to in writing, shall any Contributor be 159 | liable to You for damages, including any direct, indirect, special, 160 | incidental, or consequential damages of any character arising as a 161 | result of this License or out of the use or inability to use the 162 | Work (including but not limited to damages for loss of goodwill, 163 | work stoppage, computer failure or malfunction, or any and all 164 | other commercial damages or losses), even if such Contributor 165 | has been advised of the possibility of such damages. 166 | 167 | 9. Accepting Warranty or Additional Liability. While redistributing 168 | the Work or Derivative Works thereof, You may choose to offer, 169 | and charge a fee for, acceptance of support, warranty, indemnity, 170 | or other liability obligations and/or rights consistent with this 171 | License. However, in accepting such obligations, You may act only 172 | on Your own behalf and on Your sole responsibility, not on behalf 173 | of any other Contributor, and only if You agree to indemnify, 174 | defend, and hold each Contributor harmless for any liability 175 | incurred by, or claims asserted against, such Contributor by reason 176 | of your accepting any such warranty or additional liability. 177 | 178 | END OF TERMS AND CONDITIONS 179 | 180 | APPENDIX: How to apply the Apache License to your work. 181 | 182 | To apply the Apache License to your work, attach the following 183 | boilerplate notice, with the fields enclosed by brackets "[]" 184 | replaced with your own identifying information. (Don't include 185 | the brackets!) The text should be enclosed in the appropriate 186 | comment syntax for the file format. We also recommend that a 187 | file or class name and description of purpose be included on the 188 | same "printed page" as the copyright notice for easier 189 | identification within third-party archives. 190 | 191 | Copyright 2012-2017 Amazon.com, Inc. or its affiliates. All Rights Reserved. 192 | 193 | Licensed under the Apache License, Version 2.0 (the "License"); 194 | you may not use this file except in compliance with the License. 195 | You may obtain a copy of the License at 196 | 197 | http://www.apache.org/licenses/LICENSE-2.0 198 | 199 | Unless required by applicable law or agreed to in writing, software 200 | distributed under the License is distributed on an "AS IS" BASIS, 201 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 202 | See the License for the specific language governing permissions and 203 | limitations under the License. 204 | 205 | - For AWS SDK for Javascript see also this required NOTICE: 206 | AWS SDK for JavaScript 207 | Copyright 2012-2017 Amazon.com, Inc. or its affiliates. All Rights Reserved. 208 | 209 | This product includes software developed at 210 | Amazon Web Services, Inc. (http://aws.amazon.com/). 211 | 212 | --- 213 | 214 | \*\* @aws-sdk/client-amplify; version 3.53.0 -- https://github.com/aws/aws-sdk-js-v3 215 | 216 | Apache License 217 | Version 2.0, January 2004 218 | http://www.apache.org/licenses/ 219 | 220 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 221 | 222 | 1. Definitions. 223 | 224 | "License" shall mean the terms and conditions for use, reproduction, 225 | and distribution as defined by Sections 1 through 9 of this document. 226 | 227 | "Licensor" shall mean the copyright owner or entity authorized by 228 | the copyright owner that is granting the License. 229 | 230 | "Legal Entity" shall mean the union of the acting entity and all 231 | other entities that control, are controlled by, or are under common 232 | control with that entity. For the purposes of this definition, 233 | "control" means (i) the power, direct or indirect, to cause the 234 | direction or management of such entity, whether by contract or 235 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 236 | outstanding shares, or (iii) beneficial ownership of such entity. 237 | 238 | "You" (or "Your") shall mean an individual or Legal Entity 239 | exercising permissions granted by this License. 240 | 241 | "Source" form shall mean the preferred form for making modifications, 242 | including but not limited to software source code, documentation 243 | source, and configuration files. 244 | 245 | "Object" form shall mean any form resulting from mechanical 246 | transformation or translation of a Source form, including but 247 | not limited to compiled object code, generated documentation, 248 | and conversions to other media types. 249 | 250 | "Work" shall mean the work of authorship, whether in Source or 251 | Object form, made available under the License, as indicated by a 252 | copyright notice that is included in or attached to the work 253 | (an example is provided in the Appendix below). 254 | 255 | "Derivative Works" shall mean any work, whether in Source or Object 256 | form, that is based on (or derived from) the Work and for which the 257 | editorial revisions, annotations, elaborations, or other modifications 258 | represent, as a whole, an original work of authorship. For the purposes 259 | of this License, Derivative Works shall not include works that remain 260 | separable from, or merely link (or bind by name) to the interfaces of, 261 | the Work and Derivative Works thereof. 262 | 263 | "Contribution" shall mean any work of authorship, including 264 | the original version of the Work and any modifications or additions 265 | to that Work or Derivative Works thereof, that is intentionally 266 | submitted to Licensor for inclusion in the Work by the copyright owner 267 | or by an individual or Legal Entity authorized to submit on behalf of 268 | the copyright owner. For the purposes of this definition, "submitted" 269 | means any form of electronic, verbal, or written communication sent 270 | to the Licensor or its representatives, including but not limited to 271 | communication on electronic mailing lists, source code control systems, 272 | and issue tracking systems that are managed by, or on behalf of, the 273 | Licensor for the purpose of discussing and improving the Work, but 274 | excluding communication that is conspicuously marked or otherwise 275 | designated in writing by the copyright owner as "Not a Contribution." 276 | 277 | "Contributor" shall mean Licensor and any individual or Legal Entity 278 | on behalf of whom a Contribution has been received by Licensor and 279 | subsequently incorporated within the Work. 280 | 281 | 2. Grant of Copyright License. Subject to the terms and conditions of 282 | this License, each Contributor hereby grants to You a perpetual, 283 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 284 | copyright license to reproduce, prepare Derivative Works of, 285 | publicly display, publicly perform, sublicense, and distribute the 286 | Work and such Derivative Works in Source or Object form. 287 | 288 | 3. Grant of Patent License. Subject to the terms and conditions of 289 | this License, each Contributor hereby grants to You a perpetual, 290 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 291 | (except as stated in this section) patent license to make, have made, 292 | use, offer to sell, sell, import, and otherwise transfer the Work, 293 | where such license applies only to those patent claims licensable 294 | by such Contributor that are necessarily infringed by their 295 | Contribution(s) alone or by combination of their Contribution(s) 296 | with the Work to which such Contribution(s) was submitted. If You 297 | institute patent litigation against any entity (including a 298 | cross-claim or counterclaim in a lawsuit) alleging that the Work 299 | or a Contribution incorporated within the Work constitutes direct 300 | or contributory patent infringement, then any patent licenses 301 | granted to You under this License for that Work shall terminate 302 | as of the date such litigation is filed. 303 | 304 | 4. Redistribution. You may reproduce and distribute copies of the 305 | Work or Derivative Works thereof in any medium, with or without 306 | modifications, and in Source or Object form, provided that You 307 | meet the following conditions: 308 | 309 | (a) You must give any other recipients of the Work or 310 | Derivative Works a copy of this License; and 311 | 312 | (b) You must cause any modified files to carry prominent notices 313 | stating that You changed the files; and 314 | 315 | (c) You must retain, in the Source form of any Derivative Works 316 | that You distribute, all copyright, patent, trademark, and 317 | attribution notices from the Source form of the Work, 318 | excluding those notices that do not pertain to any part of 319 | the Derivative Works; and 320 | 321 | (d) If the Work includes a "NOTICE" text file as part of its 322 | distribution, then any Derivative Works that You distribute must 323 | include a readable copy of the attribution notices contained 324 | within such NOTICE file, excluding those notices that do not 325 | pertain to any part of the Derivative Works, in at least one 326 | of the following places: within a NOTICE text file distributed 327 | as part of the Derivative Works; within the Source form or 328 | documentation, if provided along with the Derivative Works; or, 329 | within a display generated by the Derivative Works, if and 330 | wherever such third-party notices normally appear. The contents 331 | of the NOTICE file are for informational purposes only and 332 | do not modify the License. You may add Your own attribution 333 | notices within Derivative Works that You distribute, alongside 334 | or as an addendum to the NOTICE text from the Work, provided 335 | that such additional attribution notices cannot be construed 336 | as modifying the License. 337 | 338 | You may add Your own copyright statement to Your modifications and 339 | may provide additional or different license terms and conditions 340 | for use, reproduction, or distribution of Your modifications, or 341 | for any such Derivative Works as a whole, provided Your use, 342 | reproduction, and distribution of the Work otherwise complies with 343 | the conditions stated in this License. 344 | 345 | 5. Submission of Contributions. Unless You explicitly state otherwise, 346 | any Contribution intentionally submitted for inclusion in the Work 347 | by You to the Licensor shall be under the terms and conditions of 348 | this License, without any additional terms or conditions. 349 | Notwithstanding the above, nothing herein shall supersede or modify 350 | the terms of any separate license agreement you may have executed 351 | with Licensor regarding such Contributions. 352 | 353 | 6. Trademarks. This License does not grant permission to use the trade 354 | names, trademarks, service marks, or product names of the Licensor, 355 | except as required for reasonable and customary use in describing the 356 | origin of the Work and reproducing the content of the NOTICE file. 357 | 358 | 7. Disclaimer of Warranty. Unless required by applicable law or 359 | agreed to in writing, Licensor provides the Work (and each 360 | Contributor provides its Contributions) on an "AS IS" BASIS, 361 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 362 | implied, including, without limitation, any warranties or conditions 363 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 364 | PARTICULAR PURPOSE. You are solely responsible for determining the 365 | appropriateness of using or redistributing the Work and assume any 366 | risks associated with Your exercise of permissions under this License. 367 | 368 | 8. Limitation of Liability. In no event and under no legal theory, 369 | whether in tort (including negligence), contract, or otherwise, 370 | unless required by applicable law (such as deliberate and grossly 371 | negligent acts) or agreed to in writing, shall any Contributor be 372 | liable to You for damages, including any direct, indirect, special, 373 | incidental, or consequential damages of any character arising as a 374 | result of this License or out of the use or inability to use the 375 | Work (including but not limited to damages for loss of goodwill, 376 | work stoppage, computer failure or malfunction, or any and all 377 | other commercial damages or losses), even if such Contributor 378 | has been advised of the possibility of such damages. 379 | 380 | 9. Accepting Warranty or Additional Liability. While redistributing 381 | the Work or Derivative Works thereof, You may choose to offer, 382 | and charge a fee for, acceptance of support, warranty, indemnity, 383 | or other liability obligations and/or rights consistent with this 384 | License. However, in accepting such obligations, You may act only 385 | on Your own behalf and on Your sole responsibility, not on behalf 386 | of any other Contributor, and only if You agree to indemnify, 387 | defend, and hold each Contributor harmless for any liability 388 | incurred by, or claims asserted against, such Contributor by reason 389 | of your accepting any such warranty or additional liability. 390 | 391 | END OF TERMS AND CONDITIONS 392 | 393 | APPENDIX: How to apply the Apache License to your work. 394 | 395 | To apply the Apache License to your work, attach the following 396 | boilerplate notice, with the fields enclosed by brackets "{}" 397 | replaced with your own identifying information. (Don't include 398 | the brackets!) The text should be enclosed in the appropriate 399 | comment syntax for the file format. We also recommend that a 400 | file or class name and description of purpose be included on the 401 | same "printed page" as the copyright notice for easier 402 | identification within third-party archives. 403 | 404 | Copyright 2018-2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. 405 | 406 | Licensed under the Apache License, Version 2.0 (the "License"); 407 | you may not use this file except in compliance with the License. 408 | You may obtain a copy of the License at 409 | 410 | http://www.apache.org/licenses/LICENSE-2.0 411 | 412 | Unless required by applicable law or agreed to in writing, software 413 | distributed under the License is distributed on an "AS IS" BASIS, 414 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 415 | See the License for the specific language governing permissions and 416 | limitations under the License. 417 | 418 | - For @aws-sdk/client-amplify see also this required NOTICE: 419 | AWS SDK for JavaScript v3 420 | Copyright 2012-2017 Amazon.com, Inc. or its affiliates. All Rights Reserved. 421 | 422 | This product includes software developed at 423 | Amazon Web Services, Inc. (http://aws.amazon.com/). 424 | 425 | --- 426 | 427 | \*\* typescript; version 3.9.10 -- https://github.com/Microsoft/TypeScript 428 | 429 | Apache License 430 | 431 | Version 2.0, January 2004 432 | 433 | http://www.apache.org/licenses/ 434 | 435 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 436 | 437 | 1. Definitions. 438 | 439 | "License" shall mean the terms and conditions for use, reproduction, and 440 | distribution as defined by Sections 1 through 9 of this document. 441 | 442 | "Licensor" shall mean the copyright owner or entity authorized by the copyright 443 | owner that is granting the License. 444 | 445 | "Legal Entity" shall mean the union of the acting entity and all other entities 446 | that control, are controlled by, or are under common control with that entity. 447 | For the purposes of this definition, "control" means (i) the power, direct or 448 | indirect, to cause the direction or management of such entity, whether by 449 | contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the 450 | outstanding shares, or (iii) beneficial ownership of such entity. 451 | 452 | "You" (or "Your") shall mean an individual or Legal Entity exercising 453 | permissions granted by this License. 454 | 455 | "Source" form shall mean the preferred form for making modifications, including 456 | but not limited to software source code, documentation source, and configuration 457 | files. 458 | 459 | "Object" form shall mean any form resulting from mechanical transformation or 460 | translation of a Source form, including but not limited to compiled object code, 461 | generated documentation, and conversions to other media types. 462 | 463 | "Work" shall mean the work of authorship, whether in Source or Object form, made 464 | available under the License, as indicated by a copyright notice that is included 465 | in or attached to the work (an example is provided in the Appendix below). 466 | 467 | "Derivative Works" shall mean any work, whether in Source or Object form, that 468 | is based on (or derived from) the Work and for which the editorial revisions, 469 | annotations, elaborations, or other modifications represent, as a whole, an 470 | original work of authorship. For the purposes of this License, Derivative Works 471 | shall not include works that remain separable from, or merely link (or bind by 472 | name) to the interfaces of, the Work and Derivative Works thereof. 473 | 474 | "Contribution" shall mean any work of authorship, including the original version 475 | of the Work and any modifications or additions to that Work or Derivative Works 476 | thereof, that is intentionally submitted to Licensor for inclusion in the Work 477 | by the copyright owner or by an individual or Legal Entity authorized to submit 478 | on behalf of the copyright owner. For the purposes of this definition, 479 | "submitted" means any form of electronic, verbal, or written communication sent 480 | to the Licensor or its representatives, including but not limited to 481 | communication on electronic mailing lists, source code control systems, and 482 | issue tracking systems that are managed by, or on behalf of, the Licensor for 483 | the purpose of discussing and improving the Work, but excluding communication 484 | that is conspicuously marked or otherwise designated in writing by the copyright 485 | owner as "Not a Contribution." 486 | 487 | "Contributor" shall mean Licensor and any individual or Legal Entity on behalf 488 | of whom a Contribution has been received by Licensor and subsequently 489 | incorporated within the Work. 490 | 491 | 2. Grant of Copyright License. Subject to the terms and conditions of this 492 | License, each Contributor hereby grants to You a perpetual, worldwide, non- 493 | exclusive, no-charge, royalty-free, irrevocable copyright license to reproduce, 494 | prepare Derivative Works of, publicly display, publicly perform, sublicense, and 495 | distribute the Work and such Derivative Works in Source or Object form. 496 | 497 | 3. Grant of Patent License. Subject to the terms and conditions of this License, 498 | each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no- 499 | charge, royalty-free, irrevocable (except as stated in this section) patent 500 | license to make, have made, use, offer to sell, sell, import, and otherwise 501 | transfer the Work, where such license applies only to those patent claims 502 | licensable by such Contributor that are necessarily infringed by their 503 | Contribution(s) alone or by combination of their Contribution(s) with the Work 504 | to which such Contribution(s) was submitted. If You institute patent litigation 505 | against any entity (including a cross-claim or counterclaim in a lawsuit) 506 | alleging that the Work or a Contribution incorporated within the Work 507 | constitutes direct or contributory patent infringement, then any patent licenses 508 | granted to You under this License for that Work shall terminate as of the date 509 | such litigation is filed. 510 | 511 | 4. Redistribution. You may reproduce and distribute copies of the Work or 512 | Derivative Works thereof in any medium, with or without modifications, and in 513 | Source or Object form, provided that You meet the following conditions: 514 | 515 | You must give any other recipients of the Work or Derivative Works a copy of 516 | this License; and 517 | 518 | You must cause any modified files to carry prominent notices stating that You 519 | changed the files; and 520 | 521 | You must retain, in the Source form of any Derivative Works that You distribute, 522 | all copyright, patent, trademark, and attribution notices from the Source form 523 | of the Work, excluding those notices that do not pertain to any part of the 524 | Derivative Works; and 525 | 526 | If the Work includes a "NOTICE" text file as part of its distribution, then any 527 | Derivative Works that You distribute must include a readable copy of the 528 | attribution notices contained within such NOTICE file, excluding those notices 529 | that do not pertain to any part of the Derivative Works, in at least one of the 530 | following places: within a NOTICE text file distributed as part of the 531 | Derivative Works; within the Source form or documentation, if provided along 532 | with the Derivative Works; or, within a display generated by the Derivative 533 | Works, if and wherever such third-party notices normally appear. The contents of 534 | the NOTICE file are for informational purposes only and do not modify the 535 | License. You may add Your own attribution notices within Derivative Works that 536 | You distribute, alongside or as an addendum to the NOTICE text from the Work, 537 | provided that such additional attribution notices cannot be construed as 538 | modifying the License. You may add Your own copyright statement to Your 539 | modifications and may provide additional or different license terms and 540 | conditions for use, reproduction, or distribution of Your modifications, or for 541 | any such Derivative Works as a whole, provided Your use, reproduction, and 542 | distribution of the Work otherwise complies with the conditions stated in this 543 | License. 544 | 545 | 5. Submission of Contributions. Unless You explicitly state otherwise, any 546 | Contribution intentionally submitted for inclusion in the Work by You to the 547 | Licensor shall be under the terms and conditions of this License, without any 548 | additional terms or conditions. Notwithstanding the above, nothing herein shall 549 | supersede or modify the terms of any separate license agreement you may have 550 | executed with Licensor regarding such Contributions. 551 | 552 | 6. Trademarks. This License does not grant permission to use the trade names, 553 | trademarks, service marks, or product names of the Licensor, except as required 554 | for reasonable and customary use in describing the origin of the Work and 555 | reproducing the content of the NOTICE file. 556 | 557 | 7. Disclaimer of Warranty. Unless required by applicable law or agreed to in 558 | writing, Licensor provides the Work (and each Contributor provides its 559 | Contributions) on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 560 | KIND, either express or implied, including, without limitation, any warranties 561 | or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 562 | PARTICULAR PURPOSE. You are solely responsible for determining the 563 | appropriateness of using or redistributing the Work and assume any risks 564 | associated with Your exercise of permissions under this License. 565 | 566 | 8. Limitation of Liability. In no event and under no legal theory, whether in 567 | tort (including negligence), contract, or otherwise, unless required by 568 | applicable law (such as deliberate and grossly negligent acts) or agreed to in 569 | writing, shall any Contributor be liable to You for damages, including any 570 | direct, indirect, special, incidental, or consequential damages of any character 571 | arising as a result of this License or out of the use or inability to use the 572 | Work (including but not limited to damages for loss of goodwill, work stoppage, 573 | computer failure or malfunction, or any and all other commercial damages or 574 | losses), even if such Contributor has been advised of the possibility of such 575 | damages. 576 | 577 | 9. Accepting Warranty or Additional Liability. While redistributing the Work or 578 | Derivative Works thereof, You may choose to offer, and charge a fee for, 579 | acceptance of support, warranty, indemnity, or other liability obligations 580 | and/or rights consistent with this License. However, in accepting such 581 | obligations, You may act only on Your own behalf and on Your sole 582 | responsibility, not on behalf of any other Contributor, and only if You agree to 583 | indemnify, defend, and hold each Contributor harmless for any liability incurred 584 | by, or claims asserted against, such Contributor by reason of your accepting any 585 | such warranty or additional liability. 586 | 587 | END OF TERMS AND CONDITIONS 588 | 589 | - For typescript see also this required NOTICE: 590 | Copyright (c) Microsoft Corporation. All rights reserved. 591 | 592 | --- 593 | 594 | \*\* @blueprintjs/core; version ^3.54.0 -- https://github.com/palantir/blueprint 595 | 596 | Apache License 597 | Version 2.0, January 2004 598 | http://www.apache.org/licenses/ 599 | 600 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 601 | 602 | 1. Definitions. 603 | 604 | "License" shall mean the terms and conditions for use, reproduction, 605 | and distribution as defined by Sections 1 through 9 of this document. 606 | 607 | "Licensor" shall mean the copyright owner or entity authorized by 608 | the copyright owner that is granting the License. 609 | 610 | "Legal Entity" shall mean the union of the acting entity and all 611 | other entities that control, are controlled by, or are under common 612 | control with that entity. For the purposes of this definition, 613 | "control" means (i) the power, direct or indirect, to cause the 614 | direction or management of such entity, whether by contract or 615 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 616 | outstanding shares, or (iii) beneficial ownership of such entity. 617 | 618 | "You" (or "Your") shall mean an individual or Legal Entity 619 | exercising permissions granted by this License. 620 | 621 | "Source" form shall mean the preferred form for making modifications, 622 | including but not limited to software source code, documentation 623 | source, and configuration files. 624 | 625 | "Object" form shall mean any form resulting from mechanical 626 | transformation or translation of a Source form, including but 627 | not limited to compiled object code, generated documentation, 628 | and conversions to other media types. 629 | 630 | "Work" shall mean the work of authorship, whether in Source or 631 | Object form, made available under the License, as indicated by a 632 | copyright notice that is included in or attached to the work 633 | (an example is provided in the Appendix below). 634 | 635 | "Derivative Works" shall mean any work, whether in Source or Object 636 | form, that is based on (or derived from) the Work and for which the 637 | editorial revisions, annotations, elaborations, or other modifications 638 | represent, as a whole, an original work of authorship. For the purposes 639 | of this License, Derivative Works shall not include works that remain 640 | separable from, or merely link (or bind by name) to the interfaces of, 641 | the Work and Derivative Works thereof. 642 | 643 | "Contribution" shall mean any work of authorship, including 644 | the original version of the Work and any modifications or additions 645 | to that Work or Derivative Works thereof, that is intentionally 646 | submitted to Licensor for inclusion in the Work by the copyright owner 647 | or by an individual or Legal Entity authorized to submit on behalf of 648 | the copyright owner. For the purposes of this definition, "submitted" 649 | means any form of electronic, verbal, or written communication sent 650 | to the Licensor or its representatives, including but not limited to 651 | communication on electronic mailing lists, source code control systems, 652 | and issue tracking systems that are managed by, or on behalf of, the 653 | Licensor for the purpose of discussing and improving the Work, but 654 | excluding communication that is conspicuously marked or otherwise 655 | designated in writing by the copyright owner as "Not a Contribution." 656 | 657 | "Contributor" shall mean Licensor and any individual or Legal Entity 658 | on behalf of whom a Contribution has been received by Licensor and 659 | subsequently incorporated within the Work. 660 | 661 | 2. Grant of Copyright License. Subject to the terms and conditions of 662 | this License, each Contributor hereby grants to You a perpetual, 663 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 664 | copyright license to reproduce, prepare Derivative Works of, 665 | publicly display, publicly perform, sublicense, and distribute the 666 | Work and such Derivative Works in Source or Object form. 667 | 668 | 3. Grant of Patent License. Subject to the terms and conditions of 669 | this License, each Contributor hereby grants to You a perpetual, 670 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 671 | (except as stated in this section) patent license to make, have made, 672 | use, offer to sell, sell, import, and otherwise transfer the Work, 673 | where such license applies only to those patent claims licensable 674 | by such Contributor that are necessarily infringed by their 675 | Contribution(s) alone or by combination of their Contribution(s) 676 | with the Work to which such Contribution(s) was submitted. If You 677 | institute patent litigation against any entity (including a 678 | cross-claim or counterclaim in a lawsuit) alleging that the Work 679 | or a Contribution incorporated within the Work constitutes direct 680 | or contributory patent infringement, then any patent licenses 681 | granted to You under this License for that Work shall terminate 682 | as of the date such litigation is filed. 683 | 684 | 4. Redistribution. You may reproduce and distribute copies of the 685 | Work or Derivative Works thereof in any medium, with or without 686 | modifications, and in Source or Object form, provided that You 687 | meet the following conditions: 688 | 689 | (a) You must give any other recipients of the Work or 690 | Derivative Works a copy of this License; and 691 | 692 | (b) You must cause any modified files to carry prominent notices 693 | stating that You changed the files; and 694 | 695 | (c) You must retain, in the Source form of any Derivative Works 696 | that You distribute, all copyright, patent, trademark, and 697 | attribution notices from the Source form of the Work, 698 | excluding those notices that do not pertain to any part of 699 | the Derivative Works; and 700 | 701 | (d) If the Work includes a "NOTICE" text file as part of its 702 | distribution, then any Derivative Works that You distribute must 703 | include a readable copy of the attribution notices contained 704 | within such NOTICE file, excluding those notices that do not 705 | pertain to any part of the Derivative Works, in at least one 706 | of the following places: within a NOTICE text file distributed 707 | as part of the Derivative Works; within the Source form or 708 | documentation, if provided along with the Derivative Works; or, 709 | within a display generated by the Derivative Works, if and 710 | wherever such third-party notices normally appear. The contents 711 | of the NOTICE file are for informational purposes only and 712 | do not modify the License. You may add Your own attribution 713 | notices within Derivative Works that You distribute, alongside 714 | or as an addendum to the NOTICE text from the Work, provided 715 | that such additional attribution notices cannot be construed 716 | as modifying the License. 717 | 718 | You may add Your own copyright statement to Your modifications and 719 | may provide additional or different license terms and conditions 720 | for use, reproduction, or distribution of Your modifications, or 721 | for any such Derivative Works as a whole, provided Your use, 722 | reproduction, and distribution of the Work otherwise complies with 723 | the conditions stated in this License. 724 | 725 | 5. Submission of Contributions. Unless You explicitly state otherwise, 726 | any Contribution intentionally submitted for inclusion in the Work 727 | by You to the Licensor shall be under the terms and conditions of 728 | this License, without any additional terms or conditions. 729 | Notwithstanding the above, nothing herein shall supersede or modify 730 | the terms of any separate license agreement you may have executed 731 | with Licensor regarding such Contributions. 732 | 733 | 6. Trademarks. This License does not grant permission to use the trade 734 | names, trademarks, service marks, or product names of the Licensor, 735 | except as required for reasonable and customary use in describing the 736 | origin of the Work and reproducing the content of the NOTICE file. 737 | 738 | 7. Disclaimer of Warranty. Unless required by applicable law or 739 | agreed to in writing, Licensor provides the Work (and each 740 | Contributor provides its Contributions) on an "AS IS" BASIS, 741 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 742 | implied, including, without limitation, any warranties or conditions 743 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 744 | PARTICULAR PURPOSE. You are solely responsible for determining the 745 | appropriateness of using or redistributing the Work and assume any 746 | risks associated with Your exercise of permissions under this License. 747 | 748 | 8. Limitation of Liability. In no event and under no legal theory, 749 | whether in tort (including negligence), contract, or otherwise, 750 | unless required by applicable law (such as deliberate and grossly 751 | negligent acts) or agreed to in writing, shall any Contributor be 752 | liable to You for damages, including any direct, indirect, special, 753 | incidental, or consequential damages of any character arising as a 754 | result of this License or out of the use or inability to use the 755 | Work (including but not limited to damages for loss of goodwill, 756 | work stoppage, computer failure or malfunction, or any and all 757 | other commercial damages or losses), even if such Contributor 758 | has been advised of the possibility of such damages. 759 | 760 | 9. Accepting Warranty or Additional Liability. While redistributing 761 | the Work or Derivative Works thereof, You may choose to offer, 762 | and charge a fee for, acceptance of support, warranty, indemnity, 763 | or other liability obligations and/or rights consistent with this 764 | License. However, in accepting such obligations, You may act only 765 | on Your own behalf and on Your sole responsibility, not on behalf 766 | of any other Contributor, and only if You agree to indemnify, 767 | defend, and hold each Contributor harmless for any liability 768 | incurred by, or claims asserted against, such Contributor by reason 769 | of your accepting any such warranty or additional liability. 770 | 771 | END OF TERMS AND CONDITIONS 772 | 773 | - For @blueprintjs/core see also this required NOTICE: 774 | Copyright 2017 Palantir Technologies, Inc. All rights reserved. 775 | 776 | Licensed under the Apache License, Version 2.0 (the "License"); 777 | you may not use this file except in compliance with the License. 778 | You may obtain a copy of the License at 779 | 780 | http://www.apache.org/licenses/LICENSE-2.0 781 | 782 | Unless required by applicable law or agreed to in writing, software 783 | distributed under the License is distributed on an "AS IS" BASIS, 784 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 785 | See the License for the specific language governing permissions and 786 | limitations under the License. 787 | 788 | --- 789 | 790 | \*\* eslint-config-prettier; version 8.5.0 -- https://github.com/prettier/eslint-config-prettier 791 | Copyright (c) 2017, 2018, 2019 Simon Lydell and contributors 792 | 793 | The MIT License (MIT) 794 | 795 | Copyright (c) 2017, 2018, 2019 Simon Lydell and contributors 796 | 797 | Permission is hereby granted, free of charge, to any person obtaining a copy 798 | of this software and associated documentation files (the "Software"), to deal 799 | in the Software without restriction, including without limitation the rights 800 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 801 | copies of the Software, and to permit persons to whom the Software is 802 | furnished to do so, subject to the following conditions: 803 | 804 | The above copyright notice and this permission notice shall be included in 805 | all copies or substantial portions of the Software. 806 | 807 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 808 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 809 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 810 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 811 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 812 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 813 | THE SOFTWARE. 814 | 815 | --- 816 | 817 | \*\* @types/node; version 17.0.21 -- https://github.com/DefinitelyTyped/DefinitelyTyped 818 | Copyright (c) Microsoft Corporation. All rights reserved. 819 | 820 | This project is licensed under the MIT license. 821 | Copyrights are respective of each contributor listed at the beginning of each 822 | definition file. 823 | 824 | Permission is hereby granted, free of charge, to any person obtaining a copy of 825 | this software and associated documentation files (the "Software"), to deal in 826 | the Software without restriction, including without limitation the rights to 827 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 828 | the Software, and to permit persons to whom the Software is furnished to do so, 829 | subject to the following conditions: 830 | 831 | The above copyright notice and this permission notice shall be included in all 832 | copies or substantial portions of the Software. 833 | 834 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 835 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 836 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 837 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 838 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 839 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 840 | 841 | --- 842 | 843 | \*\* eslint-config-airbnb; version 19.0.4 -- https://www.npmjs.com/package/eslint-config-airbnb 844 | Copyright (c) 2012 Airbnb 845 | 846 | MIT License 847 | 848 | Copyright (c) 2012 Airbnb 849 | 850 | Permission is hereby granted, free of charge, to any person obtaining a copy 851 | of this software and associated documentation files (the "Software"), to deal 852 | in the Software without restriction, including without limitation the rights 853 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 854 | copies of the Software, and to permit persons to whom the Software is 855 | furnished to do so, subject to the following conditions: 856 | 857 | The above copyright notice and this permission notice shall be included in all 858 | copies or substantial portions of the Software. 859 | 860 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 861 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 862 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 863 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 864 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 865 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 866 | SOFTWARE. 867 | 868 | --- 869 | 870 | \*\* eslint-plugin-jasmine; version 4.1.3 -- https://github.com/tlvince/eslint-plugin-jasmine 871 | Copyright (c) 2019 Tom Vincent (https://tlvince.com) 872 | 873 | The MIT License (MIT) 874 | 875 | Copyright (c) 2019 Tom Vincent (https://tlvince.com) 876 | 877 | Permission is hereby granted, free of charge, to any person obtaining a copy 878 | of this software and associated documentation files (the "Software"), to deal 879 | in the Software without restriction, including without limitation the rights 880 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 881 | copies of the Software, and to permit persons to whom the Software is 882 | furnished to do so, subject to the following conditions: 883 | 884 | The above copyright notice and this permission notice shall be included in 885 | all copies or substantial portions of the Software. 886 | 887 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 888 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 889 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 890 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 891 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 892 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 893 | THE SOFTWARE. 894 | 895 | --- 896 | 897 | \*\* prettier; version 2.5.1 -- https://prettier.io/ 898 | Copyright © James Long and contributors 899 | 900 | Permission is hereby granted, free of charge, to any person obtaining a copy of 901 | this software and associated documentation files (the "Software"), to deal in 902 | the Software without restriction, including without limitation the rights to 903 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 904 | the Software, and to permit persons to whom the Software is furnished to do so, 905 | subject to the following conditions: 906 | 907 | The above copyright notice and this permission notice shall be included in all 908 | copies or substantial portions of the Software. 909 | 910 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 911 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 912 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 913 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 914 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 915 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 916 | 917 | Copyright © James Long and contributors 918 | 919 | Permission is hereby granted, free of charge, to any person obtaining a copy of 920 | this software and associated documentation files (the "Software"), to deal in 921 | the Software without restriction, including without limitation the rights to 922 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 923 | the Software, and to permit persons to whom the Software is furnished to do so, 924 | subject to the following conditions: 925 | 926 | The above copyright notice and this permission notice shall be included in all 927 | copies or substantial portions of the Software. 928 | 929 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 930 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 931 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 932 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 933 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 934 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 935 | 936 | --- 937 | 938 | \*\* eslint; version 8.11.0 -- https://eslint.org/ 939 | Copyright OpenJS Foundation and other contributors, 940 | 941 | Permission is hereby granted, free of charge, to any person obtaining a copy 942 | of this software and associated documentation files (the "Software"), to deal 943 | in the Software without restriction, including without limitation the rights 944 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 945 | copies of the Software, and to permit persons to whom the Software is 946 | furnished to do so, subject to the following conditions: 947 | 948 | The above copyright notice and this permission notice shall be included in 949 | all copies or substantial portions of the Software. 950 | 951 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 952 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 953 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 954 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 955 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 956 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 957 | THE SOFTWARE. 958 | 959 | Copyright OpenJS Foundation and other contributors, 960 | 961 | Permission is hereby granted, free of charge, to any person obtaining a copy 962 | of this software and associated documentation files (the "Software"), to deal 963 | in the Software without restriction, including without limitation the rights 964 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 965 | copies of the Software, and to permit persons to whom the Software is 966 | furnished to do so, subject to the following conditions: 967 | 968 | The above copyright notice and this permission notice shall be included in 969 | all copies or substantial portions of the Software. 970 | 971 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 972 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 973 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 974 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 975 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 976 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 977 | THE SOFTWARE. 978 | 979 | --- 980 | 981 | ** @typescript-eslint/eslint-plugin; version 5.16.0 -- https://github.com/typescript-eslint/typescript-eslint/tree/master/packages/eslint-plugin 982 | Copyright JS Foundation and other contributors, https://js.foundation 983 | ** @typescript-eslint/parser; version 5.16.0 -- https://github.com/typescript-eslint/typescript-eslint 984 | Copyright JS Foundation and other contributors, https://js.foundation 985 | 986 | TypeScript ESLint 987 | 988 | Originally extracted from: 989 | 990 | TypeScript ESLint Parser 991 | Copyright JS Foundation and other contributors, https://js.foundation 992 | 993 | Redistribution and use in source and binary forms, with or without 994 | modification, are permitted provided that the following conditions are met: 995 | 996 | - Redistributions of source code must retain the above copyright 997 | notice, this list of conditions and the following disclaimer. 998 | - Redistributions in binary form must reproduce the above copyright 999 | notice, this list of conditions and the following disclaimer in the 1000 | documentation and/or other materials provided with the distribution. 1001 | 1002 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 1003 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1004 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 1005 | ARE DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY 1006 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 1007 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 1008 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 1009 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 1010 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 1011 | THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 1012 | 1013 | --- 1014 | 1015 | \*\* eslint-plugin-prettier; version 4.0.0 -- https://github.com/prettier/eslint-plugin-prettier 1016 | Copyright © 2017 Andres Suarez and Teddy Katz 1017 | 1018 | The MIT License (MIT) 1019 | 1020 | Copyright © 2017 Andres Suarez and Teddy Katz 1021 | 1022 | Permission is hereby granted, free of charge, to any person obtaining a copy of 1023 | this software and associated documentation files (the “Software”), to deal in 1024 | the Software without restriction, including without limitation the rights to 1025 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 1026 | the Software, and to permit persons to whom the Software is furnished to do so, 1027 | subject to the following conditions: 1028 | 1029 | The above copyright notice and this permission notice shall be included in all 1030 | copies or substantial portions of the Software. 1031 | 1032 | THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1033 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 1034 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 1035 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 1036 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 1037 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 1038 | 1039 | --- 1040 | 1041 | \*\* eslint-plugin-react; version 7.28.0 -- https://github.com/yannickcr/eslint-plugin-react 1042 | Copyright (c) 2014 Yannick Croissant 1043 | 1044 | The MIT License (MIT) 1045 | 1046 | Copyright (c) 2014 Yannick Croissant 1047 | 1048 | Permission is hereby granted, free of charge, to any person obtaining a copy 1049 | of this software and associated documentation files (the "Software"), to deal 1050 | in the Software without restriction, including without limitation the rights 1051 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 1052 | copies of the Software, and to permit persons to whom the Software is 1053 | furnished to do so, subject to the following conditions: 1054 | 1055 | The above copyright notice and this permission notice shall be included in all 1056 | copies or substantial portions of the Software. 1057 | 1058 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1059 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 1060 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 1061 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 1062 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 1063 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 1064 | SOFTWARE. 1065 | 1066 | --- 1067 | 1068 | \*\* archiver-promise; version 1.0.0 -- https://github.com/maichong/archiver-promise 1069 | MIT License 1070 | 1071 | Copyright (c) 2016 Maichong Software 1072 | \*\* fix-path; version 4.0.0 -- https://github.com/sindresorhus/fix-path 1073 | MIT License 1074 | 1075 | Copyright (c) Sindre Sorhus (https://sindresorhus.com) 1076 | \*\* jest; version 27.5.1 -- https://jestjs.io/ 1077 | MIT License 1078 | 1079 | Copyright (c) Facebook, Inc. and its affiliates. 1080 | \*\* AWS SDK v3 Client mock; version 0.6.2 -- https://github.com/m-radzikowski/aws-sdk-client-mock 1081 | MIT License 1082 | 1083 | Copyright (c) 2021 Maciej Radzikowski 1084 | \*\* React; version 17.0.2 -- https://reactjs.org/ 1085 | MIT License 1086 | 1087 | Copyright (c) Facebook, Inc. and its affiliates. 1088 | \*\* ts-jest; version 27.0.7 -- https://kulshekhar.github.io/ts-jest/ 1089 | MIT License 1090 | 1091 | Copyright (c) 2016-2018 1092 | \*\* eslint-plugin-jsx-a11y; version ^6.5.1 -- https://github.com/jsx-eslint/eslint-plugin-jsx-a11y 1093 | The MIT License (MIT) Copyright (c) 2016 Ethan Cohen 1094 | 1095 | Permission is hereby granted, free of charge, to any person obtaining a copy 1096 | of this software and associated documentation files (the "Software"), to deal 1097 | in the Software without restriction, including without limitation the rights 1098 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 1099 | copies of the Software, and to permit persons to whom the Software is 1100 | furnished to do so, subject to the following conditions: 1101 | 1102 | The above copyright notice and this permission notice shall be included in all 1103 | copies or substantial portions of the Software. 1104 | 1105 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1106 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 1107 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 1108 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 1109 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 1110 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 1111 | SOFTWARE. 1112 | 1113 | --- 1114 | 1115 | \*\* prettier-plugin-organize-imports; version 2.3.4 -- https://github.com/simonhaenisch/prettier-plugin-organize-imports 1116 | Copyright (c) Simon Hänisch 1117 | 1118 | MIT License 1119 | 1120 | Copyright (c) Simon Hänisch 1121 | 1122 | Permission is hereby granted, free of charge, to any person obtaining a copy 1123 | of this software and associated documentation files (the "Software"), to deal 1124 | in the Software without restriction, including without limitation the rights 1125 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 1126 | copies of the Software, and to permit persons to whom the Software is 1127 | furnished to do so, subject to the following conditions: 1128 | 1129 | The above copyright notice and this permission notice shall be included in all 1130 | copies or substantial portions of the Software. 1131 | 1132 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1133 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 1134 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 1135 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 1136 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 1137 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 1138 | SOFTWARE. 1139 | 1140 | --- 1141 | 1142 | \*\* fs-extra; version 10.0.1 -- https://github.com/jprichardson/node-fs-extra 1143 | MIT License 1144 | 1145 | Copyright (c) 2011-2017 JP Richardson 1146 | 1147 | Permission is hereby granted, free of charge, to any person obtaining a copy of 1148 | this software and associated documentation files 1149 | (the 'Software'), to deal in the Software without restriction, including without 1150 | limitation the rights to use, copy, modify, 1151 | merge, publish, distribute, sublicense, and/or sell copies of the Software, and 1152 | to permit persons to whom the Software is 1153 | furnished to do so, subject to the following conditions: 1154 | 1155 | The above copyright notice and this permission notice shall be included in all 1156 | copies or substantial portions of the Software. 1157 | 1158 | THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1159 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE 1160 | WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 1161 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS 1162 | OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, 1163 | WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 1164 | ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 1165 | DEALINGS IN THE SOFTWARE. 1166 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/.eslintignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | build 3 | *.d.ts 4 | declaration 5 | coverage -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/.eslintrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "parser": "@typescript-eslint/parser", 3 | "extends": [ 4 | "airbnb", 5 | "prettier", 6 | "plugin:@typescript-eslint/recommended", 7 | "plugin:jasmine/recommended", 8 | "plugin:react/recommended" 9 | ], 10 | "plugins": [ 11 | "prettier", 12 | "jasmine", 13 | "react", 14 | "@typescript-eslint" 15 | ], 16 | "parserOptions": { 17 | "ecmaVersion": 2022, 18 | "requireConfigFile": false, 19 | "sourceType": "module" 20 | }, 21 | "globals": { 22 | "atob": true, 23 | "btoa": true, 24 | "document": true, 25 | "navigator": true, 26 | "window": true, 27 | "XMLHttpRequest": true, 28 | "AWS": true, 29 | "BABYLON": true, 30 | "expectAsync": true 31 | }, 32 | "rules": { 33 | // Specific rule overrides can go here. 34 | "react/destructuring-assignment": "off", 35 | "indent": [ 36 | "error", 37 | 2, 38 | { 39 | "SwitchCase": 1 40 | } 41 | ], 42 | "no-underscore-dangle": [ 43 | "warn", 44 | { 45 | "allowAfterThis": true, 46 | "allowAfterSuper": true 47 | } 48 | ], 49 | "no-console": "off", 50 | "no-shadow": "off", 51 | "@typescript-eslint/no-shadow": "error", 52 | "react/jsx-filename-extension": [ 53 | 1, 54 | { 55 | "extensions": [ 56 | ".tsx", 57 | ".ts" 58 | ] 59 | } 60 | ], 61 | "import/prefer-default-export": "off", 62 | "import/extensions": [ 63 | "error", 64 | "ignorePackages", 65 | { 66 | "js": "never", 67 | "jsx": "never", 68 | "ts": "never", 69 | "tsx": "never" 70 | } 71 | ] 72 | }, 73 | "env": { 74 | "browser": true, 75 | "node": true, 76 | "jasmine": true 77 | }, 78 | "settings": { 79 | "import/resolver": { 80 | "node": { 81 | "extensions": [ 82 | ".js", 83 | ".jsx", 84 | ".ts", 85 | ".tsx" 86 | ] 87 | } 88 | } 89 | } 90 | } -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules/ 2 | build/ 3 | declaration/ 4 | .DS_Store 5 | coverage -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/.prettierignore: -------------------------------------------------------------------------------- 1 | *.md -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "printWidth": 80, 3 | "tabWidth": 2, 4 | "useTabs": false, 5 | "semi": true, 6 | "singleQuote": true, 7 | "trailingComma": "es5", 8 | "bracketSpacing": false 9 | } -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing Guidelines and Workflow 2 | 3 | Thank you for your interest in contributing to our project. This document covers specifically on how to build and test the aws-amplify-publisher-plugin package. Please refer to the main [CONTRIBUTING](../CONTRIBUTING) document for a detailed explanation on how to contribute to the repository. 4 | 5 | --- 6 | 7 | ## [Contributor Workflow](#contributor-workflow) 8 | 9 | ### Prerequisites 10 | 11 | - Refer to all [prerequisites](../CONTRIBUTING#contributor-workflow#prerequisites) from the primary repository 12 | 13 | ### Building 14 | 15 | 1. Install the plugin dependencies defined in `package.json`: 16 | `npm install` 17 | 2. Compile the Typescript code into Javascript 18 | `npm run compile` 19 | 20 | ### Testing 21 | 22 | #### Unit Tests 23 | 24 | You can run the unit test suite by using the command: `npm run test` 25 | 26 | Unit tests will be run automatically across Windows/Linux/MacOSX on every submitted PR. 27 | 28 | #### Integration Tests 29 | 30 | Manually ensure that the plugin loads in the editor, and that a host can be added to the open project without errors. 31 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/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 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/NOTICE: -------------------------------------------------------------------------------- 1 | Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/README.md: -------------------------------------------------------------------------------- 1 | # AWS Tools for Babylon.JS Editor: AWS Amplify Publisher Plugin 2 | 3 | AWS Tools for Babylon.JS Editor: AWS Amplify Publisher Plugin (AWS Tools: Amplify Publisher Plugin) is a plugin that enables one-click publishing to AWS Amplify from Babylon.JS Editor. 4 | 5 | ## License 6 | 7 | This project is licensed under the Apache-2.0 License. See the [LICENSE](LICENSE) file. 8 | 9 | ## Installation 10 | 11 | 1. Ensure you have set your [AWS Credentials properly](https://docs.aws.amazon.com/sdk-for-javascript/v3/developer-guide/configuring-the-jssdk.html) 12 | 1. If you haven't already, download and install the [Babylon.JS Editor](http://editor.babylonjs.com/) 13 | 1. Open the Babylon.JS Editor, in the upper left corner click Edit > Preferences to open the Preferences tab 14 | 1. Click "Plugins" 15 | 1. Add the plugin to your Babylon.JS Editor: 16 | - If you are not building the package manually: 17 | 1. Select "Add from NPM..." 18 | 1. Type in "@aws/aws-tools-for-babylonjs-editor-aws-amplify-publisher-plugin" 19 | 1. Press "Ok" 20 | - If you are building the package manually: 21 | 1. Ensure the plugin has been compiled and built successfully 22 | 1. Select "Add..." 23 | 1. Locate and select the [root folder](.) that contains the plugin (it will be the folder containing `package.json` ) 24 | 1. Click "Apply" on the bottom left of the preferences window 25 | 26 | Note that the editor is not capable of hot reloading; whenever changes to the plugin are made, the editor must be refreshed (close/open the editor, File->Reload Project, or press F5 with the devtools focused, or type `location.reload()` into the console window in the devtools) to see those changes reflected. 27 | 28 | To debug the plugin, press ctrl+alt+I (or cmd+option+I on a mac) to bring up the dev tools. If you log to the console, those messages will be routed here. 29 | 30 | ## Usage 31 | 32 | TODO: Define specific steps to utilize the plugin while inside the editor 33 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/jest.config.js: -------------------------------------------------------------------------------- 1 | /** @type {import('ts-jest/dist/types').InitialOptionsTsJest} */ 2 | module.exports = { 3 | preset: 'ts-jest', 4 | testRegex: '(test/.*|(\\.|/)(test|spec))\\.(ts)$', 5 | testEnvironment: 'node', 6 | }; 7 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@aws/aws-tools-for-babylonjs-editor-aws-amplify-publisher-plugin", 3 | "version": "1.0.0", 4 | "description": "AWS Tools for Babylon.JS Editor: AWS Amplify Publisher Plugin is a set of tools that enables one-click publishing to AWS Amplify.", 5 | "main": "build/src/index.js", 6 | "author": { 7 | "name": "Amazon Web Services", 8 | "url": "https://aws.amazon.com", 9 | "organization": true 10 | }, 11 | "repository": { 12 | "type": "git", 13 | "url": "https://github.com/aws-samples/aws-tools-for-babylonjs-editor.git", 14 | "directory": "aws-amplify-publisher-plugin" 15 | }, 16 | "license": "Apache 2.0", 17 | "scripts": { 18 | "compile": "tsc -p .", 19 | "lint": "eslint .", 20 | "lint:fix": "eslint . --fix", 21 | "format": "prettier --config .prettierrc --write 'src/**/*.tsx' 'test/**/**.ts' ", 22 | "build": "npm run format && npm run lint:fix && npm run compile", 23 | "watch": "tsc -p . --watch", 24 | "test": "jest --coverage --verbose", 25 | "clean": "rm -rf node_modules declaration build", 26 | "release" : "npm run lint && npm run compile && npm run test" 27 | }, 28 | "devDependencies": { 29 | "@types/jest": "^27.4.1", 30 | "@types/node": "^17.0.23", 31 | "@typescript-eslint/eslint-plugin": "^5.12.1", 32 | "@typescript-eslint/parser": "^5.12.1", 33 | "aws-sdk-client-mock": "^0.6.2", 34 | "babylonjs-editor": "^4.1.0", 35 | "eslint": "^8.9.0", 36 | "eslint-config-airbnb": "^19.0.4", 37 | "eslint-config-prettier": "^8.3.0", 38 | "eslint-plugin-import": "^2.25.4", 39 | "eslint-plugin-jasmine": "^4.1.3", 40 | "eslint-plugin-jsx-a11y": "^6.5.1", 41 | "eslint-plugin-prettier": "^4.0.0", 42 | "eslint-plugin-react": "^7.28.0", 43 | "jest": "^27.5.1", 44 | "prettier": "^2.5.1", 45 | "ts-jest": "^27.1.4", 46 | "typescript": "^3.9.10" 47 | }, 48 | "dependencies": { 49 | "@aws-sdk/client-amplify": "^3.53.0", 50 | "archiver-promise": "^1.0.0", 51 | "fs-extra": "^10.0.1" 52 | }, 53 | "peerDependencies": { 54 | "react": "^16" 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/amplifyPublishDialog.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | // eslint-disable-next-line import/no-extraneous-dependencies 6 | import {Dialog} from '@blueprintjs/core'; 7 | import fs from 'fs-extra'; 8 | // eslint-disable-next-line import/no-unresolved 9 | import {Editor, SceneExporter} from 'babylonjs-editor'; 10 | 11 | import {AmplifyClient} from '@aws-sdk/client-amplify'; 12 | 13 | import {Status, PLUGIN_VERSION} from './constants'; 14 | 15 | import { 16 | getAmplifyPublishingPreferences, 17 | setAmplifyPublishingPreferences, 18 | } from './preferences'; 19 | 20 | import {httpPutFile, zipArtifacts, getDefaultDomainForBranch} from './utils'; 21 | 22 | import { 23 | getExistingAmplifyAppId, 24 | createAmplifyApp, 25 | createAmplifyBranch, 26 | checkExistingAmplifyBranch, 27 | createAmplifyDeployment, 28 | waitJobToSucceed, 29 | startAmplifyDeployment, 30 | } from './amplifyUtils'; 31 | 32 | import {InputDialog} from './inputDialog'; 33 | import {OverwriteDialog} from './overwriteDialog'; 34 | import {ProgressDialog} from './progressDialog'; 35 | import {SuccessDialog} from './successDialog'; 36 | import {FailureDialog} from './failureDialog'; 37 | 38 | /** 39 | * The configuration that the Amplify publishing dialog should be initialized with 40 | */ 41 | export type AmplifyPublishDialogProps = { 42 | /** 43 | * The function that should be called when the dialog is closed 44 | */ 45 | handleClose: () => void; 46 | 47 | /** 48 | * The boolean state that determines whether the dialog should be visible 49 | * to the user or not 50 | */ 51 | isOpen: boolean; 52 | 53 | /** 54 | * A reference to the BabylonJS Editor object 55 | * @see {@link Editor} 56 | */ 57 | editor: Editor; 58 | }; 59 | 60 | /** 61 | * These represent the mutable values the user will change when interacting with the dialog 62 | */ 63 | export type AmplifyPublishDialogState = { 64 | /** 65 | * The Amplify application name that corresponds to the 66 | * project that should be published with this dialog 67 | */ 68 | appName: string; 69 | 70 | /** 71 | * The unique environment name that corresponds to the Amplify branch 72 | * should be published to 73 | */ 74 | envName: string; 75 | 76 | /** 77 | * The status of the publishing. 78 | */ 79 | status: Status; 80 | 81 | /** 82 | * The domain address of successfully deployed the Amplify app. 83 | */ 84 | domainAddress: string; 85 | 86 | /** 87 | * The error message. 88 | */ 89 | error: string; 90 | }; 91 | 92 | /** 93 | * This dialog component handles allowing the user to input any Amplify-related configuration 94 | * before pressing a button to publish their BabylonJS project. The configuration will be 95 | * persisted in the workspace. 96 | */ 97 | export class AmplifyPublishDialog extends React.Component< 98 | AmplifyPublishDialogProps, 99 | AmplifyPublishDialogState 100 | > { 101 | private client: AmplifyClient; 102 | 103 | public constructor(props: AmplifyPublishDialogProps) { 104 | super(props); 105 | 106 | // grab the local preferences and set them in the local state 107 | // so they can be referenced as the default values in the render() function 108 | const preferences = getAmplifyPublishingPreferences(); 109 | 110 | this.state = { 111 | appName: preferences.appName, 112 | envName: preferences.envName, 113 | status: Status.Publish, 114 | domainAddress: '', 115 | error: '', 116 | }; 117 | 118 | this.client = new AmplifyClient({ 119 | customUserAgent: `AWSToolsForBabylonJS-${PLUGIN_VERSION}`, 120 | }); 121 | } 122 | 123 | /** 124 | * Handle the close button when clicked 125 | */ 126 | private _handleCloseClick = (): void => { 127 | setAmplifyPublishingPreferences({ 128 | ...this.state, 129 | }); 130 | 131 | this.setState({status: Status.Publish}); 132 | const {handleClose} = this.props; 133 | handleClose(); 134 | }; 135 | 136 | /** 137 | * Handle the publish button when clicked 138 | * @param appName The Amplify application name. 139 | * @param envName The Amplify environment name. 140 | * @returns A Promise that resolves when the scene publishing process completes.. 141 | * Otherwise, it will change to render the failure dialog with the 142 | * error message. 143 | */ 144 | private _handlePublishClick = async ( 145 | appName: string, 146 | envName: string 147 | ): Promise => { 148 | try { 149 | if (!this.props.editor.scene) { 150 | throw new Error('No active scene to publish!'); 151 | } 152 | 153 | // check whether the Amplify App exists 154 | let appId = await getExistingAmplifyAppId(appName, this.client); 155 | if (appId === null || appId === undefined) { 156 | appId = await createAmplifyApp(appName, this.client); 157 | } 158 | if (appId === undefined) { 159 | throw new Error(`The created app has an undefined appId.`); 160 | } 161 | // check whether the branch of the Amplify App exists 162 | const doesBranchExist = await checkExistingAmplifyBranch( 163 | appId, 164 | envName, 165 | this.client 166 | ); 167 | 168 | if (!doesBranchExist) { 169 | await createAmplifyBranch(appId, envName, this.client); 170 | } else { 171 | this.setState({status: Status.ExistBranch}); 172 | return; 173 | } 174 | await this._publishToAmplify(appId, envName); 175 | } catch (error) { 176 | this.setState({error, status: Status.Failure}); 177 | } 178 | }; 179 | 180 | /** 181 | * Publish the files to AWS Amplify. 182 | * @param appId The Amplify application Id. 183 | * @param envName The Amplify environment name. 184 | * @returns A Promise that resolves when publishing the scene to Amplify 185 | * and change to render the SuccessDialog. Otherwise, it will throw 186 | * the error to the upper level. 187 | * @throws An error once the url used to upload the file is undefined. 188 | */ 189 | private _publishToAmplify = async ( 190 | appId: string, 191 | envName: string 192 | ): Promise => { 193 | let artifactsPath: string | undefined; 194 | this.setState({status: Status.Progress}); 195 | 196 | try { 197 | await SceneExporter.ExportFinalScene(this.props.editor); 198 | 199 | artifactsPath = await zipArtifacts(); 200 | 201 | // create an Amplify deployment 202 | const {jobId, zipUploadUrl} = await createAmplifyDeployment( 203 | appId, 204 | envName, 205 | this.client 206 | ); 207 | if (jobId === undefined) { 208 | throw new Error('The Job Id is undefined. Please try it again!'); 209 | } 210 | if (zipUploadUrl) { 211 | await httpPutFile(artifactsPath, zipUploadUrl); 212 | } else { 213 | throw new Error('The url used to upload the file is undefined.'); 214 | } 215 | 216 | await startAmplifyDeployment(appId, envName, jobId, this.client); 217 | 218 | await waitJobToSucceed(appId, envName, jobId, this.client); 219 | 220 | const domainAddress = getDefaultDomainForBranch(appId, envName); 221 | this.setState({domainAddress, status: Status.Success}); 222 | this.props.editor.console.logInfo(domainAddress); 223 | } finally { 224 | try { 225 | if (artifactsPath) { 226 | fs.unlinkSync(artifactsPath); 227 | } 228 | } catch (error) { 229 | const errorMessage = `An error has occurred while removing the compressed file at ${artifactsPath}. Please remove it manually. ${error}`; 230 | this.setState({error: errorMessage, status: Status.Failure}); 231 | } 232 | } 233 | }; 234 | 235 | /** 236 | * overwrite the branch to AWS Amplify application. 237 | * @param appName The Amplify application name. 238 | * @param envName The Amplify environment name. 239 | * @returns A Promise that resolves when the scene publishing process completes. 240 | * Otherwise, it will reject and change to render the Failure dialog 241 | * with error message. 242 | */ 243 | private _overwriteAmplifyBranch = async ( 244 | appName: string, 245 | envName: string 246 | ): Promise => { 247 | try { 248 | const appId = await getExistingAmplifyAppId(appName, this.client); 249 | if (appId) { 250 | await this._publishToAmplify(appId, envName); 251 | } else { 252 | throw new Error(`The appId isn't valid.`); 253 | } 254 | } catch (error) { 255 | this.setState({error, status: Status.Failure}); 256 | } 257 | }; 258 | 259 | /** 260 | * Handle the back button when clicked. 261 | */ 262 | private _handleBackClick = (): void => { 263 | this.setState({status: Status.Publish}); 264 | }; 265 | 266 | public render(): React.ReactNode { 267 | const {isOpen} = this.props; 268 | const {status, appName, envName, domainAddress, error} = this.state; 269 | 270 | return ( 271 | 279 | {status === Status.Publish && ( 280 | 284 | this.setState({appName: newAppName}) 285 | } 286 | onEnvNameChange={(newEnvName: string) => 287 | this.setState({envName: newEnvName}) 288 | } 289 | onPublish={this._handlePublishClick} 290 | onClose={this._handleCloseClick} 291 | /> 292 | )} 293 | {status === Status.ExistBranch && ( 294 | 300 | )} 301 | {status === Status.Progress && } 302 | {status === Status.Success && ( 303 | 309 | )} 310 | {status === Status.Failure && ( 311 | 312 | )} 313 | 314 | ); 315 | } 316 | } 317 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/amplifyUtils.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | import { 4 | AmplifyClient, 5 | CreateAppCommand, 6 | CreateBranchCommand, 7 | CreateDeploymentCommand, 8 | ListAppsCommand, 9 | GetJobCommand, 10 | GetBranchCommand, 11 | CreateDeploymentCommandOutput, 12 | StartDeploymentCommand, 13 | StartDeploymentCommandOutput, 14 | CreateBranchCommandOutput, 15 | } from '@aws-sdk/client-amplify'; 16 | 17 | /** 18 | * Check whether the given Amplify app exists. 19 | * @param appName The Amplify application name. 20 | * @param client The Amplify SDK client. 21 | * @returns A Promise that resolves to an app ID string. 22 | * If an app matching "appName" exists, that app ID will be returned. 23 | * Otherwise, an undefined variable will be returned. 24 | */ 25 | export const getExistingAmplifyAppId = async ( 26 | appName: string, 27 | client: AmplifyClient 28 | ): Promise => { 29 | let nextToken; 30 | /* eslint-disable no-await-in-loop */ 31 | do { 32 | const listAppResponse = await client.send(new ListAppsCommand({nextToken})); 33 | if (listAppResponse?.apps) { 34 | const existingApp = listAppResponse.apps.find( 35 | (app) => app.name === appName && app.appId 36 | ); 37 | if (existingApp && existingApp.appId) { 38 | return existingApp.appId; 39 | } 40 | } 41 | nextToken = listAppResponse?.nextToken; 42 | } while (nextToken); 43 | /* eslint-enable no-await-in-loop */ 44 | return undefined; 45 | }; 46 | 47 | /** 48 | * Create an Amplify App and a branch. 49 | * @param appName The Amplify application name. 50 | * @param client The Amplify SDK client. 51 | * @returns A Promise that resolves to an app ID string. 52 | * If an app created with the input "appName", that app ID will be returned. 53 | * Otherwise, an error will be thrown. 54 | * @throws An error with the specific error information why the app fails to be created. 55 | */ 56 | export const createAmplifyApp = async ( 57 | appName: string, 58 | client: AmplifyClient 59 | ): Promise => { 60 | try { 61 | const createAppResponse = await client.send( 62 | new CreateAppCommand({name: appName}) 63 | ); 64 | return createAppResponse.app?.appId; 65 | } catch (error) { 66 | throw new Error( 67 | `The app ${appName} could not be created due to: ${error.message}` 68 | ); 69 | } 70 | }; 71 | 72 | /** 73 | * Check whether the given Amplify branch exists in the Amplify app. 74 | * @param appId The Amplify application Id. 75 | * @param branchName The Amplify environment branch name. 76 | * @param client The Amplify SDK Client 77 | * @returns A Promise that resolves to a boolean variable. 78 | * If the branch with the input "branchName" exists, it will return true. 79 | * Otherwise, it will return false; 80 | */ 81 | export const checkExistingAmplifyBranch = async ( 82 | appId: string, 83 | branchName: string, 84 | client: AmplifyClient 85 | ): Promise => { 86 | try { 87 | const getBranchResponse = await client.send( 88 | new GetBranchCommand({appId, branchName}) 89 | ); 90 | if (getBranchResponse.branch) { 91 | return true; 92 | } 93 | return false; 94 | } catch (error) { 95 | return false; 96 | } 97 | }; 98 | 99 | /** 100 | * wait the submitted job to succeed. 101 | * @param job The job of Amplify deployment. 102 | * @param client The Amplify SDK Client. 103 | * @returns A Promise that resolves when getting a response by given jobId. 104 | * Otherwise, it will reject when it fails to get job. 105 | * @throws An error if it failed to get the job. 106 | */ 107 | export const waitJobToSucceed = async ( 108 | appId: string, 109 | branchName: string, 110 | jobId: string, 111 | client: AmplifyClient 112 | ): Promise => { 113 | let processing = true; 114 | while (processing) { 115 | /* eslint-disable no-await-in-loop */ 116 | const getResponse = await client.send( 117 | new GetJobCommand({appId, branchName, jobId}) 118 | ); 119 | 120 | const jobSummary = getResponse.job?.summary; 121 | if (jobSummary?.status === 'FAILED') { 122 | processing = false; 123 | throw new Error(`Job failed.${JSON.stringify(jobSummary)}`); 124 | } 125 | if (jobSummary?.status === 'SUCCEED') { 126 | processing = false; 127 | } 128 | await new Promise((resolve) => { 129 | setTimeout(resolve, 1000 * 3); 130 | }); 131 | } 132 | }; 133 | 134 | /** 135 | * The wrapper of Amplify CreateBranchCommend. 136 | * @param appId The Amplify application ID. 137 | * @param branchName The Amplify Environment Name. 138 | * @param client The Amplify SDK Client. 139 | * @return A Promise that resolves when the Amplify branch is created. 140 | */ 141 | export const createAmplifyBranch = async ( 142 | appId: string, 143 | branchName: string, 144 | client: AmplifyClient 145 | ): Promise => 146 | client.send(new CreateBranchCommand({appId, branchName})); 147 | 148 | /** 149 | * The wrapper of Amplify StartAmplifyDeployment. 150 | * @param appId The Amplify application ID. 151 | * @param branchName The Amplify Environment Name. 152 | * @param jobId The Amplify Application job ID 153 | * @param client The Amplify SDK Client. 154 | * @returns A Promise that resolves when the amplify deployment is started. 155 | */ 156 | export const startAmplifyDeployment = async ( 157 | appId: string, 158 | branchName: string, 159 | jobId: string, 160 | 161 | client: AmplifyClient 162 | ): Promise => 163 | client.send( 164 | new StartDeploymentCommand({ 165 | appId, 166 | branchName, 167 | jobId, 168 | }) 169 | ); 170 | 171 | /** 172 | * The wrapper of Amplify CreateDeploymentCommand. 173 | * @param appId The Amplify application ID. 174 | * @param branchName The Amplify Environment Name. 175 | * @param client The Amplify SDK Client. 176 | * @returns A Promise that resolves when the amplify deployment is created. 177 | */ 178 | export const createAmplifyDeployment = async ( 179 | appId: string, 180 | branchName: string, 181 | client: AmplifyClient 182 | ): Promise => 183 | client.send( 184 | new CreateDeploymentCommand({ 185 | appId, 186 | branchName, 187 | }) 188 | ); 189 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/constants.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | /** 5 | * The Status Enum represents different publishing status. 6 | */ 7 | export enum Status { 8 | Publish = 'publish', 9 | ExistBranch = 'existBranch', 10 | Progress = 'progress', 11 | Success = 'success', 12 | Failure = 'failure', 13 | } 14 | 15 | // Our Github Actions will replace this with a commit SHA at release time 16 | export const PLUGIN_VERSION = 'development'; 17 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/failureDialog.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | // eslint-disable-next-line import/no-extraneous-dependencies 6 | import {Button, Classes, Icon, Intent} from '@blueprintjs/core'; 7 | 8 | type FailureDialogProps = { 9 | error: string; 10 | onBack: () => void; 11 | }; 12 | /** 13 | * The dialog to show the failure information. 14 | * @param props The props passed in from the parent component 15 | * @returns the FailureDialog component. 16 | */ 17 | export function FailureDialog(props: FailureDialogProps) { 18 | const {error, onBack} = props; 19 | const failureTitle = `There was a problem!`; 20 | const failureText = `${error}`; 21 | 22 | return ( 23 | <> 24 |
25 |

26 | {failureTitle} 27 |

28 |

{failureText}

29 |
30 |
31 |
32 | 33 |
34 |
35 | 36 | ); 37 | } 38 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/index.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | // eslint-disable-next-line import/no-unresolved 6 | import {Editor, IPlugin} from 'babylonjs-editor'; 7 | 8 | import {AmplifyPublisherToolbar} from './toolbar'; 9 | import { 10 | AmplifyPublishingPreferences, 11 | getAmplifyPublishingPreferences, 12 | setAmplifyPublishingPreferences, 13 | } from './preferences'; 14 | 15 | /** 16 | * Registers the plugin by returning the IPlugin content. 17 | * @param editor defines the main reference to the editor. 18 | * @returns an object that implements IPlugin 19 | */ 20 | export const registerEditorPlugin = (editor: Editor): IPlugin => ({ 21 | /** 22 | * Defines the list of all toolbar elements to add when the plugin has been loaded. 23 | */ 24 | toolbar: [ 25 | { 26 | buttonLabel: 'AWS Amplify Publisher Tools', 27 | buttonIcon: 'export', 28 | content: , 29 | }, 30 | ], 31 | 32 | /** 33 | * This will return a dictionary that will be saved as JSON 34 | * in the workspace file. This will be typically used to store preferences of the plugin 35 | * work a given workspace and not globally. 36 | * The preferences will be saved in the .editorworkspace file each time the user 37 | * saves the project. 38 | */ 39 | getWorkspacePreferences: () => getAmplifyPublishingPreferences(), 40 | 41 | /** 42 | * When the plugin is loaded, this function will be called, 43 | * giving the plain JSON representation of the user's preferences for 44 | * the current plugin. 45 | */ 46 | setWorkspacePreferences: (preferences: AmplifyPublishingPreferences) => { 47 | setAmplifyPublishingPreferences(preferences); 48 | }, 49 | }); 50 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/inputDialog.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | // eslint-disable-next-line import/no-extraneous-dependencies 6 | import {Classes, Button, FormGroup, Label} from '@blueprintjs/core'; 7 | 8 | type InputDialogProps = { 9 | appName: string; 10 | envName: string; 11 | onPublish: (appName: string, envName: string) => void; 12 | onAppNameChange: (appName: string) => void; 13 | onEnvNameChange: (envName: string) => void; 14 | onClose: () => void; 15 | }; 16 | 17 | /** 18 | * The dialog to show the input when publishing to Amplify. 19 | * @param props The props passed in from the parent component. 20 | * @returns the InputDialog component. 21 | */ 22 | export function InputDialog(props: InputDialogProps) { 23 | const { 24 | appName, 25 | envName, 26 | onPublish, 27 | onAppNameChange, 28 | onEnvNameChange, 29 | onClose, 30 | } = props; 31 | return ( 32 | <> 33 |
34 | 35 | 49 | 61 | 62 |
63 |
64 |
65 | 66 | 73 |
74 |
75 | 76 | ); 77 | } 78 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/overwriteDialog.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | // eslint-disable-next-line import/no-extraneous-dependencies 6 | import {Classes, Text, Button} from '@blueprintjs/core'; 7 | 8 | type OverwriteDialogProps = { 9 | appName: string; 10 | envName: string; 11 | onBack: () => void; 12 | onOverwrite: (appName: string, envName: string) => void; 13 | }; 14 | 15 | /** 16 | * The dialog to show the whether overwrite the branch. 17 | * @param props The props passed in from the parent component. 18 | * @returns the OverwriteDialog component. 19 | */ 20 | export function OverwriteDialog(props: OverwriteDialogProps) { 21 | const {appName, envName, onBack, onOverwrite} = props; 22 | const overwriteText = `An application is already deployed to ${appName}(${envName}). Overwrite?`; 23 | 24 | return ( 25 | <> 26 |
27 | {overwriteText} 28 |
29 |
30 |
31 | 32 | 35 |
36 |
37 | 38 | ); 39 | } 40 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/preferences.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | /** 5 | * These user preferences are used to configure various aspects of the Amplify application. 6 | * 7 | * They are intended to be stored with the workspace and persisted between editor sessions -- 8 | * @see getWorkspacePreferences 9 | */ 10 | export type AmplifyPublishingPreferences = { 11 | /** 12 | * The unique Amplify application identifier 13 | */ 14 | appName: string; 15 | 16 | /** 17 | * The environment name 18 | */ 19 | envName: string; 20 | }; 21 | 22 | /** 23 | * The saved preferences (declared inline with default values) for the plugin 24 | */ 25 | const preferences: AmplifyPublishingPreferences = { 26 | appName: '', 27 | envName: '', 28 | }; 29 | 30 | /** 31 | * Exports the preferences of the plugin to a dictionary. 32 | * @returns A dictionary containing the values defined by AmplifyPublishingPreferences 33 | */ 34 | export const getAmplifyPublishingPreferences = 35 | (): AmplifyPublishingPreferences => ({...preferences}); 36 | 37 | /** 38 | * Imports the preferences of the plugin from its JSON representation. 39 | */ 40 | export const setAmplifyPublishingPreferences = ( 41 | config: AmplifyPublishingPreferences 42 | ) => { 43 | preferences.appName = config.appName; 44 | preferences.envName = config.envName; 45 | }; 46 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/progressDialog.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | // eslint-disable-next-line import/no-extraneous-dependencies 6 | import {ProgressBar, Classes, Text} from '@blueprintjs/core'; 7 | 8 | /** 9 | * The dialog to show the progress information of the current deployment. 10 | * @returns the ProgressDialog component. 11 | */ 12 | export function ProgressDialog() { 13 | const progressText = `Deploying application...`; 14 | return ( 15 |
16 | {progressText} 17 | 18 |
19 | ); 20 | } 21 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/successDialog.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | // eslint-disable-next-line import/no-extraneous-dependencies 6 | import {Button, Classes, Text, Icon, Intent} from '@blueprintjs/core'; 7 | 8 | type SuccessProps = { 9 | appName: string; 10 | envName: string; 11 | domainAddress: string; 12 | onClose: () => void; 13 | }; 14 | 15 | /** 16 | * The dialog to show the successful deployment information. 17 | * @param props The props passed in from the parent component. 18 | * @returns the SuccessDialog component. 19 | */ 20 | export function SuccessDialog(props: SuccessProps) { 21 | const {appName, envName, domainAddress, onClose} = props; 22 | const successTitle = `Deployment complete.`; 23 | const successText = `${appName} (${envName})`; 24 | return ( 25 | <> 26 |
27 |

28 | {successTitle} 29 |

30 | {successText} 31 | {domainAddress} 32 |
33 |
34 |
35 | 36 |
37 |
38 | 39 | ); 40 | } 41 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/toolbar.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import React from 'react'; 5 | 6 | // eslint-disable-next-line import/no-unresolved 7 | import {Editor} from 'babylonjs-editor'; 8 | // eslint-disable-next-line import/no-extraneous-dependencies 9 | import {Menu, MenuItem} from '@blueprintjs/core'; 10 | 11 | import {AmplifyPublishDialog} from './amplifyPublishDialog'; 12 | 13 | /** 14 | * The configuration that the Amplify Toolbar should be initialized with. 15 | */ 16 | type AmplifyPublisherToolbarProps = { 17 | /** 18 | * A reference to the BabylonJS Editor object. 19 | * @see {@link Editor} 20 | */ 21 | editor: Editor; 22 | }; 23 | 24 | /** 25 | * Mutable values that will change at runtime 26 | */ 27 | type AmplifyPublisherToolbarState = { 28 | /** 29 | * This boolean state determines whether the Amplify publish dialog 30 | * is visible and therefore should be rendered to the user 31 | */ 32 | isPublishDialogOpen: boolean; 33 | }; 34 | 35 | /** 36 | * The Amplify toolbar is a single button that, when clicked, shows a drop-down menu 37 | * of helpful tools and dialogs that allow the user to interact with AWS. 38 | */ 39 | export class AmplifyPublisherToolbar extends React.Component< 40 | AmplifyPublisherToolbarProps, 41 | AmplifyPublisherToolbarState 42 | > { 43 | public constructor(props: Readonly) { 44 | super(props); 45 | 46 | this.state = { 47 | isPublishDialogOpen: false, 48 | }; 49 | } 50 | 51 | private _handleClose = () => { 52 | this._hidePublishDialog(); 53 | }; 54 | 55 | private _handlePublishClick = () => { 56 | this._showPublishDialog(); 57 | }; 58 | 59 | private _showPublishDialog() { 60 | this.setState({isPublishDialogOpen: true}); 61 | } 62 | 63 | private _hidePublishDialog() { 64 | this.setState({isPublishDialogOpen: false}); 65 | } 66 | 67 | public render(): React.ReactNode { 68 | const {editor} = this.props; 69 | const {isPublishDialogOpen} = this.state; 70 | 71 | return ( 72 | <> 73 | 74 | 79 | 80 | 85 | 86 | ); 87 | } 88 | } 89 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/src/utils.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import fs from 'fs-extra'; 5 | import archiver from 'archiver-promise'; 6 | // eslint-disable-next-line import/no-unresolved 7 | import {WorkSpace} from 'babylonjs-editor'; 8 | /** 9 | * Put file into a HTTP URL request body. 10 | * @param filePath the path of the file. 11 | * @param url the url string. 12 | * @returns A Promise that resolves when the file upload is complete. 13 | * @throws Can throw the same errors thrown by fetch(). 14 | * See [fetch documentation]{@link https://developer.mozilla.org/en-US/docs/Web/API/fetch} for details. 15 | */ 16 | export async function httpPutFile( 17 | filePath: fs.PathLike, 18 | url: string 19 | ): Promise { 20 | await fetch(url, { 21 | method: 'PUT', 22 | body: fs.readFileSync(filePath), 23 | }); 24 | } 25 | 26 | /** 27 | * Compress files to a zip file. 28 | * @param sourceDir the path of the source directory. 29 | * @param destFilePath the path of the destination file. 30 | * @returns A Promise object that resolves the zip file path. 31 | * Otherwise, it will reject if no file exists or any errors appear 32 | * and throw error message to the upper level. 33 | * @throws An error once the path does not exist. 34 | */ 35 | async function zipFile( 36 | sourceDir: string, 37 | destFilePath: string 38 | ): Promise { 39 | if (!fs.pathExistsSync(sourceDir)) { 40 | throw new Error( 41 | `Please ensure the build artifacts path ${sourceDir} exists.` 42 | ); 43 | } 44 | const archive = archiver(destFilePath, {store: true}); 45 | await archive.directory(sourceDir, false); 46 | await archive.finalize(); 47 | return destFilePath; 48 | } 49 | 50 | /** 51 | * Compress the files needed to be host on the server. 52 | * @returns A Promise object that resolves the zip file path. 53 | */ 54 | export async function zipArtifacts(): Promise { 55 | const workSpaceDirPath = WorkSpace.DirPath; 56 | if (workSpaceDirPath == null || !fs.existsSync(workSpaceDirPath)) { 57 | throw new Error( 58 | `Cannot get WorkSpace directory ${workSpaceDirPath}, or it does not exist.` 59 | ); 60 | } 61 | const zipFilePath = `${workSpaceDirPath}.zip`; 62 | return zipFile(workSpaceDirPath, zipFilePath); 63 | } 64 | 65 | /** 66 | * Get the default Domain URL for the given appId and branch. 67 | * @param appId The Amplify application Id. 68 | * @param branch The Amplify environment branch name. 69 | * @returns The domain url for the given appId with the branch. 70 | */ 71 | export function getDefaultDomainForBranch( 72 | appId: string, 73 | branch: string 74 | ): string { 75 | return `https://${branch}.${appId}.amplifyapp.com`; 76 | } 77 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/test/amplifyUtils.test.ts: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | import {mockClient} from 'aws-sdk-client-mock'; 4 | import { 5 | AmplifyClient, 6 | CreateAppCommand, 7 | ListAppsCommand, 8 | GetBranchCommand, 9 | GetJobCommand, 10 | CreateBranchCommand, 11 | StartDeploymentCommand, 12 | CreateDeploymentCommand, 13 | } from '@aws-sdk/client-amplify'; 14 | import { 15 | getExistingAmplifyAppId, 16 | createAmplifyApp, 17 | checkExistingAmplifyBranch, 18 | waitJobToSucceed, 19 | createAmplifyBranch, 20 | startAmplifyDeployment, 21 | createAmplifyDeployment, 22 | } from '../src/amplifyUtils'; 23 | 24 | /** 25 | * mock the given instance of the AWS SDK Client: 26 | */ 27 | const amplifyClient = new AmplifyClient({}); 28 | const amplifyMock = mockClient(amplifyClient); 29 | 30 | // The mocked Amplify App object 31 | const mockApp1 = { 32 | appId: '1234', 33 | name: 'testApp1', 34 | appArn: '', 35 | description: 'The mocked Amplify App object', 36 | createTime: new Date(), 37 | updateTime: new Date(), 38 | repository: '', 39 | enableBranchAutoBuild: true, 40 | platform: '', 41 | environmentVariables: {}, 42 | defaultDomain: '', 43 | enableBasicAuth: true, 44 | }; 45 | const mockApp2 = { 46 | appId: '5678', 47 | name: 'testApp2', 48 | appArn: '', 49 | description: 'The mocked Amplify App object', 50 | createTime: new Date(), 51 | updateTime: new Date(), 52 | repository: '', 53 | enableBranchAutoBuild: true, 54 | platform: '', 55 | environmentVariables: {}, 56 | defaultDomain: '', 57 | enableBasicAuth: true, 58 | }; 59 | 60 | // The mocked Amplify Branch object 61 | const mockBranch = { 62 | branchName: 'testBranch', 63 | branchArn: '', 64 | description: 'The mocked Amplify Branch object', 65 | stage: '', 66 | displayName: '', 67 | enableNotification: true, 68 | createTime: new Date(), 69 | updateTime: new Date(), 70 | environmentVariables: {}, 71 | framework: '', 72 | enableAutoBuild: true, 73 | customDomains: [], 74 | activeJobId: '', 75 | totalNumberOfJobs: '', 76 | enableBasicAuth: true, 77 | ttl: '', 78 | enablePullRequestPreview: true, 79 | }; 80 | 81 | // The mocked Amplify succeed job object 82 | const mockSucceedJob = { 83 | summary: { 84 | jobArn: '', 85 | jobId: 'testId', 86 | commitId: '', 87 | commitMessage: '', 88 | commitTime: new Date(), 89 | startTime: new Date(), 90 | jobType: '', 91 | status: 'SUCCEED', 92 | }, 93 | steps: [], 94 | }; 95 | 96 | // The mocked Amplify failed job object 97 | const mockFailedJob = { 98 | summary: { 99 | jobArn: '', 100 | jobId: 'testId', 101 | commitId: '', 102 | commitMessage: '', 103 | commitTime: new Date(), 104 | startTime: new Date(), 105 | jobType: '', 106 | status: 'FAILED', 107 | }, 108 | steps: [], 109 | }; 110 | 111 | describe('getExistingAmplifyAppId', () => { 112 | // To be sure that unit tests are independent from each other, 113 | // reset mock behavior between the tests. 114 | beforeEach(() => { 115 | amplifyMock.reset(); 116 | }); 117 | 118 | it('should return appId after calling getExistingAmplifyAppId with an existing app name', async () => { 119 | amplifyMock.on(ListAppsCommand).resolves({ 120 | apps: [mockApp1, mockApp2], 121 | }); 122 | 123 | const appId = await getExistingAmplifyAppId('testApp1', amplifyClient); 124 | 125 | expect(appId).toBe('1234'); 126 | }); 127 | 128 | it('should return undefined after calling getExistingAmplifyAppId with a nonexisting app name', async () => { 129 | amplifyMock.on(ListAppsCommand).resolves({ 130 | apps: [mockApp1, mockApp2], 131 | }); 132 | 133 | const appId = await getExistingAmplifyAppId( 134 | 'nonExistingAppName', 135 | amplifyClient 136 | ); 137 | 138 | expect(appId).toBe(undefined); 139 | }); 140 | 141 | it('should return undefined after calling getExistingAmplifyAppId with an empty app name', async () => { 142 | amplifyMock.on(ListAppsCommand).resolves({ 143 | apps: [mockApp1, mockApp2], 144 | }); 145 | 146 | const appId = await getExistingAmplifyAppId('', amplifyClient); 147 | 148 | expect(appId).toBe(undefined); 149 | }); 150 | 151 | it('should return the second appId since there is a nextToken in first time ListAppsCommand API call', async () => { 152 | amplifyMock 153 | .on(ListAppsCommand) 154 | .resolvesOnce({ 155 | apps: [mockApp1], 156 | nextToken: 'nextToken', 157 | }) 158 | .resolvesOnce({apps: [mockApp2]}); 159 | 160 | const appId = await getExistingAmplifyAppId('testApp2', amplifyClient); 161 | 162 | expect(appId).toBe('5678'); 163 | }); 164 | 165 | it('should return undefined since there is no nextToken in first time ListAppsCommand API call', async () => { 166 | amplifyMock 167 | .on(ListAppsCommand) 168 | .resolvesOnce({ 169 | apps: [mockApp1], 170 | }) 171 | .resolvesOnce({apps: [mockApp2]}); 172 | 173 | const appId = await getExistingAmplifyAppId('testApp2', amplifyClient); 174 | 175 | expect(appId).toBe(undefined); 176 | }); 177 | }); 178 | 179 | describe('createAmplifyApp', () => { 180 | beforeEach(() => { 181 | amplifyMock.reset(); 182 | }); 183 | 184 | it('should return appId from createAmplifyApp function with the right app name', async () => { 185 | amplifyMock.on(CreateAppCommand, {name: 'testApp1'}).resolves({ 186 | app: mockApp1, 187 | }); 188 | 189 | const appId = await createAmplifyApp('testApp1', amplifyClient); 190 | 191 | expect(appId).toBe('1234'); 192 | }); 193 | 194 | it('should throw error from createAmplifyApp function when CreateAppCommand throws an error.', async () => { 195 | amplifyMock 196 | .on(CreateAppCommand, {name: 'invalidName'}) 197 | .rejects('mocked rejection'); 198 | 199 | await expect( 200 | createAmplifyApp('invalidName', amplifyClient) 201 | ).rejects.toThrow( 202 | 'The app invalidName could not be created due to: mocked rejection' 203 | ); 204 | }); 205 | }); 206 | 207 | describe('checkExistingAmplifyBranch', () => { 208 | beforeEach(() => { 209 | amplifyMock.reset(); 210 | }); 211 | 212 | it('should return true after calling checkExistingAmplifyBranch with the existing amplify branch', async () => { 213 | amplifyMock 214 | .on(GetBranchCommand, {appId: '1234', branchName: 'testBranch'}) 215 | .resolves({ 216 | branch: mockBranch, 217 | }); 218 | const doesExist = await checkExistingAmplifyBranch( 219 | '1234', 220 | 'testBranch', 221 | amplifyClient 222 | ); 223 | 224 | expect(doesExist).toBe(true); 225 | }); 226 | 227 | it('should return false after calling checkExistingAmplifyBranch with the nonexisting amplify branch', async () => { 228 | amplifyMock.on(GetBranchCommand, {appId: '1234'}).resolves({ 229 | branch: undefined, 230 | }); 231 | 232 | const doesExist = await checkExistingAmplifyBranch( 233 | '1234', 234 | 'nonexistingBranch', 235 | amplifyClient 236 | ); 237 | 238 | expect(doesExist).toBe(false); 239 | }); 240 | 241 | it('should return false after calling checkExistingAmplifyBranch with error thrown', async () => { 242 | amplifyMock 243 | .on(GetBranchCommand, {appId: '1234'}) 244 | .rejects('mocked rejection'); 245 | 246 | const doesExist = await checkExistingAmplifyBranch( 247 | '1234', 248 | 'testBranch', 249 | amplifyClient 250 | ); 251 | 252 | expect(doesExist).toBe(false); 253 | }); 254 | }); 255 | 256 | describe('waitJobToSucceed', () => { 257 | beforeEach(() => { 258 | amplifyMock.reset(); 259 | }); 260 | 261 | it('should resolve Promise when the job succeeds', async () => { 262 | amplifyMock.on(GetJobCommand).resolves({ 263 | job: mockSucceedJob, 264 | }); 265 | // Since the waitJobToSucceed will return Promise when the job succeeds and a 266 | // Promise resolves to an undefined, we test the resolves result to be undefined here. 267 | await expect( 268 | waitJobToSucceed('1234', 'testBranch', 'testJob', amplifyClient) 269 | ).resolves.toBe(undefined); 270 | }); 271 | 272 | it('should throw error after calling waitJobToSucceed with a failed job', async () => { 273 | amplifyMock.on(GetJobCommand).resolves({ 274 | job: mockFailedJob, 275 | }); 276 | 277 | await expect( 278 | waitJobToSucceed('1234', 'testBranch', 'testJob', amplifyClient) 279 | ).rejects.toThrow('Job failed.'); 280 | }); 281 | }); 282 | 283 | describe('createAmplifyBranch', () => { 284 | it('check whether the amplify CreateBranchCommand is called with the right arguments', async () => { 285 | let actualCommand; 286 | amplifyClient.send = jest.fn((command) => { 287 | actualCommand = command; 288 | return Promise.resolve(); 289 | }); 290 | await createAmplifyBranch('1234', 'testBranch', amplifyClient); 291 | 292 | const expectCommand = new CreateBranchCommand({ 293 | appId: '1234', 294 | branchName: 'testBranch', 295 | }); 296 | 297 | expect(amplifyClient.send).toHaveBeenCalledTimes(1); 298 | expect(actualCommand.input.appId).toBe(expectCommand.input.appId); 299 | expect(actualCommand.input.branchName).toBe(expectCommand.input.branchName); 300 | }); 301 | }); 302 | 303 | describe('startAmplifyDeployment', () => { 304 | it('check whether the amplify StartDeploymentCommand is called with the right arguments', async () => { 305 | let actualCommand; 306 | amplifyClient.send = jest.fn((command) => { 307 | actualCommand = command; 308 | return Promise.resolve(); 309 | }); 310 | await startAmplifyDeployment( 311 | '1234', 312 | 'testBranch', 313 | 'testJob', 314 | amplifyClient 315 | ); 316 | 317 | const expectCommand = new StartDeploymentCommand({ 318 | appId: '1234', 319 | branchName: 'testBranch', 320 | jobId: 'testJob', 321 | }); 322 | 323 | expect(amplifyClient.send).toHaveBeenCalledTimes(1); 324 | expect(actualCommand.input.appId).toBe(expectCommand.input.appId); 325 | expect(actualCommand.input.branchName).toBe(expectCommand.input.branchName); 326 | expect(actualCommand.input.jobId).toBe(expectCommand.input.jobId); 327 | }); 328 | }); 329 | 330 | describe('createAmplifyDeployment', () => { 331 | it('check whether the amplify CreateDeploymentCommand is called with the right arguments', async () => { 332 | let actualCommand; 333 | amplifyClient.send = jest.fn((command) => { 334 | actualCommand = command; 335 | return Promise.resolve(); 336 | }); 337 | await createAmplifyDeployment('1234', 'testBranch', amplifyClient); 338 | 339 | const expectCommand = new CreateDeploymentCommand({ 340 | appId: '1234', 341 | branchName: 'testBranch', 342 | }); 343 | 344 | expect(amplifyClient.send).toHaveBeenCalledTimes(1); 345 | expect(actualCommand.input.appId).toBe(expectCommand.input.appId); 346 | expect(actualCommand.input.branchName).toBe(expectCommand.input.branchName); 347 | }); 348 | }); 349 | -------------------------------------------------------------------------------- /aws-amplify-publisher-plugin/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es5", 4 | // the following is necessary so BabylonJS can import our plugin - it is itself a CommonJS module 5 | "module": "CommonJS", 6 | "moduleResolution": "node", 7 | "sourceMap": true, 8 | "declaration": true, 9 | "outDir": "./build/src", 10 | "declarationDir": "./declaration/src", 11 | "jsx": "react", 12 | "strictNullChecks": true, 13 | "noUnusedLocals": true, 14 | "noUnusedParameters": true, 15 | "allowSyntheticDefaultImports": true, 16 | "esModuleInterop": true, 17 | "typeRoots": [ 18 | "node_modules/@types", 19 | "node_modules/babylonjs-editor" 20 | ], 21 | "downlevelIteration": true, 22 | "experimentalDecorators": true, 23 | "skipLibCheck": true, 24 | "types": ["jest"], 25 | "lib": [ 26 | "es2015.promise", 27 | "es2015", 28 | "dom" 29 | ] 30 | }, 31 | "exclude": [ 32 | "./node_modules", 33 | "./build", 34 | "./declaration", 35 | "**/*.test.ts" 36 | ] 37 | } 38 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/.eslintignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | build 3 | declaration 4 | scripts -------------------------------------------------------------------------------- /open-source-hosts-plugin/.eslintrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "parser": "@typescript-eslint/parser", 3 | "extends": [ 4 | "airbnb", 5 | "prettier", 6 | "plugin:@typescript-eslint/recommended", 7 | "plugin:jasmine/recommended", 8 | "plugin:react/recommended" 9 | ], 10 | "plugins": [ 11 | "prettier", 12 | "jasmine", 13 | "react", 14 | "@typescript-eslint" 15 | ], 16 | "parserOptions": { 17 | "ecmaVersion": 2022, 18 | "requireConfigFile": false, 19 | "sourceType": "module" 20 | }, 21 | "rules": { 22 | // The Babylon.js API often requires creating new objects via "new" even 23 | // if we don't plan on referencing those objects directly through variables. 24 | // Therefore, we must disable the "no-new" rule. 25 | "no-new": "off", 26 | "react/destructuring-assignment": "off", 27 | "indent": [ 28 | "error", 29 | 2, 30 | { 31 | "SwitchCase": 1 32 | } 33 | ], 34 | "no-underscore-dangle": [ 35 | "warn", 36 | { 37 | "allowAfterThis": true, 38 | "allowAfterSuper": true 39 | } 40 | ], 41 | "no-console": "off", 42 | "no-shadow": "off", 43 | "@typescript-eslint/no-shadow": "error", 44 | "react/jsx-filename-extension": [ 45 | 1, 46 | { 47 | "extensions": [ 48 | ".tsx", 49 | ".ts" 50 | ] 51 | } 52 | ], 53 | "import/prefer-default-export": "off", 54 | "import/extensions": [ 55 | "error", 56 | "ignorePackages", 57 | { 58 | "js": "never", 59 | "jsx": "never", 60 | "ts": "never", 61 | "tsx": "never" 62 | } 63 | ] 64 | }, 65 | "env": { 66 | "browser": true, 67 | "node": true, 68 | "jasmine": true 69 | }, 70 | "settings": { 71 | "import/resolver": { 72 | "node": { 73 | "extensions": [ 74 | ".js", 75 | ".jsx", 76 | ".ts", 77 | ".tsx" 78 | ] 79 | } 80 | } 81 | } 82 | } -------------------------------------------------------------------------------- /open-source-hosts-plugin/.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | node_modules/ 3 | build/ 4 | declaration/ 5 | assets/ -------------------------------------------------------------------------------- /open-source-hosts-plugin/.npmignore: -------------------------------------------------------------------------------- 1 | node_modules/ -------------------------------------------------------------------------------- /open-source-hosts-plugin/CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing Guidelines and Workflow 2 | 3 | Thank you for your interest in contributing to our project. This document covers specifically on how to build and test the open-source-hosts-plugin package. Please refer to the main [CONTRIBUTING](../CONTRIBUTING) document for a detailed explanation on how to contribute to the repository. 4 | 5 | --- 6 | 7 | ## [Contributor Workflow](#contributor-workflow) 8 | 9 | ### Prerequisites 10 | 11 | - Refer to all [prerequisites](../CONTRIBUTING#contributor-workflow#prerequisites) from the primary repository 12 | 13 | ### Building 14 | 15 | 1. Install the plugin dependencies defined in `package.json`: 16 | `npm install` 17 | **Note that this will download the required asset files as a script run during post-install -- this may take a while!** 18 | 1. Format, lint, and compile the Typescript code into Javascript 19 | `npm run build` 20 | 21 | ### Testing 22 | 23 | #### Unit Tests 24 | 25 | You can run the unit test suite by using the command: `npm run test` 26 | 27 | Unit tests will be run automatically across Windows/Linux/MacOSX on every submitted PR. 28 | 29 | #### Integration Tests 30 | 31 | Manually ensure that the plugin loads in the editor, and that a host can be added to the open project without errors. 32 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/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 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/NOTICE: -------------------------------------------------------------------------------- 1 | Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/README.md: -------------------------------------------------------------------------------- 1 | # AWS Tools for Babylon.JS Editor: Open Source Hosts Plugin 2 | 3 | AWS Tools for Babylon.JS Editor: Open Source Hosts Plugin (AWS Tools: Open Source Hosts Plugin) is a plugin that enables BabylonJS Editor workflows with Amazon Sumerian Hosts. 4 | 5 | ## License 6 | 7 | This project is licensed under the Apache-2.0 License. See the [LICENSE](LICENSE) file. 8 | 9 | ## Installation 10 | 11 | 1. If you haven't already, download and install the [Babylon.JS Editor](http://editor.babylonjs.com/) 12 | 1. Open the Babylon.JS Editor, in the upper left corner click Edit > Preferences to open the Preferences tab 13 | 1. Click "Plugins" 14 | 1. Add the plugin to your Babylon.JS Editor: 15 | - If you are installing directly from NPM (recommended): 16 | 1. Select "Add from NPM..." 17 | 1. Type in "@aws/aws-tools-for-babylonjs-editor-open-source-hosts-plugin" 18 | 1. Press "Ok" 19 | - If you'd like to build the plugin from source: 20 | 1. Clone this repository. 21 | 1. Follow the instructions in this package's [CONTRIBUTING.md](CONTRIBUTING.md) file to build the plugin. 22 | 1. Back in the Babylon.JS Editor "Plugins" window, select "Add..." 23 | 1. Locate and select the `open-source-hosts-plugin` folder in your local repository. 24 | 1. Click "Apply" on the bottom left of the preferences window 25 | 26 | Note that the editor is not capable of hot reloading; whenever changes to the plugin are made, the editor must be refreshed (close/open the editor, File->Reload Project, or press F5 with the devtools focused, or type `location.reload()` into the console window in the devtools) to see those changes reflected. 27 | 28 | To debug the plugin, press ctrl+alt+I (or cmd+option+I on a mac) to bring up the dev tools. If you log to the console, those messages will be routed here. 29 | 30 | ## Usage 31 | 32 | ### Add a host to the scene 33 | 34 | > ⚠️ **Note:** There is a known issue that causes undesirable shadowing artifacts when you use the Host characters. This is due to an issue in Babylon.js Editor v4.2.0 with Babylon.js v4.2.1. Until this bug is fixed, you can disable the Screen Space Ambient Occlusion (SSAO) post-processing effect to avoid the issue. Please use the following steps: 1. Click **Scene** in the Graph List. 2. In the Inspector window, select **Rendering** tab. 3. Toggle the **SSAO 2** off. 35 | 36 | Locate `Open Source Hosts Tools` in the editor toolbars. When you expand "Add Hosts", you will see a submenu of possible host characters, each with their own unique model. Select one to spawn it at the origin of your scene. This will automatically copy some scripts to your workspace under `src/scenes/AwsTools/`. It will also create two new nodes in your scene: "AWSConnector" and a node named after the character you selected (example: "Cristine"). 37 | 38 | Select the "AWSConnector" node. 39 | 40 | In the Inspector, you should see a "Cognito Identity Pool ID" field. ⚠️ *If instead you see a spinning icon that doesn't go away, save your project (**File > Save Project**), reload the project (**File > Reload Project...**), and then select the "AWSConnector" node again.* 41 | 42 | Set the "Cognito Identity Pool ID" value of the attached script to a Cognito Identity Pool ID you've configured in your AWS account which has *"AmazonPollyReadOnlyAccess"*. For a full walk-through of how to set this up, see [AWS Infrastructure Setup.md](https://github.com/aws-samples/amazon-sumerian-hosts/blob/mainline2.0/AWS-Infrastructure-Setup.md). 43 | 44 | ### Configure webpack 45 | 46 | The `@amazon-sumerian-hosts` library needs to be configured to use the same instance of BabylonJS as the rest of the project. To do this, use an external text editor to open the `webpack.config.js` file stored in the root directory of your project workspace. Update the `module.exports.resolve` section to match the following: 47 | 48 | ``` 49 | resolve: { 50 | extensions: [".ts", ".js"], 51 | modules: ['node_modules'], 52 | alias: { 53 | '@babylonjs/core': path.resolve('./node_modules/@babylonjs/core') 54 | } 55 | }, 56 | ``` 57 | 58 | ### Test your host 59 | 60 | After you've completed the above steps your host character is ready for use in your application. If you run the scene now you'll see that the host character comes alive and always looks toward the camera as you move it. However, hosts are pretty boring until you start writing code to interact with them. 61 | 62 | To get you started, we've provided a simple script, "HelloWorldScript.ts". To use this script, do the following... 63 | 64 | Add a new dummy node to your scene using the **Add** button *at the top of the screen*: **Add > Dummy Node**. 65 | 66 | Select the dummy node in the scene hierarchy. 67 | 68 | In the Asset Browser, locate the "HelloWorldScript.ts" found under `src/scenes/AwsTools/`. Attach this script to the dummy node by drag-dropping it from the Asset Browser to the "Script" section of the Inspector panel. 69 | 70 | In the Inspector, set the "Host Mesh" property to "Cristine" (or whichever host you added). 71 | 72 | *(Optional)* Change the value of the "Speech Text" property. 73 | 74 | Run the scene. 75 | 76 | Click anywhere in the scene to give it keyboard focus and then press the "t" key to make the host speak. 77 | 78 | ### Next Steps 79 | 80 | Now that you have a working host character in your scene you can start building your custom functionality. Here are some things that will help... 81 | 82 | You can customize your character's voice by editing the "Voice ID", "Language ID", and "Polly Engine" values of the script attached to the host. See the official Amazon Polly documentation covering the [voices and languages available](https://docs.aws.amazon.com/polly/latest/dg/voicelist.html) and the [standard and neural voice engines](https://docs.aws.amazon.com/polly/latest/dg/NTTS-main.html) for more information. 83 | 84 | As you can observe in the "HelloWorldScript.ts", you interact with the host API using the `.host` property of the SumerianHostScript object. For full details on the host API, see the following key documentation entries: 85 | 86 | - [HostObject](https://aws-samples.github.io/amazon-sumerian-hosts/babylonjs_HostObject.html) - This is the class type for the `hostScript.host` property. 87 | - [TextToSpeechFeature](https://aws-samples.github.io/amazon-sumerian-hosts/babylonjs_TextToSpeechFeature.html) - Available via `hostScript.host.TextToSpeechFeature`. Use this API for triggering speeches. 88 | - [PointOfInterestFeature](https://aws-samples.github.io/amazon-sumerian-hosts/babylonjs_PointOfInterestFeature.html) - Available via `hostScript.host.PointOfInterestFeature`. Use this API to control what the character is looking at. 89 | - [GestureFeature](https://aws-samples.github.io/amazon-sumerian-hosts/core_GestureFeature.html) - Available via `hostScript.host.GestureFeature`. Use this API to trigger built-in gestures and emotes. 90 | - [LexFeature](https://aws-samples.github.io/amazon-sumerian-hosts/babylonjs_LexFeature.html) - This class provides the ability to incorporate a Lex chatbot into your scene. The LexFeature class can be used with or without a host. Use of this class is beyond the scope of this documentation but will be showcased in a future sample application. -------------------------------------------------------------------------------- /open-source-hosts-plugin/config/SceneRequirements.json: -------------------------------------------------------------------------------- 1 | { 2 | "runtimeDependencies": { 3 | "@amazon-sumerian-hosts/babylon": "^2", 4 | "aws-sdk": "^2.1096.0", 5 | "util": "^0.12.4" 6 | } 7 | } -------------------------------------------------------------------------------- /open-source-hosts-plugin/jest.config.js: -------------------------------------------------------------------------------- 1 | /** @type {import('ts-jest/dist/types').InitialOptionsTsJest} */ 2 | module.exports = { 3 | preset: 'ts-jest', 4 | testRegex: '(test/.*|(\\.|/)(test|spec))\\.(ts)$', 5 | testEnvironment: 'node', 6 | }; 7 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@aws/aws-tools-for-babylonjs-editor-open-source-hosts-plugin", 3 | "version": "1.0.0", 4 | "description": "AWS Tools for Babylon.JS Editor: Open Source Hosts Plugin is a set of tools meant to communicate with Amazon Sumerian Hosts (https://github.com/aws-samples/amazon-sumerian-hosts) inside of Babylon.JS Editor", 5 | "main": "build/src/index.js", 6 | "author": { 7 | "name": "Amazon Web Services", 8 | "url": "https://aws.amazon.com", 9 | "organization": true 10 | }, 11 | "repository": { 12 | "type": "git", 13 | "url": "https://github.com/aws-samples/aws-tools-for-babylonjs-editor.git", 14 | "directory": "open-source-hosts-plugin" 15 | }, 16 | "license": "Apache 2.0", 17 | "scripts": { 18 | "compile": "tsc -p .", 19 | "lint": "eslint . ", 20 | "lint-fix": "eslint . --fix", 21 | "format": "prettier src/**/*.ts* scripts/**/*.ts* test/**/**.ts --write", 22 | "build": "npm run format && npm run lint-fix && npm run compile && npm run copy-config", 23 | "test": "jest --verbose", 24 | "watch": "tsc -p . --watch", 25 | "copy-config": "node tools/copyConfig", 26 | "postinstall": "npm run retrieve-assets", 27 | "retrieve-assets": "node tools/retrieveHostAssets", 28 | "release": "npm run lint && npm run compile && npm run test && npm run copy-config" 29 | }, 30 | "devDependencies": { 31 | "@types/jest": "^27.4.1", 32 | "@typescript-eslint/eslint-plugin": "^5.16.0", 33 | "@typescript-eslint/parser": "^5.16.0", 34 | "babylonjs-editor": "^4.1.1", 35 | "eslint": "^8.11.0", 36 | "eslint-config-airbnb": "^19.0.4", 37 | "eslint-config-prettier": "^8.5.0", 38 | "eslint-plugin-jasmine": "^4.1.3", 39 | "eslint-plugin-prettier": "^4.0.0", 40 | "jest": "^27.5.1", 41 | "prettier": "^2.5.1", 42 | "prettier-plugin-organize-imports": "^2.3.4", 43 | "ts-jest": "^27.1.4", 44 | "typescript": "^4.6.2" 45 | }, 46 | "dependencies": { 47 | "@amazon-sumerian-hosts/babylon": "^2", 48 | "@babylonjs/core": "4.2.1", 49 | "@blueprintjs/core": "^3.54.0", 50 | "@types/node": "^17.0.21", 51 | "aws-sdk": "^2.1096.0", 52 | "babylonjs": "^4.2.1", 53 | "babylonjs-loaders": "4.2.1", 54 | "fix-path": "^3.0.0", 55 | "fs-extra": "^10.0.1" 56 | }, 57 | "peerDependencies": { 58 | "react": "^17.0.2" 59 | }, 60 | "prettier": { 61 | "printWidth": 80, 62 | "tabWidth": 2, 63 | "useTabs": false, 64 | "semi": true, 65 | "singleQuote": true, 66 | "trailingComma": "es5", 67 | "bracketSpacing": false 68 | } 69 | } -------------------------------------------------------------------------------- /open-source-hosts-plugin/scripts/AwsTools/AwsCognitoIdConnectorScript.ts: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import {Node} from '@babylonjs/core/node'; 5 | import * as AWS from 'aws-sdk'; 6 | import {visibleInInspector} from '../decorators'; 7 | import IAwsConnector from './IAwsConnector'; 8 | 9 | /** 10 | * An IAwsConnector implementation which authenticates using a Cognito 11 | * Identity Pool ID. 12 | */ 13 | export default class AwsCognitoIdConnectorScript 14 | extends Node 15 | implements IAwsConnector 16 | { 17 | @visibleInInspector('string', 'Cognito Identity Pool ID', '') 18 | cognitoIdentityPoolId = ''; 19 | 20 | // @ts-ignore DO NOT EDIT this empty constructor! 21 | protected constructor() {} 22 | 23 | /** 24 | * The AWS region to use when calling AWS services. 25 | */ 26 | getRegion(): string | null { 27 | const cognitoId = this.cognitoIdentityPoolId.trim(); 28 | if (AwsCognitoIdConnectorScript.validateCognitoIdentityPoolId(cognitoId)) { 29 | return cognitoId.split(':')[0]; 30 | } 31 | 32 | return null; 33 | } 34 | 35 | protected _credentials: AWS.Credentials | null = null; 36 | 37 | /** 38 | * The credentials to be used when calling AWS services. 39 | */ 40 | getCredentials(): AWS.Credentials | null { 41 | // We're using lazy initialization of this property because there are 42 | // no BJS Editor lifecyle methods that would allow initialization to 43 | // happen *after* the Inspector-exposed "cognitoIdentityPoolId" value 44 | // has been injected but *before* other scripts may request this 45 | // property. 46 | if (!this._credentials) { 47 | const cognitoId = this.cognitoIdentityPoolId.trim(); 48 | if ( 49 | !AwsCognitoIdConnectorScript.validateCognitoIdentityPoolId(cognitoId) 50 | ) { 51 | alert( 52 | `Error: You must set a valid Cognito Identity Pool ID on the "${this.name}" node.` 53 | ); 54 | return null; 55 | } 56 | this._credentials = new AWS.CognitoIdentityCredentials({ 57 | IdentityPoolId: this.cognitoIdentityPoolId, 58 | }); 59 | } 60 | 61 | return this._credentials; 62 | } 63 | 64 | /** 65 | * Confirms whether the provided value is in the form of a valid 66 | * Cognito Identity Pool ID. 67 | * 68 | * @param value Any string 69 | * @returns true if the value is valid. Othewise, false. 70 | */ 71 | static validateCognitoIdentityPoolId(value: string): boolean { 72 | const cognitoIdRegExp = /[a-z]+-[a-z]+-[0-9]:[a-f0-9-]+([\W]{1}|$)/g; 73 | return cognitoIdRegExp.test(value); 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/scripts/AwsTools/HelloWorldScript.ts: -------------------------------------------------------------------------------- 1 | import {KeyboardEventTypes} from '@babylonjs/core'; 2 | import {Node} from '@babylonjs/core/node'; 3 | import {onKeyboardEvent, visibleInInspector} from '../decorators'; 4 | import SumerianHostScript from './SumerianHostScript'; 5 | 6 | /** 7 | * This simple script will cause a host character to speak when the "t" key 8 | * is pressed. To use, attach this script to a dummy node in your scene, fill 9 | * in the "Host Mesh" value to match the name of the character object, and 10 | * (optionally) change the "Speech Text" value. 11 | * 12 | * Note, when your scene is running it must have focus for keypresses to be 13 | * detected. If a keypress doesn't seem to be working, try clicking on the scene 14 | * and then pressing the key again. 15 | */ 16 | export default class HelloWorldScript extends Node { 17 | // @ts-ignore DO NOT EDIT this empty constructor! 18 | protected constructor() {} 19 | 20 | /** 21 | * The name of the host character object. 22 | */ 23 | @visibleInInspector('string', 'Host Mesh', '') 24 | public hostNodeName: string; 25 | 26 | /** 27 | * The text that should be spoken. 28 | */ 29 | @visibleInInspector('string', 'Speech Text', 'Hello, world!') 30 | public speechText: string; 31 | 32 | @onKeyboardEvent('t', KeyboardEventTypes.KEYDOWN) 33 | protected onSpeakKeyDown(): void { 34 | const node = this.getScene().getNodeByName(this.hostNodeName); 35 | const hostNode = node as SumerianHostScript; 36 | hostNode.host.TextToSpeechFeature.play(this.speechText); 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/scripts/AwsTools/IAwsConnector.ts: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import * as AWS from 'aws-sdk'; 5 | 6 | /** 7 | * Interface implemented by any script that can vend AWS credentials to other 8 | * scripts. 9 | */ 10 | export default interface IAwsConnector { 11 | /** 12 | * The AWS region to use when calling AWS services. 13 | */ 14 | getRegion(): string | null; 15 | 16 | /** 17 | * The credentials to be used when calling AWS services. 18 | */ 19 | getCredentials(): AWS.Credentials | null; 20 | } 21 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/scripts/AwsTools/SumerianHostScript.ts: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | 4 | import {HostObject} from '@amazon-sumerian-hosts/babylon'; 5 | import {Mesh, Observable} from '@babylonjs/core'; 6 | import * as AWS from 'aws-sdk'; 7 | import {fromScene, visibleInInspector} from '../decorators'; 8 | import IAwsConnector from './IAwsConnector'; 9 | 10 | type SumerianHostMetadata = { 11 | bindPoseOffsetName: string; 12 | poiConfigPath: string; 13 | gestureConfigPath: string; 14 | animClipPaths: any; 15 | lookJoint: string; 16 | }; 17 | 18 | /* Define data types for parameters required by the 19 | @amazon-sumerian-hosts/babylon module. */ 20 | 21 | type BlendStateOption = { 22 | clip: string; 23 | name: string; 24 | }; 25 | 26 | type PoiConfigItem = { 27 | name: string; 28 | maxSpeed: number; 29 | reference: string; 30 | forwardAxis: string; 31 | animation: string; 32 | blendStateOptions: BlendStateOption[]; 33 | blendThresholds: number[][]; 34 | }; 35 | 36 | type PoiConfig = PoiConfigItem[]; 37 | 38 | // Our Github Actions will replace this with a commit SHA at release time 39 | // Right now this script is the only runtime asset published by our plugin 40 | // As we build out more runtime complexity into this plugin, this versioning should move there 41 | export const PLUGIN_VERSION = 'development'; 42 | 43 | /** 44 | * This is the script attached to a Sumerian Host. You will typically not need 45 | * to edit this script. Instead, other scripts in your scene should interact 46 | * with the host via the `SumerianHost.host` property which provides a 47 | * HostObject instance. 48 | * 49 | * Host initialization is asynchronous. Your scripts can subscribe to the 50 | * SumerianHost.onHostReadyObserver to be notified when the host is fully 51 | * initialized and ready for use. 52 | * 53 | * Example: 54 | * _In your own script..._ 55 | ``` 56 | // Assume hostNode references a SumerianHost instance. 57 | hostNode.onHostReadyObserver.add(() -> { 58 | hostNode.host.TextToSpeechFeature.play("Hello, world!"); 59 | }); 60 | ``` 61 | */ 62 | export default class SumerianHostScript extends Mesh { 63 | @visibleInInspector('string', 'Voice ID', 'Joanna') 64 | public pollyVoiceId = 'Joanna'; 65 | 66 | @visibleInInspector('string', 'Language ID', 'en-US') 67 | public pollyLanguageId = 'en-US'; 68 | 69 | @visibleInInspector( 70 | 'string', 71 | 'Polly Engine ("standard" or "neural")', 72 | 'neural' 73 | ) 74 | public pollyEngine = 'neural'; 75 | 76 | @fromScene('AWSConnector') 77 | public awsConnector: IAwsConnector; 78 | 79 | /** 80 | * Observer which signals when the SumerianHost.host instance is fully 81 | * initialized and ready for use. 82 | */ 83 | public onHostReadyObserver: Observable = new Observable(); 84 | 85 | /** 86 | * Provides access to the APIs that control host functionality, namely: 87 | * 88 | * Text-to-speech functions, available via `SumerianHost.host.TextToSpeechFeature`. 89 | * See [TextToSpeechFeature API documentation](https://aws-samples.github.io/amazon-sumerian-hosts/babylonjs_TextToSpeechFeature.html). 90 | * 91 | * Point-of-interest tracking, available via `SumerianHost.host.PointOfInterestFeature`. 92 | * See [PointOfInterestFeature API documentation](https://aws-samples.github.io/amazon-sumerian-hosts/babylonjs_PointOfInterestFeature.html). 93 | * 94 | * Gesture functions, available via `SumerianHost.host.GestureFeature`. 95 | * See [GestureFeature API documentation](https://aws-samples.github.io/amazon-sumerian-hosts/core_GestureFeature.html) 96 | * 97 | * Developer note: This property is typed as "HostObject | any" because 98 | * the HostObject's TypeScript definition doesn't include some properties 99 | * that are dynamically added to the object at runtime such as 100 | * HostObject.TextToSpeechFeature and others. The "any" designation 101 | * prevents the TypeScript compiler from reporting errors when accessing those 102 | * dynamic properties. 103 | */ 104 | public host: HostObject | any; 105 | 106 | // @ts-ignore DO NOT EDIT this empty constructor! 107 | protected constructor() {} 108 | 109 | /** 110 | * This method gets called immediately after the constructor. 111 | */ 112 | public async onInitialize(): Promise { 113 | const config: SumerianHostMetadata = this.getMetadata(); 114 | const poiConfig = (await HostObject.loadJson( 115 | config.poiConfigPath 116 | )) as PoiConfig; 117 | 118 | await this.initHostCharacter(config, poiConfig); 119 | this.initPointOfInterestTracking(poiConfig, config.lookJoint); 120 | await this.initTextToSpeech(); 121 | this.onHostReady(); 122 | } 123 | 124 | protected async initHostCharacter( 125 | config: SumerianHostMetadata, 126 | poiConfig: PoiConfig 127 | ): Promise { 128 | const bindPoseOffset = this._scene.animationGroups.find( 129 | (animGroup) => animGroup.name === config.bindPoseOffsetName 130 | ); 131 | 132 | const animClips = await HostObject.loadCharacterAnimations( 133 | this.getScene(), 134 | this, 135 | bindPoseOffset, 136 | config.animClipPaths 137 | ); 138 | const gestureConfig = await HostObject.loadJson(config.gestureConfigPath); 139 | 140 | // set up animations 141 | const assets = { 142 | characterMesh: this, 143 | animClips, 144 | gestureConfig, 145 | poiConfig, 146 | bindPoseOffset, 147 | }; 148 | this.host = HostObject.assembleHost(assets, this.getScene()); 149 | } 150 | 151 | protected initPointOfInterestTracking( 152 | poiConfig: PoiConfig, 153 | lookJoint: string 154 | ): void { 155 | // have the Host track the scene's active camera 156 | HostObject.addPointOfInterestTracking( 157 | this.host, 158 | this._scene, 159 | poiConfig, 160 | lookJoint 161 | ); 162 | 163 | // Track the active camera by default. 164 | const camera = this.getScene().activeCamera; 165 | this.host.PointOfInterestFeature.setTarget(camera); 166 | } 167 | 168 | protected async initTextToSpeech(): Promise { 169 | const region = this.awsConnector.getRegion(); 170 | const credentials = this.awsConnector.getCredentials(); 171 | 172 | // setting this global config is necessary - 173 | // else the Polly SDK's first call to Cognito.getID(...) will fail 174 | AWS.config.region = region; 175 | 176 | const customUserAgent = `AWSToolsForBabylonJSEditor-${PLUGIN_VERSION}`; 177 | 178 | const pollyClient = new AWS.Polly({credentials, region, customUserAgent}); 179 | const pollyPresigner = new AWS.Polly.Presigner({ 180 | service: pollyClient, 181 | }); 182 | 183 | await HostObject.initTextToSpeech(pollyClient, pollyPresigner); 184 | 185 | HostObject.addTextToSpeech( 186 | this.host, 187 | this.getScene(), 188 | this.pollyVoiceId, 189 | this.pollyEngine, 190 | this.pollyLanguageId 191 | ); 192 | } 193 | 194 | /** 195 | * Call this method to signal when the host has finished its asynchronous 196 | * initialization and is ready for use. 197 | */ 198 | protected onHostReady(): void { 199 | this.onHostReadyObserver.notifyObservers(this); 200 | } 201 | 202 | /** 203 | * If the scene is being run from the editor, this method will return the version of 204 | * the configuration that uses local paths. 205 | * Otherwise, this method will return the version of the configuration that uses paths 206 | * relative to the workspace directory. 207 | * @returns {SumerianHostMetadata} 208 | */ 209 | protected getMetadata(): SumerianHostMetadata { 210 | if (this.isRunFromEditor()) { 211 | return this.metadata.editor.sumerian; 212 | } 213 | 214 | return this.metadata.sumerian; 215 | } 216 | 217 | /** 218 | * NodeJS defines the global variable 'process' -- as does recent versions of 219 | * FireFox, which is why we check the name as well. 220 | * We use this to determine whether the code is being run locally from the editor, 221 | * or is running in the browser 222 | * @returns boolean 223 | */ 224 | protected isRunFromEditor(): boolean { 225 | return ( 226 | typeof process !== 'undefined' && 227 | process && 228 | process.release.name === 'node' 229 | ); 230 | } 231 | } 232 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/src/hostAdder.ts: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | /* eslint-disable import/no-unresolved */ 4 | /* eslint-disable @typescript-eslint/no-explicit-any */ 5 | /* eslint no-param-reassign: ["error", { "props": false }] */ 6 | /* eslint-disable class-methods-use-this */ 7 | 8 | import {HostObject} from '@amazon-sumerian-hosts/babylon'; 9 | import {AssetContainer, Scene, SceneLoader} from 'babylonjs'; 10 | import {Editor, SceneImporterTools} from 'babylonjs-editor'; 11 | import path from 'path'; 12 | import { 13 | RELATIVE_ASSETS_DIR, 14 | RELATIVE_GLTF_ASSETS_DIR, 15 | validateAssetsPath, 16 | } from './workspace'; 17 | 18 | /** 19 | * This class is responsible for the process of adding a Sumerian Host to a workspace, 20 | * copying over files from the plugin to the workspace as needed. 21 | */ 22 | class SumerianHostAdder { 23 | /** 24 | * The full path to the GLTF assets directory from which the Host files should be loaded 25 | */ 26 | gLTFAssetsDir: string; 27 | 28 | workSpaceAssetsDir: string; 29 | 30 | /** 31 | * The configuration object contains paths to the model, textures, 32 | * animations, and configuration files that a Sumerian Host needs. 33 | * See: HostObject 34 | */ 35 | characterConfig: any; 36 | 37 | /** 38 | * The identifier of the character we'd like to add to the scene. 39 | */ 40 | characterId: string; 41 | 42 | /** 43 | * 44 | * @param workspaceDir The absolute path to the workspace directory 45 | * @param characterId The identifier of the Host we wish to add 46 | */ 47 | constructor(workSpaceDir: string, characterId: string) { 48 | this.workSpaceAssetsDir = path.join(workSpaceDir, RELATIVE_ASSETS_DIR); 49 | this.gLTFAssetsDir = path.join(workSpaceDir, RELATIVE_GLTF_ASSETS_DIR); 50 | validateAssetsPath(this.gLTFAssetsDir); 51 | 52 | this.characterConfig = HostObject.getCharacterConfig( 53 | this.gLTFAssetsDir, 54 | characterId 55 | ); 56 | 57 | this.characterId = characterId; 58 | } 59 | 60 | public static getAvailableHosts() { 61 | return HostObject.getAvailableCharacters(); 62 | } 63 | 64 | /** 65 | * This method adds the model and textures to the current scene, 66 | * enabling the host to be rendered and exported 67 | * @param {Babylon.Scene} scene 68 | * @returns {Babylon.AssetContainer} 69 | */ 70 | public async addToScene(scene: Scene, editor: Editor) { 71 | const absModelPath = this.characterConfig.modelUrl; 72 | const relModelPath = path.relative(this.workSpaceAssetsDir, absModelPath); 73 | 74 | // this renders the Host in the current scene 75 | const characterAsset = await SceneLoader.LoadAssetContainerAsync( 76 | this.characterConfig.modelUrl, 77 | undefined, 78 | scene 79 | ); 80 | 81 | // rename mesh to something human-readable instead of the default '__root__' 82 | characterAsset.meshes[0].name = this.characterId; 83 | 84 | characterAsset.addAllToScene(); 85 | 86 | // the editor expects the mesh to be configured a certain way, so that 87 | // saving and reloading the scene will work 88 | await SceneImporterTools.Configure(scene, { 89 | isGltf: true, 90 | relativePath: relModelPath, 91 | absolutePath: absModelPath, 92 | editor, 93 | result: characterAsset, 94 | }); 95 | 96 | return characterAsset; 97 | } 98 | 99 | /** 100 | * This method takes a configuration object of absolute paths to animation files, 101 | * and returns the same object where the paths are instead relative to the workspace 102 | * directory 103 | * @param {Object} animUrls An object where the key-value pairs point to absolute paths 104 | * to animation files 105 | * @returns {Object} An object where the key-value pairs point to relative paths 106 | * to animation files 107 | */ 108 | private convertToRelativeAnimationPaths(animUrls) { 109 | const relativeAnimUrls = {}; 110 | Object.keys(animUrls).forEach((key) => { 111 | const relAnimationPath = this.getWorkspaceRelativePath( 112 | this.characterConfig.animUrls[key] 113 | ); 114 | relativeAnimUrls[key] = relAnimationPath; 115 | }); 116 | return relativeAnimUrls; 117 | } 118 | 119 | private getWorkspaceRelativePath(absolutePath: string) { 120 | const workspaceDir = path.join(this.workSpaceAssetsDir, '..'); 121 | return path.relative(workspaceDir, absolutePath); 122 | } 123 | 124 | /** 125 | * This method configures the character so that the attached script 126 | * will be invoked at startup by the Babylon engine. 127 | * 128 | * Note that - by current design in the BabylonJS editor - a mesh 129 | * can only have one script attached to it at a time. 130 | * @param characterAsset 131 | */ 132 | public attachInitScriptToHost(characterAsset: AssetContainer) { 133 | const rootMesh = characterAsset.meshes[0]; 134 | const metadata = rootMesh.metadata ?? {}; 135 | const editorMetadata = metadata.editor ?? {}; 136 | const scriptPath = 'src/scenes/AwsTools/SumerianHostScript.ts'; 137 | 138 | // This version of the Sumerian metadata includes absolute paths to local files -- 139 | // these can be loaded by an application, such as the BabylonJS Editor 140 | editorMetadata.sumerian = { 141 | bindPoseOffsetName: characterAsset.animationGroups[0].name, 142 | poiConfigPath: this.characterConfig.pointOfInterestConfigUrl, 143 | gestureConfigPath: this.characterConfig.gestureConfigUrl, 144 | animClipPaths: this.characterConfig.animUrls, 145 | lookJoint: this.characterConfig.lookJoint, 146 | }; 147 | metadata.editor = editorMetadata; 148 | 149 | // This version of the metadata converts the paths to be relative to the workspace, 150 | // so that they can be served by a running server. 151 | // First, let's make a deep copy 152 | metadata.sumerian = { 153 | ...editorMetadata.sumerian, 154 | animClipPaths: {...editorMetadata.sumerian.animClipPaths}, 155 | pollyConfig: {...editorMetadata.sumerian.pollyConfig}, 156 | }; 157 | metadata.sumerian.animClipPaths = this.convertToRelativeAnimationPaths( 158 | this.characterConfig.animUrls 159 | ); 160 | metadata.sumerian.gestureConfigPath = this.getWorkspaceRelativePath( 161 | this.characterConfig.gestureConfigUrl 162 | ); 163 | metadata.sumerian.poiConfigPath = this.getWorkspaceRelativePath( 164 | this.characterConfig.pointOfInterestConfigUrl 165 | ); 166 | 167 | // This indicates to the BabylonJS editor to instantiate and run 168 | // this script at scene start 169 | metadata.script = { 170 | name: scriptPath, 171 | }; 172 | 173 | rootMesh.metadata = metadata; 174 | } 175 | } 176 | 177 | export {SumerianHostAdder}; 178 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/src/hostMenu.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | /* eslint-disable import/no-unresolved */ 4 | import {MenuItem} from '@blueprintjs/core'; 5 | import {TransformNode} from 'babylonjs'; 6 | import {Editor, SceneExporter, WorkSpace} from 'babylonjs-editor'; 7 | import React from 'react'; 8 | import {SumerianHostAdder} from './hostAdder'; 9 | import { 10 | AssetsNotFoundError, 11 | installDependencies, 12 | prepareWorkspace, 13 | WorkspaceNotPreparedError, 14 | } from './workspace'; 15 | 16 | // eslint-disable-next-line @typescript-eslint/no-var-requires 17 | const configuration = require('../config/SceneRequirements.json'); 18 | 19 | /** 20 | * The configuration that the Sumerian 'add host' menu should be initialized with 21 | */ 22 | interface ISumerianAddHostMenuProps { 23 | /** 24 | * A reference to the BabylonJS Editor object 25 | * @see {@link Editor} 26 | */ 27 | editor: Editor; 28 | 29 | /** 30 | * The absolute path to where the plugin package is found. 31 | */ 32 | pluginPath: string; 33 | } 34 | 35 | export default class SumerianAddHostMenu extends React.Component { 36 | availableHosts: string[]; 37 | 38 | public constructor(props) { 39 | super(props); 40 | this.availableHosts = SumerianHostAdder.getAvailableHosts(); 41 | } 42 | 43 | private _handleAddClick = async (event) => { 44 | const {editor, pluginPath} = this.props; 45 | const currentScene = editor.scene; 46 | const selectedCharacter = event.target.textContent; 47 | const workSpaceDir = WorkSpace.DirPath ?? ''; 48 | const addHostProgress = editor.addTaskFeedback(100, 'Adding Sumerian Host'); 49 | 50 | if (currentScene) { 51 | // First - try to install dependencies in the scene 52 | // It is not a hard blocker if this does not succeed, as the main reason this fails is because 53 | // npm cannot be found - in which case the user has a manual workaround available to them to fix this 54 | try { 55 | editor.updateTaskFeedback( 56 | addHostProgress, 57 | 0, 58 | 'Installing dependencies in scene' 59 | ); 60 | 61 | await installDependencies( 62 | workSpaceDir, 63 | configuration.runtimeDependencies 64 | ); 65 | } catch (error) { 66 | editor.console.logError( 67 | 'Dependencies were not successfully installed due to error: ' 68 | ); 69 | editor.console.logError(error.message); 70 | editor.console.logError( 71 | 'For any failed npm installs above, run each listed install command manually from the root of this Editor workspace.' 72 | ); 73 | } 74 | 75 | try { 76 | editor.updateTaskFeedback( 77 | addHostProgress, 78 | 10, 79 | 'Copying required files into scene' 80 | ); 81 | 82 | await prepareWorkspace(pluginPath, workSpaceDir); 83 | 84 | editor.updateTaskFeedback(addHostProgress, 20, 'Validating assets'); 85 | const hostAdder = new SumerianHostAdder( 86 | workSpaceDir, 87 | selectedCharacter 88 | ); 89 | 90 | // Create AWSConnector node if not already present. 91 | const awsConnectorNodeName = 'AWSConnector'; 92 | if (!currentScene.getNodeByName(awsConnectorNodeName)) { 93 | const awsConnectorNode = new TransformNode( 94 | awsConnectorNodeName, 95 | currentScene 96 | ); 97 | awsConnectorNode.metadata = { 98 | script: { 99 | name: 'src/scenes/AwsTools/AwsCognitoIdConnectorScript.ts', 100 | }, 101 | }; 102 | } 103 | 104 | editor.updateTaskFeedback( 105 | addHostProgress, 106 | 25, 107 | 'Adding Sumerian Host to scene' 108 | ); 109 | const characterAsset = await hostAdder.addToScene(currentScene, editor); 110 | 111 | editor.updateTaskFeedback( 112 | addHostProgress, 113 | 50, 114 | 'Attaching initialization script to Sumerian Host' 115 | ); 116 | hostAdder.attachInitScriptToHost(characterAsset); 117 | 118 | editor.updateTaskFeedback(addHostProgress, 75, 'Updating editor'); 119 | 120 | // update script mapping; this gets done automatically when the user hits 'play' 121 | // as the scene auto-saves (exports) before it runs, but we want to update ASAP 122 | // so that the scene code-base (which has the script mapping copied into it) reflects the changes 123 | await SceneExporter.GenerateScripts(editor); 124 | 125 | editor.updateTaskFeedback( 126 | addHostProgress, 127 | 100, 128 | 'Successfully added Sumerian Host' 129 | ); 130 | } catch (error) { 131 | let errorMessage = 132 | 'An error has occurred while adding a Sumerian Host:'; 133 | let errorStatus = 'An error has occurred while adding a Sumerian Host'; 134 | switch (error.constructor) { 135 | case AssetsNotFoundError: 136 | errorMessage = 137 | 'An error has occurred while initializing a Sumerian Host; the assets could not be found. Were they downloaded correctly when this plugin was installed?'; 138 | errorStatus = 139 | 'An error has ocurred while initializing a Sumerian Host'; 140 | break; 141 | case WorkspaceNotPreparedError: 142 | errorMessage = 143 | 'An error has occurred while copying necessary files into your workspace.'; 144 | errorStatus = 'An error has ocurred while preparing the workspace'; 145 | break; 146 | default: 147 | break; 148 | } 149 | 150 | console.log(error); 151 | editor.console.logError(errorMessage); 152 | editor.console.logError(error.message); 153 | editor.updateTaskFeedback(addHostProgress, 0, errorStatus); 154 | } finally { 155 | editor.graph.refresh(); // update editor's scene graph to show the new Host node 156 | editor.closeTaskFeedback(addHostProgress, 15000); 157 | } 158 | } 159 | }; 160 | 161 | public render(): React.ReactNode { 162 | return ( 163 | 164 | {this.availableHosts.map((characterId) => ( 165 | 170 | ))} 171 | 172 | ); 173 | } 174 | } 175 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/src/index.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | // eslint-disable-next-line import/no-unresolved 4 | import {Editor, IPlugin, IPluginConfiguration} from 'babylonjs-editor'; 5 | // We need to call this when the plugin is loaded so that the required file loaders 6 | // (specifically for gltf) are properly loaded into the engine. 7 | import 'babylonjs-loaders'; 8 | import * as React from 'react'; 9 | import OpenSourceHostsToolbar from './toolbar'; 10 | 11 | /** 12 | * Registers the plugin by returning the IPlugin content. 13 | * @param editor defines the main reference to the editor. 14 | * @param configuration defines the configuration of the plugin: its path, etc.). 15 | * @returns an object that implements IPlugin 16 | */ 17 | // The BabylonJS editor calls require(), which expects this function to be exported this way 18 | // eslint-disable-next-line import/prefer-default-export 19 | export const registerEditorPlugin = ( 20 | editor: Editor, 21 | configuration: IPluginConfiguration 22 | ): IPlugin => ({ 23 | /** 24 | * Defines the list of all toolbar elements to add when the plugin has been loaded. 25 | */ 26 | toolbar: [ 27 | { 28 | buttonLabel: 'Open Source Hosts Tools', 29 | buttonIcon: 'export', 30 | content: ( 31 | 35 | ), 36 | }, 37 | ], 38 | }); 39 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/src/toolbar.tsx: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | import {Menu} from '@blueprintjs/core'; 4 | // eslint-disable-next-line import/no-unresolved 5 | import {Editor} from 'babylonjs-editor'; 6 | import * as React from 'react'; 7 | import SumerianAddHostMenu from './hostMenu'; 8 | 9 | /** 10 | * The configuration that the Sumerian Toolbar should be initialized with. 11 | */ 12 | interface IOpenSourceHostsToolbarProps { 13 | /** 14 | * A reference to the BabylonJS Editor object. 15 | * @see {@link Editor} 16 | */ 17 | editor: Editor; 18 | 19 | /** 20 | * The absolute path to where the plugin package is found. 21 | */ 22 | pluginPath: string; 23 | } 24 | 25 | /** 26 | * The Sumerian toolbar is a single button that, when clicked, shows a drop-down menu 27 | * of helpful tools and dialogs that allow the user to interact with AWS, the Sumerian Hosts, etc. 28 | */ 29 | // eslint-disable-next-line react/prefer-stateless-function 30 | class OpenSourceHostsToolbar extends React.Component { 31 | public render(): React.ReactNode { 32 | const {editor, pluginPath} = this.props; 33 | 34 | return ( 35 | 36 | 41 | 42 | ); 43 | } 44 | } 45 | 46 | export default OpenSourceHostsToolbar; 47 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/src/workspace.ts: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | /* eslint-disable max-classes-per-file */ 4 | /* eslint-disable @typescript-eslint/no-explicit-any */ 5 | 6 | import {execFile} from 'child_process'; 7 | import fixPath from 'fix-path'; 8 | import fs from 'fs-extra'; 9 | import os from 'os'; 10 | import path from 'path'; 11 | import util from 'util'; 12 | 13 | class DependenciesNotInstalledError extends Error { 14 | cause?: Error; 15 | 16 | constructor(message: string, cause?: Error) { 17 | super(message); 18 | this.name = this.constructor.name; 19 | this.cause = cause; 20 | } 21 | } 22 | 23 | class WorkspaceNotPreparedError extends Error { 24 | cause?: Error; 25 | 26 | constructor(message: string, cause?: Error) { 27 | super(message); 28 | this.name = this.constructor.name; 29 | this.cause = cause; 30 | } 31 | } 32 | 33 | class AssetsNotFoundError extends Error { 34 | constructor(message: string) { 35 | super(message); 36 | this.name = this.constructor.name; 37 | } 38 | } 39 | 40 | // These are all relative to the package.json file of the respective projects 41 | const RELATIVE_ASSETS_DIR = 'assets'; 42 | const RELATIVE_GLTF_ASSETS_DIR = path.join(RELATIVE_ASSETS_DIR, 'gLTF'); 43 | 44 | // Any scripts in this plugin subdirectory will be copied to the workspace. 45 | const RELATIVE_PLUGIN_SCRIPTS_PATH = path.join('scripts', 'AwsTools'); 46 | 47 | // BabylonJS Editor requires scripts be stored anywhere below the 48 | // `src/scenes/` directory within the workspace. 49 | const RELATIVE_WORKSPACE_SCRIPTS_PATH = path.join('src', 'scenes', 'AwsTools'); 50 | 51 | /** 52 | * Copy the directory from one path to the other one. 53 | * @param fromDir The source directory 54 | * @param toDir The destination directory 55 | */ 56 | const copyDirectory = async (fromDir: string, toDir: string): Promise => { 57 | await fs.promises.mkdir(toDir, {recursive: true}); // will create nested directories if they don't exist 58 | await fs.copy(fromDir, toDir, { 59 | overwrite: false, 60 | errorOnExist: false, 61 | }); 62 | }; 63 | 64 | /** 65 | * This method runs `npm install` of all required runtime directories on the workspace directory 66 | * @param workSpaceDir The absolute path to the workspace open in the BabylonJS Editor 67 | * @param runtimeDependencies An object that contains runtime dependencies and their versions as key-value pairs 68 | * @throws {DependenciesNotInstalledError} 69 | */ 70 | const installDependencies = async ( 71 | workSpaceDir: string, 72 | runtimeDependencies: { 73 | [name: string]: string; 74 | } 75 | ): Promise => { 76 | try { 77 | // Check the environment for the path to the interactive shell, 78 | // which is likely to have $PATH set correctly to find npm. 79 | // Note that BabylonJS Editor expects npm to be installed locally, 80 | // so we're reasonably confident it exists. 81 | const shell = process.env[os.platform() === 'win32' ? 'COMSPEC' : 'SHELL']; 82 | 83 | fixPath(); 84 | 85 | const installPromises: any[] = []; 86 | 87 | const execFilePromise = util.promisify(execFile); 88 | 89 | // queue up `npm install` commands 90 | Object.keys(runtimeDependencies).forEach((name) => { 91 | const version = runtimeDependencies[name]; 92 | installPromises.push( 93 | execFilePromise('npm', ['install', `${name}@${version}`], { 94 | cwd: workSpaceDir, 95 | shell, 96 | }) 97 | ); 98 | }); 99 | 100 | await Promise.all(installPromises); 101 | } catch (error) { 102 | // Ideally we'd like to pass the old error as the cause for the new error, 103 | // but BabylonJS Editor uses an old version of typescript that doesn't use this field 104 | // for errors. 105 | console.log(`Original error's stack: ${error.stack}`); 106 | throw new DependenciesNotInstalledError(error.message, error); 107 | } 108 | }; 109 | 110 | /** 111 | * This method runs copies any necessary files over from the 112 | * plugin directory to the workspace directory - assets, scripts, etc. 113 | * @param pluginDir The absolute path to the directory where the plugin resides 114 | * @param workSpaceDir The absolute path to the workspace open in the BabylonJS Editor 115 | * @throws {WorkspaceNotPreparedError} 116 | */ 117 | const prepareWorkspace = async ( 118 | pluginDir: string, 119 | workSpaceDir: string 120 | ): Promise => { 121 | try { 122 | const copyPromises: any[] = []; 123 | 124 | // Copy our custom Editor scripts to the workspace. 125 | const scriptsSourceDirectory = path.join( 126 | pluginDir, 127 | RELATIVE_PLUGIN_SCRIPTS_PATH 128 | ); 129 | const scriptsTargetDirectory = path.join( 130 | workSpaceDir, 131 | RELATIVE_WORKSPACE_SCRIPTS_PATH 132 | ); 133 | copyPromises.push( 134 | copyDirectory(scriptsSourceDirectory, scriptsTargetDirectory) 135 | ); 136 | 137 | // copy asset directory into the workspace, so that they will be bundled relative to the workspace 138 | const pluginAssetDir = path.join(pluginDir, RELATIVE_GLTF_ASSETS_DIR); 139 | const workspaceAssetDir = path.join(workSpaceDir, RELATIVE_GLTF_ASSETS_DIR); 140 | 141 | copyPromises.push(copyDirectory(pluginAssetDir, workspaceAssetDir)); 142 | 143 | await Promise.all(copyPromises); 144 | } catch (error) { 145 | // Ideally we'd like to pass the old error as the cause for the new error, 146 | // but BabylonJS Editor uses an old version of typescript that doesn't use this field 147 | // for errors. 148 | console.log(`Original error's stack: ${error.stack}`); 149 | throw new WorkspaceNotPreparedError(error.message, error); 150 | } 151 | }; 152 | 153 | /** 154 | * This method validates that the assets directory exists - the assets 155 | * must be asynchronously downloaded as part of the plugin, and are thus not 156 | * guaranteed to exist. 157 | * @param assetsDir The path to the assets directory 158 | * @throws {AssetsNotFoundError} 159 | */ 160 | const validateAssetsPath = (assetsDir: string): void => { 161 | if (!fs.existsSync(assetsDir)) { 162 | throw new AssetsNotFoundError( 163 | `Sumerian Host assets could not be found at ${assetsDir}` 164 | ); 165 | } 166 | }; 167 | 168 | export { 169 | prepareWorkspace, 170 | validateAssetsPath, 171 | installDependencies, 172 | AssetsNotFoundError, 173 | DependenciesNotInstalledError, 174 | WorkspaceNotPreparedError, 175 | RELATIVE_ASSETS_DIR, 176 | RELATIVE_GLTF_ASSETS_DIR, 177 | RELATIVE_WORKSPACE_SCRIPTS_PATH as RELATIVE_WORKSPACE_SCRIPT_PATH, 178 | }; 179 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/test/workspace.test.ts: -------------------------------------------------------------------------------- 1 | import fs from 'fs-extra'; 2 | import path from 'path'; 3 | import { 4 | AssetsNotFoundError, 5 | prepareWorkspace, 6 | validateAssetsPath, 7 | WorkspaceNotPreparedError, 8 | } from '../src/workspace'; 9 | 10 | jest.mock('fs-extra', () => ({ 11 | ...jest.requireActual('fs-extra'), 12 | promises: { 13 | copyFile: jest.fn().mockResolvedValue(null), 14 | mkdir: jest.fn().mockResolvedValue(null), 15 | }, 16 | copy: jest.fn(), 17 | existsSync: jest.fn(), 18 | })); 19 | 20 | describe('workspace', () => { 21 | beforeEach(() => { 22 | jest.resetAllMocks(); 23 | }); 24 | 25 | describe('prepareWorkspace', () => { 26 | it('should copy scripts to workspace', async () => { 27 | const mockCopy = jest.fn(); 28 | jest.spyOn(fs, 'copy').mockImplementation(mockCopy); 29 | 30 | await prepareWorkspace('testPluginDir', 'testWorkSpaceDir'); 31 | 32 | const fromPath = path.join('testPluginDir', 'scripts', 'AwsTools'); 33 | const toPath = path.join('testWorkSpaceDir', 'src', 'scenes', 'AwsTools'); 34 | 35 | expect(mockCopy).toHaveBeenCalledWith( 36 | fromPath, 37 | toPath, 38 | expect.anything() 39 | ); 40 | }); 41 | 42 | it('should copy glTF assets to workspace', async () => { 43 | const mockCopy = jest.fn(); 44 | jest.spyOn(fs, 'copy').mockImplementation(mockCopy); 45 | 46 | await prepareWorkspace('testPluginDir', 'testWorkSpaceDir'); 47 | 48 | const fromPath = path.join('testPluginDir', 'assets', 'gLTF'); 49 | const toPath = path.join('testWorkSpaceDir', 'assets', 'gLTF'); 50 | 51 | expect(mockCopy).toHaveBeenCalledWith( 52 | fromPath, 53 | toPath, 54 | expect.anything() 55 | ); 56 | }); 57 | 58 | it('should create workspace directories for scripts', async () => { 59 | const mockMkDir = jest.fn(); 60 | jest.spyOn(fs.promises, 'mkdir').mockImplementation(mockMkDir); 61 | 62 | await prepareWorkspace('testPluginDir', 'testWorkSpaceDir'); 63 | 64 | const scriptsDirPath = path.join( 65 | 'testWorkSpaceDir', 66 | 'src', 67 | 'scenes', 68 | 'AwsTools' 69 | ); 70 | 71 | expect(mockMkDir).toHaveBeenCalledWith(scriptsDirPath, {recursive: true}); 72 | }); 73 | 74 | it('should create workspace directories for glTF assets', async () => { 75 | const mockMkDir = jest.fn(); 76 | jest.spyOn(fs.promises, 'mkdir').mockImplementation(mockMkDir); 77 | 78 | await prepareWorkspace('testPluginDir', 'testWorkSpaceDir'); 79 | 80 | const gltfDirPath = path.join('testWorkSpaceDir', 'assets', 'gLTF'); 81 | 82 | expect(mockMkDir).toHaveBeenCalledWith(gltfDirPath, {recursive: true}); 83 | }); 84 | 85 | it('should throw custom WorkspaceNotPreparedError when there are errors with fs package', async () => { 86 | // Fake a copy error. 87 | jest 88 | .spyOn(fs, 'copy') 89 | .mockImplementation(() => Promise.reject(new Error('mock copy error'))); 90 | 91 | await expect( 92 | prepareWorkspace('testPluginDir', 'testWorkSpaceDir') 93 | ).rejects.toThrow(WorkspaceNotPreparedError); 94 | }); 95 | }); 96 | 97 | describe('validateAssetsPath', () => { 98 | it('should return nothing when the assetDir exists', () => { 99 | const spyExistsSync = jest 100 | .spyOn(fs, 'existsSync') 101 | .mockReturnValueOnce(true); 102 | validateAssetsPath('testPluginDir'); 103 | 104 | expect(spyExistsSync).toHaveBeenCalledTimes(1); 105 | }); 106 | 107 | it('should throw Error when the assetDir does not exist', () => { 108 | jest.spyOn(fs, 'existsSync').mockReturnValueOnce(false); 109 | function testValidateAsset() { 110 | validateAssetsPath('testPluginDir'); 111 | } 112 | 113 | expect(testValidateAsset).toThrowError( 114 | 'Sumerian Host assets could not be found at ' 115 | ); 116 | 117 | expect(testValidateAsset).toThrowError(AssetsNotFoundError); 118 | }); 119 | }); 120 | }); 121 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/tools/copyConfig.js: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | // eslint-disable-next-line @typescript-eslint/no-var-requires 4 | const fs = require('fs-extra'); 5 | // eslint-disable-next-line @typescript-eslint/no-var-requires 6 | const path = require('path'); 7 | 8 | const srcDir = path.join(__dirname, '..', 'config'); 9 | 10 | const destDir = path.join(__dirname, '..', 'build/config'); 11 | if (!fs.existsSync(destDir)) { 12 | fs.mkdirSync(destDir, {recursive: true}); 13 | } 14 | 15 | fs.copySync(srcDir, destDir); 16 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/tools/retrieveHostAssets.js: -------------------------------------------------------------------------------- 1 | // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | // SPDX-License-Identifier: Apache-2.0 3 | // eslint-disable-next-line @typescript-eslint/no-var-requires 4 | const {spawnSync} = require('child_process'); 5 | // eslint-disable-next-line @typescript-eslint/no-var-requires 6 | const {existsSync, copySync, rmSync, ensureDirSync} = require('fs-extra'); 7 | // eslint-disable-next-line @typescript-eslint/no-var-requires 8 | const path = require('path'); 9 | // eslint-disable-next-line @typescript-eslint/no-var-requires 10 | const process = require('process'); 11 | 12 | // check whether git exists. If not, throw the error and ask customers to install it. 13 | const {stdout, error} = spawnSync('git', ['--version']); 14 | if (error) { 15 | console.error( 16 | `${error} Please check that Git is installed and set as the environment variable.` 17 | ); 18 | process.exit(1); 19 | } 20 | console.log(stdout.toString('utf8')); 21 | 22 | const assetsDir = path.join(__dirname, '../assets'); 23 | 24 | // check whether Assets folder exists. 25 | if (existsSync(assetsDir)) { 26 | console.log('Assets have already been downloaded'); 27 | process.exit(0); 28 | } 29 | 30 | // Clone repo with no history, no file content, and of only the topmost directory 31 | // This is essentially the 'smallest' clone we can do 32 | console.log('Now downloading asset files -- this can take up to ten minutes'); 33 | spawnSync( 34 | 'git', 35 | [ 36 | 'clone', 37 | '--depth', 38 | '1', 39 | '--filter=blob:none', 40 | '--sparse', 41 | 'https://github.com/aws-samples/amazon-sumerian-hosts', 42 | ], 43 | {stdio: ['ignore', 'inherit', 'inherit']} 44 | ); 45 | 46 | const hostDir = path.join(__dirname, '../amazon-sumerian-hosts'); 47 | process.chdir(hostDir); 48 | 49 | // Check out files matching this pattern -- in this case we're filtering by directory 50 | spawnSync('git', ['sparse-checkout', 'set', 'd1', 'packages/demos-babylon/src/character-assets'], { 51 | stdio: ['ignore', 'inherit', 'inherit'], 52 | }); 53 | 54 | process.chdir('../'); 55 | 56 | // We want our asset files to be nested under /gLTF 57 | const gLTFDir = path.join(assetsDir, 'gLTF'); 58 | ensureDirSync(gLTFDir); 59 | 60 | copySync( 61 | path.join(process.cwd(), 'amazon-sumerian-hosts/packages/demos-babylon/src/character-assets'), 62 | gLTFDir 63 | ); 64 | 65 | rmSync(hostDir, {recursive: true, force: true}); 66 | -------------------------------------------------------------------------------- /open-source-hosts-plugin/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es6", 4 | // the following is necessary so BabylonJS can import our plugin - it is itself a CommonJS module 5 | "module": "CommonJS", 6 | "moduleResolution": "node", 7 | "sourceMap": true, 8 | "declaration": true, 9 | "outDir": "./build/src", 10 | "declarationDir": "./declaration/src", 11 | "jsx": "react", 12 | "strictNullChecks": true, 13 | "noUnusedLocals": true, 14 | "noUnusedParameters": true, 15 | "allowSyntheticDefaultImports": true, 16 | "esModuleInterop": true, 17 | "typeRoots": [ 18 | "node_modules/@types", 19 | "node_modules/babylonjs-editor" 20 | ], 21 | "downlevelIteration": true, 22 | "experimentalDecorators": true, 23 | "skipLibCheck": true, 24 | "types": [ 25 | "node", 26 | "jest" 27 | ], 28 | "lib": [ 29 | "es2015.promise", 30 | "es2015", 31 | "dom" 32 | ] 33 | }, 34 | "exclude": [ 35 | "./node_modules", 36 | "./build", 37 | "./declaration", 38 | "./scripts", 39 | "**/*.test.ts" 40 | ] 41 | } --------------------------------------------------------------------------------