├── .cfignore ├── .env.example ├── .eslintignore ├── .eslintrc.yml ├── .gitignore ├── .travis.yml ├── CONTRIBUTING.md ├── LICENSE ├── README.md ├── app.js ├── config ├── error-handler.js ├── express.js └── security.js ├── manifest.yml ├── package-lock.json ├── package.json ├── public ├── css │ ├── browser-compatibility.css │ └── watson-bootstrap-style.css ├── demo.js ├── fonts │ ├── glyphicons-halflings-regular.eot │ ├── glyphicons-halflings-regular.svg │ ├── glyphicons-halflings-regular.ttf │ ├── glyphicons-halflings-regular.woff │ ├── helvneueboldforibm.eot │ ├── helvneueboldforibm.svg │ ├── helvneueboldforibm.ttf │ ├── helvneueboldforibm.woff │ ├── helvneuebolditalicforibm.eot │ ├── helvneuebolditalicforibm.svg │ ├── helvneuebolditalicforibm.ttf │ ├── helvneuebolditalicforibm.woff │ ├── helvneuecondforibm.eot │ ├── helvneuecondforibm.svg │ ├── helvneuecondforibm.ttf │ ├── helvneuecondforibm.woff │ ├── helvneuelightcondforibm.eot │ ├── helvneuelightcondforibm.svg │ ├── helvneuelightcondforibm.ttf │ ├── helvneuelightcondforibm.woff │ ├── helvneuelightforibm.eot │ ├── helvneuelightforibm.svg │ ├── helvneuelightforibm.ttf │ ├── helvneuelightforibm.woff │ ├── helvneuelightitalicforibm.eot │ ├── helvneuelightitalicforibm.svg │ ├── helvneuelightitalicforibm.ttf │ ├── helvneuelightitalicforibm.woff │ ├── helvneuemediumforibm.eot │ ├── helvneuemediumforibm.svg │ ├── helvneuemediumforibm.ttf │ ├── helvneuemediumforibm.woff │ ├── helvneuemediumitalicforibm.eot │ ├── helvneuemediumitalicforibm.svg │ ├── helvneuemediumitalicforibm.ttf │ ├── helvneuemediumitalicforibm.woff │ ├── helvneueromanforibm.eot │ ├── helvneueromanforibm.svg │ ├── helvneueromanforibm.ttf │ ├── helvneueromanforibm.woff │ ├── helvneueromanitalicforibm.eot │ ├── helvneueromanitalicforibm.svg │ ├── helvneueromanitalicforibm.ttf │ ├── helvneueromanitalicforibm.woff │ ├── menlo.eot │ ├── menlo.svg │ ├── menlo.ttf │ └── menlo.woff ├── images │ ├── drop-down-arrow-white.svg │ ├── drop-down-arrow.svg │ ├── drop-up-arrow.svg │ ├── favicon │ │ ├── android-icon-144x144.png │ │ ├── android-icon-192x192.png │ │ ├── android-icon-36x36.png │ │ ├── android-icon-48x48.png │ │ ├── android-icon-72x72.png │ │ ├── android-icon-96x96.png │ │ ├── apple-icon-114x114.png │ │ ├── apple-icon-120x120.png │ │ ├── apple-icon-144x144.png │ │ ├── apple-icon-152x152.png │ │ ├── apple-icon-180x180.png │ │ ├── apple-icon-57x57.png │ │ ├── apple-icon-60x60.png │ │ ├── apple-icon-72x72.png │ │ ├── apple-icon-76x76.png │ │ ├── apple-icon-precomposed.png │ │ ├── apple-icon.png │ │ ├── favicon-16x16.png │ │ ├── favicon-32x32.png │ │ ├── favicon-96x96.png │ │ ├── favicon.ico │ │ ├── ms-icon-144x144.png │ │ ├── ms-icon-150x150.png │ │ ├── ms-icon-310x310.png │ │ └── ms-icon-70x70.png │ ├── information-teal.svg │ ├── information.svg │ ├── language-translator.svg │ ├── link.svg │ └── reset.svg └── js │ ├── css_browser_selector.js │ └── tab.js ├── server.js ├── test └── test.express.js └── views └── index.ejs /.cfignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .env 3 | coverage 4 | -------------------------------------------------------------------------------- /.env.example: -------------------------------------------------------------------------------- 1 | # see https://cloud.ibm.com/docs/watson?topic=watson-iam 2 | LANGUAGE_TRANSLATOR_URL=https://gateway.watsonplatform.net/language-translator/api 3 | LANGUAGE_TRANSLATOR_IAM_APIKEY= -------------------------------------------------------------------------------- /.eslintignore: -------------------------------------------------------------------------------- 1 | public/js/css_browser_selector.js -------------------------------------------------------------------------------- /.eslintrc.yml: -------------------------------------------------------------------------------- 1 | env: 2 | browser: true 3 | jquery: true 4 | node: true 5 | mocha: true 6 | es6: true 7 | extends: 'eslint:recommended' 8 | rules: 9 | indent: 10 | - error 11 | - 2 12 | linebreak-style: 13 | - error 14 | - unix 15 | quotes: 16 | - error 17 | - single 18 | semi: 19 | - error 20 | - always 21 | no-console: 22 | - off -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .env 3 | npm-debug.log* 4 | .DS_Store 5 | .nyc_output 6 | /.idea/ 7 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: node_js 2 | sudo: true 3 | node_js: 12 4 | script: 5 | - npm run lint 6 | - npm run codecov 7 | env: 8 | global: 9 | - BX_APP=language-translator-demo 10 | - BX_API=https://api.ng.bluemix.net 11 | - BX_ORGANIZATION=WatsonPlatformServices 12 | - BX_SPACE=demos 13 | before_deploy: npm install -g bx-blue-green 14 | deploy: 15 | - provider: script 16 | script: bx-blue-green-travis 17 | on: 18 | branch: master 19 | repo: watson-developer-cloud/language-translator-nodejs 20 | skip_cleanup: true 21 | - provider: script 22 | skip_cleanup: true 23 | script: npx semantic-release 24 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Questions 2 | 3 | If you are having problems using the APIs or have a question about the IBM 4 | Watson Services, please ask a question on 5 | [dW Answers](https://developer.ibm.com/answers/questions/ask/?topics=watson) 6 | or [Stack Overflow](http://stackoverflow.com/questions/ask?tags=ibm-watson). 7 | 8 | # Code 9 | 10 | * Our style guide is based on [Google's](https://google.github.io/styleguide/jsguide.html), most of it is automaticaly enforced (and can be automatically applied with `npm run autofix`) 11 | * Commits should follow the [Angular commit message guidelines](https://github.com/angular/angular/blob/master/CONTRIBUTING.md#-commit-message-guidelines). This is because our release tool uses this format for determining release versions and generating changelogs. To make this easier, we recommend using the [Commitizen CLI](https://github.com/commitizen/cz-cli) with the `cz-conventional-changelog` adapter. 12 | 13 | # Issues 14 | 15 | If you encounter an issue with the Node.js library, you are welcome to submit 16 | a [bug report](https://github.com/watson-developer-cloud/language-translator-nodejs/issues). 17 | Before that, please search for similar issues. It's possible somebody has 18 | already encountered this issue. 19 | 20 | # Pull Requests 21 | 22 | If you want to contribute to the repository, follow these steps: 23 | 24 | 1. Fork the repo. 25 | 2. Develop and test your code changes: `npm install -d && npm test`. 26 | 3. Travis-CI will run the tests for all services once your changes are merged. 27 | 4. Add a test for your changes. Only refactoring and documentation changes require no new tests. 28 | 5. Make the test pass. 29 | 6. Commit your changes. 30 | 7. Push to your fork and submit a pull request. 31 | 32 | # Developer's Certificate of Origin 1.1 33 | 34 | By making a contribution to this project, I certify that: 35 | 36 | (a) The contribution was created in whole or in part by me and I 37 | have the right to submit it under the open source license 38 | indicated in the file; or 39 | 40 | (b) The contribution is based upon previous work that, to the best 41 | of my knowledge, is covered under an appropriate open source 42 | license and I have the right under that license to submit that 43 | work with modifications, whether created in whole or in part 44 | by me, under the same open source license (unless I am 45 | permitted to submit under a different license), as indicated 46 | in the file; or 47 | 48 | (c) The contribution was provided directly to me by some other 49 | person who certified (a), (b) or (c) and I have not modified 50 | it. 51 | 52 | (d) I understand and agree that this project and the contribution 53 | are public and that a record of the contribution (including all 54 | personal information I submit with it, including my sign-off) is 55 | maintained indefinitely and may be redistributed consistent with 56 | this project or the open source license(s) involved. 57 | 58 | ## Tests 59 | 60 | Ideally, we'd like to see both unit and innervation tests on each method. 61 | (Unit tests do not actually connect to the Watson service, integration tests do.) 62 | 63 | Out of the box, `npm test` runs linting and unit tests, but skips the integration tests, 64 | because they require credentials. -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | 2 | Apache License 3 | Version 2.0, January 2004 4 | http://www.apache.org/licenses/ 5 | 6 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 7 | 8 | 1. Definitions. 9 | 10 | "License" shall mean the terms and conditions for use, reproduction, 11 | and distribution as defined by Sections 1 through 9 of this document. 12 | 13 | "Licensor" shall mean the copyright owner or entity authorized by 14 | the copyright owner that is granting the License. 15 | 16 | "Legal Entity" shall mean the union of the acting entity and all 17 | other entities that control, are controlled by, or are under common 18 | control with that entity. For the purposes of this definition, 19 | "control" means (i) the power, direct or indirect, to cause the 20 | direction or management of such entity, whether by contract or 21 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 22 | outstanding shares, or (iii) beneficial ownership of such entity. 23 | 24 | "You" (or "Your") shall mean an individual or Legal Entity 25 | exercising permissions granted by this License. 26 | 27 | "Source" form shall mean the preferred form for making modifications, 28 | including but not limited to software source code, documentation 29 | source, and configuration files. 30 | 31 | "Object" form shall mean any form resulting from mechanical 32 | transformation or translation of a Source form, including but 33 | not limited to compiled object code, generated documentation, 34 | and conversions to other media types. 35 | 36 | "Work" shall mean the work of authorship, whether in Source or 37 | Object form, made available under the License, as indicated by a 38 | copyright notice that is included in or attached to the work 39 | (an example is provided in the Appendix below). 40 | 41 | "Derivative Works" shall mean any work, whether in Source or Object 42 | form, that is based on (or derived from) the Work and for which the 43 | editorial revisions, annotations, elaborations, or other modifications 44 | represent, as a whole, an original work of authorship. For the purposes 45 | of this License, Derivative Works shall not include works that remain 46 | separable from, or merely link (or bind by name) to the interfaces of, 47 | the Work and Derivative Works thereof. 48 | 49 | "Contribution" shall mean any work of authorship, including 50 | the original version of the Work and any modifications or additions 51 | to that Work or Derivative Works thereof, that is intentionally 52 | submitted to Licensor for inclusion in the Work by the copyright owner 53 | or by an individual or Legal Entity authorized to submit on behalf of 54 | the copyright owner. For the purposes of this definition, "submitted" 55 | means any form of electronic, verbal, or written communication sent 56 | to the Licensor or its representatives, including but not limited to 57 | communication on electronic mailing lists, source code control systems, 58 | and issue tracking systems that are managed by, or on behalf of, the 59 | Licensor for the purpose of discussing and improving the Work, but 60 | excluding communication that is conspicuously marked or otherwise 61 | designated in writing by the copyright owner as "Not a Contribution." 62 | 63 | "Contributor" shall mean Licensor and any individual or Legal Entity 64 | on behalf of whom a Contribution has been received by Licensor and 65 | subsequently incorporated within the Work. 66 | 67 | 2. Grant of Copyright License. Subject to the terms and conditions of 68 | this License, each Contributor hereby grants to You a perpetual, 69 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 70 | copyright license to reproduce, prepare Derivative Works of, 71 | publicly display, publicly perform, sublicense, and distribute the 72 | Work and such Derivative Works in Source or Object form. 73 | 74 | 3. Grant of Patent License. Subject to the terms and conditions of 75 | this License, each Contributor hereby grants to You a perpetual, 76 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 77 | (except as stated in this section) patent license to make, have made, 78 | use, offer to sell, sell, import, and otherwise transfer the Work, 79 | where such license applies only to those patent claims licensable 80 | by such Contributor that are necessarily infringed by their 81 | Contribution(s) alone or by combination of their Contribution(s) 82 | with the Work to which such Contribution(s) was submitted. If You 83 | institute patent litigation against any entity (including a 84 | cross-claim or counterclaim in a lawsuit) alleging that the Work 85 | or a Contribution incorporated within the Work constitutes direct 86 | or contributory patent infringement, then any patent licenses 87 | granted to You under this License for that Work shall terminate 88 | as of the date such litigation is filed. 89 | 90 | 4. Redistribution. You may reproduce and distribute copies of the 91 | Work or Derivative Works thereof in any medium, with or without 92 | modifications, and in Source or Object form, provided that You 93 | meet the following conditions: 94 | 95 | (a) You must give any other recipients of the Work or 96 | Derivative Works a copy of this License; and 97 | 98 | (b) You must cause any modified files to carry prominent notices 99 | stating that You changed the files; and 100 | 101 | (c) You must retain, in the Source form of any Derivative Works 102 | that You distribute, all copyright, patent, trademark, and 103 | attribution notices from the Source form of the Work, 104 | excluding those notices that do not pertain to any part of 105 | the Derivative Works; and 106 | 107 | (d) If the Work includes a "NOTICE" text file as part of its 108 | distribution, then any Derivative Works that You distribute must 109 | include a readable copy of the attribution notices contained 110 | within such NOTICE file, excluding those notices that do not 111 | pertain to any part of the Derivative Works, in at least one 112 | of the following places: within a NOTICE text file distributed 113 | as part of the Derivative Works; within the Source form or 114 | documentation, if provided along with the Derivative Works; or, 115 | within a display generated by the Derivative Works, if and 116 | wherever such third-party notices normally appear. The contents 117 | of the NOTICE file are for informational purposes only and 118 | do not modify the License. You may add Your own attribution 119 | notices within Derivative Works that You distribute, alongside 120 | or as an addendum to the NOTICE text from the Work, provided 121 | that such additional attribution notices cannot be construed 122 | as modifying the License. 123 | 124 | You may add Your own copyright statement to Your modifications and 125 | may provide additional or different license terms and conditions 126 | for use, reproduction, or distribution of Your modifications, or 127 | for any such Derivative Works as a whole, provided Your use, 128 | reproduction, and distribution of the Work otherwise complies with 129 | the conditions stated in this License. 130 | 131 | 5. Submission of Contributions. Unless You explicitly state otherwise, 132 | any Contribution intentionally submitted for inclusion in the Work 133 | by You to the Licensor shall be under the terms and conditions of 134 | this License, without any additional terms or conditions. 135 | Notwithstanding the above, nothing herein shall supersede or modify 136 | the terms of any separate license agreement you may have executed 137 | with Licensor regarding such Contributions. 138 | 139 | 6. Trademarks. This License does not grant permission to use the trade 140 | names, trademarks, service marks, or product names of the Licensor, 141 | except as required for reasonable and customary use in describing the 142 | origin of the Work and reproducing the content of the NOTICE file. 143 | 144 | 7. Disclaimer of Warranty. Unless required by applicable law or 145 | agreed to in writing, Licensor provides the Work (and each 146 | Contributor provides its Contributions) on an "AS IS" BASIS, 147 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 148 | implied, including, without limitation, any warranties or conditions 149 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 150 | PARTICULAR PURPOSE. You are solely responsible for determining the 151 | appropriateness of using or redistributing the Work and assume any 152 | risks associated with Your exercise of permissions under this License. 153 | 154 | 8. Limitation of Liability. In no event and under no legal theory, 155 | whether in tort (including negligence), contract, or otherwise, 156 | unless required by applicable law (such as deliberate and grossly 157 | negligent acts) or agreed to in writing, shall any Contributor be 158 | liable to You for damages, including any direct, indirect, special, 159 | incidental, or consequential damages of any character arising as a 160 | result of this License or out of the use or inability to use the 161 | Work (including but not limited to damages for loss of goodwill, 162 | work stoppage, computer failure or malfunction, or any and all 163 | other commercial damages or losses), even if such Contributor 164 | has been advised of the possibility of such damages. 165 | 166 | 9. Accepting Warranty or Additional Liability. While redistributing 167 | the Work or Derivative Works thereof, You may choose to offer, 168 | and charge a fee for, acceptance of support, warranty, indemnity, 169 | or other liability obligations and/or rights consistent with this 170 | License. However, in accepting such obligations, You may act only 171 | on Your own behalf and on Your sole responsibility, not on behalf 172 | of any other Contributor, and only if You agree to indemnify, 173 | defend, and hold each Contributor harmless for any liability 174 | incurred by, or claims asserted against, such Contributor by reason 175 | of your accepting any such warranty or additional liability. 176 | 177 | END OF TERMS AND CONDITIONS -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |

*** DEPRECATED ***

2 |

🚀 Language Translator Sample Application

3 |

*** DEPRECATED ***

4 |

There is a new demo available for 5 | Language Translator service 6 |

7 |

This Node.js app demonstrates some of the Language Translator service features. 8 |

9 |

10 | 11 | Travis 12 | 13 | 14 | semantic-release 15 | 16 |

17 |

18 | 19 | The IBM Watson™ [Language Translator][service_url] service provides an Application Programming Interface (API) that lets you identify the language of text, and then use a custom business domain to translate the text from one supported language to another. 20 | You can translate either by letting the service identify the source language or by selecting a source language and then by selecting a target language, and a business domain. In addition to text translation, you can use the API to translate full documents and preserve the file formatting! 21 | 22 | 23 | Give it a try! Click the button below to fork into IBM DevOps Services and deploy your own copy of this application on IBM Cloud. 24 | 25 | 26 | ## Prerequisites 27 | 28 | [![Greenkeeper badge](https://badges.greenkeeper.io/watson-developer-cloud/language-translator-nodejs.svg)](https://greenkeeper.io/) 29 | 30 | 1. Sign up for an [IBM Cloud account](https://cloud.ibm.com/registration/). 31 | 1. Download the [IBM Cloud CLI](https://cloud.ibm.com/docs/cli/index.html#overview). 32 | 1. Create an instance of the Language Translator service and get your credentials: 33 | - Go to the [Language Translator](https://cloud.ibm.com/catalog/services/language-translator) page in the IBM Cloud Catalog. 34 | - Log in to your IBM Cloud account. 35 | - Click **Create**. 36 | - Click **Show** to view the service credentials. 37 | - Copy the `apikey` value. 38 | - Copy the `url` value. 39 | 40 | ## Configuring the application 41 | 42 | 1. In the application folder, copy the *.env.example* file and create a file called *.env* 43 | 44 | ``` 45 | cp .env.example .env 46 | ``` 47 | 48 | 2. Open the *.env* file and add the service credentials that you obtained in the previous step. 49 | 50 | Example *.env* file that configures the `apikey` and `url` for a Language Translator service instance hosted in the US East region: 51 | 52 | ``` 53 | LANGUAGE_TRANSLATOR_IAM_APIKEY=X4rbi8vwZmKpXfowaS3GAsA7vdy17Qh7km5D6EzKLHL2 54 | LANGUAGE_TRANSLATOR_URL=https://gateway-wdc.watsonplatform.net/language-translator/api 55 | ``` 56 | 57 | ## Running locally 58 | 59 | 1. Install the dependencies 60 | 61 | ``` 62 | npm install 63 | ``` 64 | 65 | 1. Run the application 66 | 67 | ``` 68 | npm start 69 | ``` 70 | 71 | 1. View the application in a browser at `localhost:3000` 72 | 73 | ## Deploying to IBM Cloud as a Cloud Foundry Application 74 | 75 | 1. Login to IBM Cloud with the [IBM Cloud CLI](https://cloud.ibm.com/docs/cli/index.html#overview) 76 | 77 | ``` 78 | ibmcloud login 79 | ``` 80 | 81 | 1. Target a Cloud Foundry organization and space. 82 | 83 | ``` 84 | ibmcloud target --cf 85 | ``` 86 | 87 | 1. Edit the *manifest.yml* file. Change the **name** field to something unique. 88 | For example, `- name: my-app-name`. 89 | 1. Deploy the application 90 | 91 | ``` 92 | ibmcloud app push 93 | ``` 94 | 95 | 1. View the application online at the app URL. 96 | For example: https://my-app-name.mybluemix.net 97 | 98 | 99 | ## License 100 | 101 | This sample code is licensed under Apache 2.0. 102 | Full license text is available in [LICENSE](LICENSE). 103 | 104 | ## Contributing 105 | 106 | See [CONTRIBUTING](CONTRIBUTING.md). 107 | 108 | ## Open Source @ IBM 109 | 110 | Find more open source projects on the 111 | [IBM Github Page](http://ibm.github.io/). 112 | 113 | [service_url]: https://www.ibm.com/watson/services/language-translator/ 114 | [docs]: https://cloud.ibm.com/docs/language-translator?topic=language-translator-about#about 115 | -------------------------------------------------------------------------------- /app.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2015 IBM Corp. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | 'use strict'; 18 | 19 | const express = require('express'); 20 | const app = express(); 21 | const LanguageTranslatorV3 = require('ibm-watson/language-translator/v3'); 22 | const { IamAuthenticator } = require('ibm-watson/auth'); 23 | 24 | // Bootstrap application settings 25 | require('./config/express')(app); 26 | 27 | // Create the service wrapper 28 | const translator = new LanguageTranslatorV3({ 29 | version: '2019-10-10', 30 | authenticator: new IamAuthenticator({ 31 | apikey: process.env.LANGUAGE_TRANSLATOR_IAM_APIKEY, 32 | }), 33 | url: process.env.LANGUAGE_TRANSLATOR_URL, 34 | headers: { 35 | 'X-Watson-Technology-Preview': '2018-05-01', 36 | 'X-Watson-Learning-Opt-Out': true, 37 | }, 38 | }); 39 | 40 | // render index page 41 | app.get('/', function(req, res) { 42 | // If hide_header is found in the query string and is set to 1 or true, 43 | // the header should be hidden. Default is to show header 44 | res.render('index', { 45 | hideHeader: !!(req.query.hide_header == 'true' || req.query.hide_header == '1'), 46 | }); 47 | }); 48 | 49 | app.get('/api/models', function(req, res, next) { 50 | console.log('/v3/models'); 51 | translator 52 | .listModels() 53 | .then(({ result }) => res.json(result)) 54 | .catch(error => next(error)); 55 | }); 56 | 57 | app.post('/api/identify', function(req, res, next) { 58 | console.log('/v3/identify'); 59 | translator 60 | .identify(req.body) 61 | .then(({ result }) => res.json(result)) 62 | .catch(error => next(error)); 63 | }); 64 | 65 | app.get('/api/identifiable_languages', function(req, res, next) { 66 | console.log('/v3/identifiable_languages'); 67 | translator 68 | .listIdentifiableLanguages(req.body) 69 | .then(({ result }) => res.json(result)) 70 | .catch(error => next(error)); 71 | }); 72 | 73 | app.post('/api/translate', function(req, res, next) { 74 | console.log('/v3/translate'); 75 | translator 76 | .translate(req.body) 77 | .then(({ result }) => res.json(result)) 78 | .catch(error => next(error)); 79 | }); 80 | 81 | // express error handler 82 | require('./config/error-handler')(app); 83 | module.exports = app; 84 | -------------------------------------------------------------------------------- /config/error-handler.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2014 IBM Corp. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | 'use strict'; 18 | 19 | module.exports = function(app) { 20 | // catch 404 and forward to error handler 21 | app.use(function(req, res, next) { 22 | var err = new Error('Not Found'); 23 | err.code = 404; 24 | err.message = 'Not Found'; 25 | next(err); 26 | }); 27 | 28 | // error handler 29 | // eslint-disable-next-line 30 | app.use(function(err, req, res, next) { 31 | var error = { 32 | code: err.code || 500, 33 | error: err.message || err.error, 34 | }; 35 | console.log('error:', error); 36 | res.status(error.code).json(error); 37 | }); 38 | }; 39 | -------------------------------------------------------------------------------- /config/express.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2014 IBM Corp. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | 'use strict'; 18 | 19 | // Module dependencies 20 | const express = require('express'); 21 | const morgan = require('morgan'); 22 | const bodyParser = require('body-parser'); 23 | 24 | module.exports = function(app) { 25 | // Configure Express 26 | app.set('view engine', 'ejs'); 27 | app.set('views', __dirname + '/../views'); 28 | 29 | // Only loaded when running in the IBM Cloud 30 | if (process.env.VCAP_APPLICATION) { 31 | require('./security')(app); 32 | } 33 | 34 | // Configure Express 35 | app.use(bodyParser.urlencoded({ extended: true })); 36 | app.use(bodyParser.json()); 37 | app.use(morgan('dev')); 38 | 39 | // Setup static public directory 40 | app.use(express.static(__dirname + '/../public')); 41 | }; 42 | -------------------------------------------------------------------------------- /config/security.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Copyright 2015 IBM Corp. All Rights Reserved. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | 'use strict'; 18 | 19 | // security.js 20 | const secure = require('express-secure-only'); 21 | const rateLimit = require('express-rate-limit'); 22 | const helmet = require('helmet'); 23 | 24 | module.exports = function(app) { 25 | // 1. redirects http to https 26 | app.enable('trust proxy'); // required when running on bluemix or similar to know if users originally came in on HTTPS and avoid endless redirects 27 | app.use(secure()); 28 | app.use( 29 | helmet({ 30 | frameguard: false, 31 | }) 32 | ); 33 | 34 | // 3. rate limiting 35 | const translateLimiter = rateLimit({ 36 | windowMs: 60 * 1000, 37 | max: 10, 38 | }); 39 | app.use('/api/translate', translateLimiter); 40 | 41 | const identifyLimiter = rateLimit({ 42 | windowMs: 60 * 1000, 43 | max: 10, 44 | }); 45 | app.use('/api/identify', identifyLimiter); 46 | }; 47 | -------------------------------------------------------------------------------- /manifest.yml: -------------------------------------------------------------------------------- 1 | applications: 2 | name: language-translator-demo 3 | command: npm start 4 | path: . 5 | memory: 256M 6 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "language-translator-demo", 3 | "version": "0.3.10", 4 | "description": "A sample nodejs app for the IBM Cloud that use the Language Translator service", 5 | "dependencies": { 6 | "body-parser": "^1.19.0", 7 | "dotenv": "^8.2.0", 8 | "ejs": "^2.7.1", 9 | "express": "^4.17.1", 10 | "express-rate-limit": "^5.0.0", 11 | "express-secure-only": "^0.2.1", 12 | "helmet": "^3.21.2", 13 | "ibm-watson": "^5.1.0", 14 | "jade": "~1.11.0", 15 | "morgan": "^1.9.1" 16 | }, 17 | "engines": { 18 | "node": ">=12" 19 | }, 20 | "repository": { 21 | "type": "git", 22 | "url": "git://github.com/watson-developer-cloud/language-translator-nodejs.git" 23 | }, 24 | "author": "IBM Corp.", 25 | "contributors": [ 26 | { 27 | "name": "German Attanasio Ruiz", 28 | "email": "germanatt@us.ibm.com" 29 | } 30 | ], 31 | "license": "Apache-2.0", 32 | "bugs": { 33 | "url": "https://github.com/watson-developer-cloud/language-translator-nodejs/issues" 34 | }, 35 | "scripts": { 36 | "start": "node server.js", 37 | "codecov": "npm run test && (codecov || true)", 38 | "validate": "npm ls", 39 | "lint": "eslint .", 40 | "test-unit": "nyc mocha", 41 | "test": "npm run lint && npm run test-unit" 42 | }, 43 | "devDependencies": { 44 | "codecov": "^3.6.1", 45 | "eslint": "^6.6.0", 46 | "mocha": "^6.2.2", 47 | "nyc": "^14.1.1", 48 | "supertest": "^4.0.2" 49 | }, 50 | "publishConfig": { 51 | "registry": "https://registry.npmjs.org/", 52 | "access": "public" 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /public/css/browser-compatibility.css: -------------------------------------------------------------------------------- 1 | /* css_browser_selector styles */ 2 | .win * { 3 | font-family: Arial, sans-serif; 4 | } 5 | .win .navbar-brand { 6 | font-family: Arial; 7 | font-weight: bold; 8 | } 9 | .win .thin-branding { 10 | font-family: Arial; 11 | } 12 | .win pre, 13 | .win code, 14 | .win kbd, 15 | .win samp, 16 | .win pre *, 17 | .win code *, 18 | .win kbd *, 19 | .win samp * { 20 | font-family: Menlo, "Menlo", Monaco, Consolas, "Courier New", monospace; 21 | } 22 | 23 | .win .fixed-nav { 24 | font-family: Arial; 25 | } -------------------------------------------------------------------------------- /public/demo.js: -------------------------------------------------------------------------------- 1 | /* eslint-disable no-prototype-builtins */ 2 | /** 3 | * Copyright 2015 IBM Corp. All Rights Reserved. 4 | * 5 | * Licensed under the Apache License, Version 2.0 (the "License"); 6 | * you may not use this file except in compliance with the License. 7 | * You may obtain a copy of the License at 8 | * 9 | * http://www.apache.org/licenses/LICENSE-2.0 10 | * 11 | * Unless required by applicable law or agreed to in writing, software 12 | * distributed under the License is distributed on an "AS IS" BASIS, 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | * See the License for the specific language governing permissions and 15 | * limitations under the License. 16 | */ 17 | /*eslint no-native-reassign: "off"*/ 18 | 'use strict'; 19 | 20 | $(document).ready(function () { 21 | var modelList = []; 22 | var pageDomain = ''; 23 | var sourceList = []; 24 | var sourceLangSelect = 'Choose Language'; 25 | var langAbbrevList = []; 26 | var nmtValue = '2018-05-01'; 27 | 28 | // Update input-output dropdown based on selected domain 29 | $('input:radio[name=group1]').click(function () { 30 | sourceList = []; 31 | pageDomain = $(this).val(); 32 | 33 | // Reset all the values when domain is changed 34 | $('#resetSpan').trigger('click'); 35 | 36 | // Autodetect language option 37 | $('#ulSourceLang').append('
  • Detect Language
  • '); 38 | // Update language array based on domain 39 | 40 | for (var y in modelList) { 41 | var sourceVal = ''; 42 | var targetVal = ''; 43 | // if model has the domain property then add the language in dropdown list. Otherwise add 'news' domain to JSON model list 44 | if (!(modelList[y].hasOwnProperty('domain'))) { 45 | modelList[y].domain = 'general'; 46 | //console.log('no domain'); 47 | } 48 | var modelListDomain = modelList[y].domain.toString(); 49 | //console.log(modelListDomain.toLowerCase() + ' DOMAIN ' + pageDomain.toString().toLowerCase() ); 50 | if (modelListDomain.toLowerCase() === pageDomain.toString().toLowerCase()) { 51 | sourceVal = getLanguageName(modelList[y].source); 52 | targetVal = getLanguageName(modelList[y].target); 53 | sourceList.push({ 54 | source: sourceVal, 55 | target: targetVal 56 | }); 57 | //console.log("source" + sourceVal + "target" + targetVal); 58 | } 59 | } 60 | 61 | // Sort by source then target ,so source languages are sorted in dropdown 62 | sourceList.sort(function(a,b) { 63 | return (a.source > b.source) ? 1 : ((b.source > a.source) ? -1 : 64 | ( a.target < b.target ? -1 : a.target > b.target ? 1 : 0)); 65 | }); 66 | 67 | // Update Input Dropdown Menu with Source Language 68 | $('#ulSourceLang').html(''); 69 | $('#ulSourceLang').append('
  • Detect Language
  • '); 70 | $('#ulTargetLang').html(''); 71 | fillInDropdown('ulSourceLang'); 72 | }); 73 | 74 | // Get list of Models after getting languages 75 | $.ajax({ 76 | type: 'GET', 77 | url: '/api/models', 78 | headers: { 79 | 'X-Watson-Technology-Preview': nmtValue 80 | }, 81 | async: true 82 | }) 83 | .done(function (data) { 84 | //console.log(data + " response received"); 85 | modelList = data.models; 86 | 87 | // Get list of languages 88 | $.ajax({ 89 | type: 'GET', 90 | url: '/api/identifiable_languages', 91 | headers: { 92 | 'X-Watson-Technology-Preview': nmtValue 93 | }, 94 | async: true 95 | }) 96 | .done(function (data) { 97 | //console.log("demo.js identifiable",data); 98 | langAbbrevList = data.languages; 99 | // select news option in domain and update dropdown with language selections 100 | $('input:radio[name=group1]:nth(1)').prop('checked', true).trigger('click'); 101 | }); 102 | }) 103 | .fail(function (jqXHR, statustext, errorthrown) { 104 | console.log(statustext + errorthrown); 105 | }); 106 | 107 | // Update dropdown Menu Input value with source lang selected 108 | $('#ulSourceLang').on('click', 'a', function (e) { 109 | e.preventDefault(); 110 | sourceLangSelect = $.trim($(this).text()); 111 | //console.log('click href ' + sourceLangSelect); 112 | $('#dropdownMenuInput').html('').html(sourceLangSelect + ''); 113 | 114 | // if Choose lang or detect lang is selected again then send request for lang id service 115 | if (sourceLangSelect.toLowerCase().indexOf('language') >= 0) { 116 | if (parseInt($('#home textarea').val().length) > 0) { 117 | doneTyping(); 118 | } 119 | } 120 | updateOutputDropdownMenu(); 121 | getTranslation(); 122 | }); 123 | 124 | // Update dropdown Menu Output value with target lang selected 125 | $('#ulTargetLang').on('click', 'a', function (e) { 126 | e.preventDefault(); 127 | //console.log('click href ' + $(this).text()); 128 | $('#dropdownMenuOutput').html('').html($(this).text() + ''); 129 | getTranslation(); 130 | }); 131 | 132 | // Bidirectional toggle for source and target languages 133 | $('#sourceTargetLangSwitch').on('click', function(e) { 134 | e.preventDefault(); 135 | var sourceLang = $.trim($('#dropdownMenuInput').text()); 136 | var targetLang = $.trim($('#dropdownMenuOutput').text()); 137 | var targetText = $.trim($('#home2 textarea').val()); 138 | // switch source/target languages, use target text for source 139 | $('#dropdownMenuInput').html('').html(targetLang + ''); 140 | updateOutputDropdownMenu(); 141 | $('#dropdownMenuOutput').html('').html(sourceLang + ''); 142 | 143 | $('#home textarea').val(targetText); 144 | // trigger re-translation/recount 145 | doneTyping(); 146 | countCharacters(); 147 | }); 148 | 149 | // Lang Service - Start - This set send request for lang service to detect language 150 | // setup timer value for function 151 | var typingTimer; //timer identifier 152 | var doneTypingInterval = 1000; //time in ms, 1 second 153 | 154 | // on keyup, start the countdown 155 | $('#home textarea').keyup(function () { 156 | // if textarea is empty the reset value of textarea 157 | if (parseInt($('#home textarea').val().length) <= 0) { 158 | $('#home2 textarea').val(''); 159 | $('#profile textarea').val(''); 160 | $('#profile2 textarea').val(''); 161 | 162 | if ((sourceLangSelect.toLowerCase() === 'detect language') || (sourceLangSelect.toLowerCase() === 'choose language')) { 163 | $('#dropdownMenuInput').html('Choose Language '); 164 | $('#dropdownMenuOutput').html('Choose Language '); 165 | } 166 | } 167 | clearTimeout(typingTimer); 168 | typingTimer = setTimeout(doneTyping, doneTypingInterval); 169 | 170 | }); 171 | 172 | // on keydown, clear the countdown 173 | $('#home textarea').keydown(function () { 174 | clearTimeout(typingTimer); 175 | }); 176 | // Lang Service - End here 177 | 178 | // Set maximum form input length 179 | var maxInputLength = 10000; 180 | $(document).ready(function() { 181 | $('#home textarea').attr('maxlength', maxInputLength); 182 | $('#home .input-counter').html('0/' + maxInputLength); 183 | }); 184 | 185 | // Update input character counter 186 | $('#home textarea').on('input', function(){ 187 | countCharacters(); 188 | }); 189 | 190 | // Reset all the values on page 191 | $('#resetSpan').click(function (e) { 192 | e.preventDefault(); 193 | $('#dropdownMenuInput').html('Choose Language '); 194 | $('#dropdownMenuOutput').html('Choose Language '); 195 | $('#home textarea').val(''); 196 | $('#home2 textarea').val(''); 197 | $('#profile textarea').val(''); 198 | $('#profile2 textarea').val(''); 199 | sourceLangSelect = 'Choose Language'; 200 | countCharacters(); 201 | }); 202 | 203 | /* -------------------------------- Functions start from here ---------------------------------------- */ 204 | 205 | function countCharacters() { 206 | var currentLength = $('#home textarea').val().length; 207 | $('#home .input-counter').html(currentLength + '/' + maxInputLength); 208 | // enable/disable notification to funnel users to paid acct 209 | if (currentLength >= maxInputLength) { 210 | $('#home #character-limit-warning').css('display', 'flex'); 211 | } else { 212 | $('#home #character-limit-warning').css('display', 'none'); 213 | } 214 | } 215 | 216 | // user is "finished typing," send for service request 217 | function doneTyping() { 218 | //console.log('done typing - ' + $('#home textarea').val() + ' SourceLangSelect ' + sourceLangSelect.toLowerCase()); 219 | // if option selected for dropdown is detect or choose language then send request for service to get lang-id 220 | if (((sourceLangSelect.toLowerCase() === 'detect language') || (sourceLangSelect.toLowerCase() === 'choose language')) && (parseInt($('#home textarea').val().length) > 0)) { 221 | // Create call for AJAX and to get Lang-Id for text 222 | var restAPICall = { 223 | type: 'POST', 224 | url: '/api/identify', 225 | headers: { 226 | 'X-Watson-Technology-Preview': nmtValue 227 | }, 228 | data: { 229 | text: $('#home textarea').val() 230 | }, 231 | async: true 232 | }; 233 | 234 | var oldSrcLang = $('#dropdownMenuInput').html(); 235 | $('#dropdownMenuInput').html('detecting language...'); 236 | $.ajax(restAPICall) 237 | .done(function (data) { 238 | //console.log(data + " data " + langAbbrevList[data]); 239 | var langIdentified = false; 240 | //console.log("detected language code is " + data); 241 | data = data.languages[0].language; 242 | var dataLangName = getLanguageName(data); 243 | //console.log("detected language as " + dataLangName); 244 | $.each(sourceList, function (index, value) { 245 | //console.log(value.source + ' source value ' + getLanguageName(data)); 246 | if (value.source == dataLangName) { 247 | langIdentified = true; 248 | } 249 | }); 250 | 251 | if (langIdentified) { 252 | //console.log('lang identified'); 253 | // If souce lang is same as identified land then add in dropdown Input menu 254 | $('#dropdownMenuInput').html('').html(dataLangName + ' '); 255 | } else { 256 | //console.log('lang not identified'); 257 | $('#dropdownMenuInput').html('').html(dataLangName + ': not supported for this domain '); 258 | } 259 | // update outputDropDown only when the detected source changed 260 | if (oldSrcLang != $('#dropdownMenuInput').html()) 261 | updateOutputDropdownMenu(); 262 | getTranslation(); 263 | }) 264 | .always(function () { 265 | getTranslation(); 266 | }) 267 | .fail(function (jqXHR, statustext, errorthrown) { 268 | $('#dropdownMenuInput').html(oldSrcLang); 269 | console.log(statustext + errorthrown); 270 | }); 271 | } else { 272 | //console.log('gettranslation not in if'); 273 | getTranslation(); 274 | } 275 | } 276 | 277 | // get Language Name from abbreviation 278 | function getLanguageName(langAbbrev) { 279 | // the /models endpoint doesn't include names, and the /identifiable_languages endpoint doesn't include Indonesian 280 | // so it's hard-coded for now 281 | if (langAbbrev === 'id') { 282 | return 'Indonesian'; 283 | } 284 | if (langAbbrev === 'zht') { 285 | return 'Traditional Chinese'; 286 | } 287 | var test = langAbbrevList; 288 | for (var i = 0; i < test.length; i++) { 289 | //console.log ('length ' + langAbbrev.length); 290 | var langString = (langAbbrev.length == 2) ? test[i].language.substring(0, 2) : test[i].language; 291 | //console.log(langString + ' ggg ' + langAbbrev); 292 | if (langString == langAbbrev) { 293 | //console.log(' return ' + test[i].name); 294 | return test[i].name; 295 | } 296 | } 297 | return langAbbrev; 298 | } 299 | 300 | // get abbreviation of language from Name 301 | function getLanguageCode(langName) { 302 | // the /models endpoint doesn't include names, and the /identifiable_languages endpoint doesn't include Indonesian 303 | // so it's hard-coded for now 304 | if (langName === 'Indonesian') { 305 | return 'id'; 306 | } 307 | var test = langAbbrevList; 308 | for (var i = 0; i < test.length; i++) { 309 | //console.log(test[i].name + ' dd '+ langName); 310 | if (test[i].name == langName) { 311 | return test[i].language; 312 | } 313 | } 314 | return langName; 315 | } 316 | 317 | // Fill in dropdown menu 318 | function fillInDropdown(ulName) { 319 | $.each(sourceList, function (index, value) { 320 | var exists = false; 321 | // Look for source value in drop down list 322 | $('#' + ulName).find('a').each(function() { 323 | if ($(this).text() == value.source) { 324 | exists = true; 325 | return false; // exit the loop when match is found 326 | } 327 | }); 328 | // Create new list item if source value was not in select list 329 | if (!exists) { 330 | $('#' + ulName).append('
  • ' + value.source + '
  • '); 331 | } 332 | else { 333 | console.log(value.source,'source lang already exist in li list'); 334 | } 335 | }); 336 | } 337 | 338 | function updateOutputDropdownMenu() { 339 | var exists; 340 | $('#ulTargetLang').html(''); 341 | $('#dropdownMenuOutput').html('').html('Choose Language '); 342 | 343 | // Update output dropdown menu with target language 344 | $.each(sourceList, function (index, value) { 345 | if (value.source == $.trim($('#dropdownMenuInput').text())) { 346 | exists = false; 347 | // Look for target value in drop down list 348 | $('#ulTargetLang').find('a').each(function() { 349 | if ($(this).text() == value.target) { 350 | exists = true; 351 | return false; // exit the loop when match is found 352 | } 353 | }); 354 | // Create new list item if source value was not in select list 355 | if (!exists) { 356 | $('#ulTargetLang').append('
  • ' + value.target + '
  • '); 357 | } 358 | else { 359 | console.log(value.target,'target lang already exist in li list'); 360 | } 361 | } 362 | }); 363 | 364 | if ($('#ulTargetLang li').length == 1) { 365 | $('#dropdownMenuOutput').html('').html($($('#ulTargetLang a')).text() + ''); 366 | } 367 | } 368 | 369 | // Send request to translate service if input-output and textarea have values 370 | function getTranslation() { 371 | var pageDomain = ''; 372 | var source = ''; 373 | var target = ''; 374 | var textContent = ''; 375 | 376 | if ($('input:radio[name=\'group1\']').is(':checked')) { 377 | pageDomain = $('input:radio[name=group1]:checked').val(); 378 | } 379 | 380 | if (($('#dropdownMenuInput').text()).toLowerCase().indexOf('choose language') < 0) { 381 | source = getLanguageCode($.trim($('#dropdownMenuInput').text())); 382 | } 383 | 384 | if (($('#dropdownMenuOutput').text()).toLowerCase().indexOf('choose language') < 0) { 385 | target = getLanguageCode($.trim($('#dropdownMenuOutput').text())); 386 | } 387 | 388 | if ((parseInt($('#home textarea').val().length) > 0)) { 389 | textContent = $('#home textarea').val(); 390 | } 391 | 392 | // get model_id from domain, source and target 393 | var model_id = getModelId(pageDomain, source, target); 394 | 395 | if (pageDomain && source && target && textContent && model_id) { 396 | //console.log('source-' + source + ' target-' + target + ' textContent-' + textContent); 397 | 398 | // Create call for AJAX and to populate REST API tab 399 | var callData = { 400 | modelId: model_id, 401 | text: textContent 402 | }; 403 | 404 | var restAPICall = { 405 | type: 'POST', 406 | url: '/api/translate', 407 | data: callData, 408 | dataType: 'json', 409 | headers: { 410 | 'X-WDC-PL-OPT-OUT': $('input:radio[name=serRadio]:radio:checked').val(), 411 | 'X-Watson-Technology-Preview': nmtValue 412 | }, 413 | async: true 414 | }; 415 | 416 | $('#profile textarea').val(JSON.stringify(callData, null, 2)); 417 | $('#home2 textarea').val('translating...'); 418 | 419 | $.ajax(restAPICall) 420 | .done(function (data) { 421 | $('#home2 textarea').val(data['translations'][0]['translation']); 422 | $('#profile2 textarea').val(JSON.stringify(data, null, 2)); 423 | }) 424 | .fail(function (jqXHR, statustext, errorthrown) { 425 | $('#home2 textarea').val('translation error'); 426 | console.log(statustext + errorthrown); 427 | }); 428 | } else { 429 | console.log('not all values' + 'source- ' + source + ' target- ' + target + ' textContent- ' + textContent + ' model_id - ' + model_id); 430 | } 431 | } // get Translation end here 432 | 433 | // accepts a lang or locale (e.g. en-US) and returns the lang (e.g. en) 434 | function getLang(locale){ 435 | // split/shift rather than substr to handle cases like arz where the language part is actually 3 letters 436 | return locale.split('-').shift().toLowerCase(); 437 | } 438 | 439 | // Get model_id from domain, source , target 440 | function getModelId(pageDomain, source, target) { 441 | var modelId = ''; 442 | 443 | // Preferred: search for an exact lang/locale match (e.g. en-US to es-LA) 444 | for (var y in modelList) { 445 | if (modelList[y].hasOwnProperty('domain')) { 446 | var modelListDomain = modelList[y].domain.toString(); 447 | if ((modelListDomain.toLowerCase() === pageDomain.toString().toLowerCase()) && source === modelList[y].source && target === modelList[y].target) { 448 | modelId = modelList[y].model_id; 449 | return modelId; 450 | } 451 | } 452 | } 453 | 454 | // Fallback: search for a language-only match (e.g. en to es) 455 | source = getLang(source); 456 | target = getLang(target); 457 | for (var y2 in modelList) { 458 | if (modelList[y2].hasOwnProperty('domain')) { 459 | var modelListDomain2 = modelList[y2].domain.toString(); 460 | if ((modelListDomain2.toLowerCase() === pageDomain.toString().toLowerCase()) && source === getLang(modelList[y2].source) && target === getLang(modelList[y2].target)) { 461 | modelId = modelList[y2].model_id; 462 | return modelId; 463 | } 464 | } 465 | } 466 | 467 | return modelId; 468 | } 469 | 470 | $('#nav-tabs a').click(function (e) { 471 | e.preventDefault(); 472 | $(this).tab('show'); 473 | }); 474 | 475 | }); 476 | -------------------------------------------------------------------------------- /public/fonts/glyphicons-halflings-regular.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/glyphicons-halflings-regular.eot -------------------------------------------------------------------------------- /public/fonts/glyphicons-halflings-regular.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | 123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | 134 | 135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 150 | 151 | 152 | 153 | 154 | 155 | 156 | 157 | 158 | 159 | 160 | 161 | 162 | 163 | 164 | 165 | 166 | 167 | 168 | 169 | 170 | 171 | 172 | 173 | 174 | 175 | 176 | 177 | 178 | 179 | 180 | 181 | 182 | 183 | 184 | 185 | 186 | 187 | 188 | 189 | 190 | 191 | 192 | 193 | 194 | 195 | 196 | 197 | 198 | 199 | 200 | 201 | 202 | 203 | 204 | 205 | 206 | 207 | 208 | 209 | 210 | 211 | 212 | 213 | 214 | 215 | 216 | 217 | 218 | 219 | 220 | 221 | 222 | 223 | 224 | 225 | 226 | 227 | 228 | 229 | -------------------------------------------------------------------------------- /public/fonts/glyphicons-halflings-regular.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/glyphicons-halflings-regular.ttf -------------------------------------------------------------------------------- /public/fonts/glyphicons-halflings-regular.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/glyphicons-halflings-regular.woff -------------------------------------------------------------------------------- /public/fonts/helvneueboldforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueboldforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneueboldforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueboldforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneueboldforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueboldforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneuebolditalicforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuebolditalicforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneuebolditalicforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuebolditalicforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneuebolditalicforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuebolditalicforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneuecondforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuecondforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneuecondforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuecondforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneuecondforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuecondforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneuelightcondforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightcondforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneuelightcondforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightcondforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneuelightcondforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightcondforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneuelightforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneuelightforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneuelightforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneuelightitalicforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightitalicforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneuelightitalicforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightitalicforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneuelightitalicforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuelightitalicforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneuemediumforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuemediumforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneuemediumforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuemediumforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneuemediumforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuemediumforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneuemediumitalicforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuemediumitalicforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneuemediumitalicforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuemediumitalicforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneuemediumitalicforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneuemediumitalicforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneueromanforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueromanforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneueromanforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueromanforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneueromanforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueromanforibm.woff -------------------------------------------------------------------------------- /public/fonts/helvneueromanitalicforibm.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueromanitalicforibm.eot -------------------------------------------------------------------------------- /public/fonts/helvneueromanitalicforibm.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueromanitalicforibm.ttf -------------------------------------------------------------------------------- /public/fonts/helvneueromanitalicforibm.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/helvneueromanitalicforibm.woff -------------------------------------------------------------------------------- /public/fonts/menlo.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/menlo.eot -------------------------------------------------------------------------------- /public/fonts/menlo.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/menlo.ttf -------------------------------------------------------------------------------- /public/fonts/menlo.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/fonts/menlo.woff -------------------------------------------------------------------------------- /public/images/drop-down-arrow-white.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /public/images/drop-down-arrow.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /public/images/drop-up-arrow.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /public/images/favicon/android-icon-144x144.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/android-icon-144x144.png -------------------------------------------------------------------------------- /public/images/favicon/android-icon-192x192.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/android-icon-192x192.png -------------------------------------------------------------------------------- /public/images/favicon/android-icon-36x36.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/android-icon-36x36.png -------------------------------------------------------------------------------- /public/images/favicon/android-icon-48x48.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/android-icon-48x48.png -------------------------------------------------------------------------------- /public/images/favicon/android-icon-72x72.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/android-icon-72x72.png -------------------------------------------------------------------------------- /public/images/favicon/android-icon-96x96.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/android-icon-96x96.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-114x114.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-114x114.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-120x120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-120x120.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-144x144.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-144x144.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-152x152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-152x152.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-180x180.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-180x180.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-57x57.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-57x57.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-60x60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-60x60.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-72x72.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-72x72.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-76x76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-76x76.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon-precomposed.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon-precomposed.png -------------------------------------------------------------------------------- /public/images/favicon/apple-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/apple-icon.png -------------------------------------------------------------------------------- /public/images/favicon/favicon-16x16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/favicon-16x16.png -------------------------------------------------------------------------------- /public/images/favicon/favicon-32x32.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/favicon-32x32.png -------------------------------------------------------------------------------- /public/images/favicon/favicon-96x96.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/favicon-96x96.png -------------------------------------------------------------------------------- /public/images/favicon/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/favicon.ico -------------------------------------------------------------------------------- /public/images/favicon/ms-icon-144x144.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/ms-icon-144x144.png -------------------------------------------------------------------------------- /public/images/favicon/ms-icon-150x150.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/ms-icon-150x150.png -------------------------------------------------------------------------------- /public/images/favicon/ms-icon-310x310.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/ms-icon-310x310.png -------------------------------------------------------------------------------- /public/images/favicon/ms-icon-70x70.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/watson-developer-cloud/language-translator-nodejs/6aa91b46f0126f43b896e083b8c1ecaeaf950b5b/public/images/favicon/ms-icon-70x70.png -------------------------------------------------------------------------------- /public/images/information-teal.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 9 | 10 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /public/images/information.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 9 | 10 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /public/images/language-translator.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | 9 | 10 | 26 | 27 | -------------------------------------------------------------------------------- /public/images/link.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 14 | 15 | -------------------------------------------------------------------------------- /public/images/reset.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 8 | 9 | -------------------------------------------------------------------------------- /public/js/css_browser_selector.js: -------------------------------------------------------------------------------- 1 | /* 2 | CSS Browser Selector v0.4.0 (Nov 02, 2010) 3 | Rafael Lima (http://rafael.adm.br) 4 | http://rafael.adm.br/css_browser_selector 5 | License: http://creativecommons.org/licenses/by/2.5/ 6 | Contributors: http://rafael.adm.br/css_browser_selector#contributors 7 | */ 8 | function css_browser_selector(u){var ua=u.toLowerCase(),is=function(t){return ua.indexOf(t)>-1;},g='gecko',w='webkit',s='safari',o='opera',m='mobile',h=document.documentElement,b=[(!(/opera|webtv/i.test(ua))&&/msie\s(\d)/.test(ua))?('ie ie'+RegExp.$1):is('firefox/2')?g+' ff2':is('firefox/3.5')?g+' ff3 ff3_5':is('firefox/3.6')?g+' ff3 ff3_6':is('firefox/3')?g+' ff3':is('gecko/')?g:is('opera')?o+(/version\/(\d+)/.test(ua)?' '+o+RegExp.$1:(/opera(\s|\/)(\d+)/.test(ua)?' '+o+RegExp.$2:'')):is('konqueror')?'konqueror':is('blackberry')?m+' blackberry':is('android')?m+' android':is('chrome')?w+' chrome':is('iron')?w+' iron':is('applewebkit/')?w+' '+s+(/version\/(\d+)/.test(ua)?' '+s+RegExp.$1:''):is('mozilla/')?g:'',is('j2me')?m+' j2me':is('iphone')?m+' iphone':is('ipod')?m+' ipod':is('ipad')?m+' ipad':is('mac')?'mac':is('darwin')?'mac':is('webtv')?'webtv':is('win')?'win'+(is('windows nt 6.0')?' vista':''):is('freebsd')?'freebsd':(is('x11')||is('linux'))?'linux':'','js']; c = b.join(' '); h.className += ' '+c; return c;} css_browser_selector(navigator.userAgent); 9 | -------------------------------------------------------------------------------- /public/js/tab.js: -------------------------------------------------------------------------------- 1 | /* ======================================================================== 2 | * Bootstrap: tab.js v3.1.1 3 | * http://getbootstrap.com/javascript/#tabs 4 | * ======================================================================== 5 | * Copyright 2011-2014 Twitter, Inc. 6 | * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE) 7 | * ======================================================================== */ 8 | 9 | 10 | +function ($) { 11 | 'use strict'; 12 | 13 | // TAB CLASS DEFINITION 14 | // ==================== 15 | 16 | var Tab = function (element) { 17 | this.element = $(element); 18 | }; 19 | 20 | Tab.prototype.show = function () { 21 | var $this = this.element; 22 | var $ul = $this.closest('ul:not(.dropdown-menu)'); 23 | var selector = $this.data('target'); 24 | 25 | if (!selector) { 26 | selector = $this.attr('href'); 27 | selector = selector && selector.replace(/.*(?=#[^\s]*$)/, ''); //strip for ie7 28 | } 29 | 30 | if ($this.parent('li').hasClass('active')) return; 31 | 32 | var previous = $ul.find('.active:last a')[0]; 33 | var e = $.Event('show.bs.tab', { 34 | relatedTarget: previous 35 | }); 36 | 37 | $this.trigger(e); 38 | 39 | if (e.isDefaultPrevented()) return; 40 | 41 | var $target = $(selector); 42 | 43 | this.activate($this.parent('li'), $ul); 44 | this.activate($target, $target.parent(), function () { 45 | $this.trigger({ 46 | type: 'shown.bs.tab', 47 | relatedTarget: previous 48 | }); 49 | }); 50 | }; 51 | 52 | Tab.prototype.activate = function (element, container, callback) { 53 | var $active = container.find('> .active'); 54 | var transition = callback 55 | && $.support.transition 56 | && $active.hasClass('fade'); 57 | 58 | function next() { 59 | $active 60 | .removeClass('active') 61 | .find('> .dropdown-menu > .active') 62 | .removeClass('active'); 63 | 64 | element.addClass('active'); 65 | 66 | if (transition) { 67 | element[0].offsetWidth; // reflow for transition 68 | element.addClass('in'); 69 | } else { 70 | element.removeClass('fade'); 71 | } 72 | 73 | if (element.parent('.dropdown-menu')) { 74 | element.closest('li.dropdown').addClass('active'); 75 | } 76 | 77 | callback && callback(); 78 | } 79 | 80 | transition ? 81 | $active 82 | .one($.support.transition.end, next) 83 | .emulateTransitionEnd(150) : 84 | next(); 85 | 86 | $active.removeClass('in'); 87 | }; 88 | 89 | 90 | // TAB PLUGIN DEFINITION 91 | // ===================== 92 | 93 | var old = $.fn.tab; 94 | 95 | $.fn.tab = function ( option ) { 96 | return this.each(function () { 97 | var $this = $(this); 98 | var data = $this.data('bs.tab'); 99 | 100 | if (!data) $this.data('bs.tab', (data = new Tab(this))); 101 | if (typeof option == 'string') data[option](); 102 | }); 103 | }; 104 | 105 | $.fn.tab.Constructor = Tab; 106 | 107 | 108 | // TAB NO CONFLICT 109 | // =============== 110 | 111 | $.fn.tab.noConflict = function () { 112 | $.fn.tab = old; 113 | return this; 114 | }; 115 | 116 | 117 | // TAB DATA-API 118 | // ============ 119 | 120 | $(document).on('click.bs.tab.data-api', '[data-toggle="tab"], [data-toggle="pill"]', function (e) { 121 | e.preventDefault(); 122 | $(this).tab('show'); 123 | }); 124 | 125 | }(jQuery); 126 | -------------------------------------------------------------------------------- /server.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 'use strict'; 3 | 4 | require('dotenv').config({ silent: true }); 5 | 6 | const server = require('./app'); 7 | const port = process.env.PORT || 3000; 8 | 9 | const startServer = server.listen(port, function() { 10 | console.log('Server running on port: %d', port); 11 | }); 12 | 13 | function close() { 14 | startServer.close(); 15 | } 16 | 17 | module.exports = { 18 | close, 19 | }; 20 | -------------------------------------------------------------------------------- /test/test.express.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | require('dotenv').config({ silent: true }); 4 | 5 | if (!process.env.LANGUAGE_TRANSLATOR_IAM_APIKEY) { 6 | console.log('Skipping unit test because LANGUAGE_TRANSLATOR_IAM_APIKEY is null'); 7 | return; 8 | } 9 | 10 | const bodyParser = require('body-parser'); 11 | const request = require('supertest'); 12 | const assert = require('assert'); 13 | const app = require('../app'); 14 | 15 | app.use(bodyParser.json()); 16 | 17 | describe('Basic API tests', function() { 18 | it('GET to / should load the home page', function(done) { 19 | request(app) 20 | .get('/') 21 | .expect(200, done); 22 | }); 23 | 24 | it('GET to /api/models should return the models', function(done) { 25 | request(app) 26 | .get('/api/models') 27 | .expect('Content-Type', /json/) 28 | .end(function(err, res) { 29 | if (err) throw err; 30 | 31 | assert(res.body.models); 32 | assert(res.body.models.length > 1); 33 | done(); 34 | }); 35 | }); 36 | 37 | it('POST to /api/translate should translate text', function(done) { 38 | request(app) 39 | .post('/api/translate') 40 | .send({ 41 | modelId: 'en-es', 42 | text: 'Messi is the best soccer player in the world', 43 | }) 44 | .end(function(err, res) { 45 | if (err) throw err; 46 | assert(res.body.translations); 47 | assert.equal(res.body.word_count, 9); 48 | assert.equal(res.body.character_count, 44); 49 | done(); 50 | }); 51 | }); 52 | 53 | it('GET to /api/identifiable_languages should the identifiable languages', function(done) { 54 | request(app) 55 | .get('/api/identifiable_languages') 56 | .expect('Content-Type', /json/) 57 | .end(function(err, res) { 58 | if (err) throw err; 59 | 60 | assert(res.body.languages); 61 | assert(res.body.languages.length > 1); 62 | done(); 63 | }); 64 | }); 65 | 66 | it('POST to /api/identify should identify the given text', function(done) { 67 | request(app) 68 | .post('/api/identify') 69 | .send({ 70 | text: 'Messi es el mejor del mundo', 71 | }) 72 | .end(function(err, res) { 73 | if (err) throw err; 74 | 75 | assert(res.body.languages); 76 | assert(res.body.languages.length > 1); 77 | done(); 78 | }); 79 | }); 80 | 81 | it('GET to /not-a-real-page should return 404', function(done) { 82 | request(app) 83 | .get('/not-a-real-page') 84 | .expect(404, done); 85 | }); 86 | }); 87 | -------------------------------------------------------------------------------- /views/index.ejs: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | Language Translator 22 | 23 | 26 | 27 | 28 | 29 | 30 | 31 | <% if (!hideHeader) { %> 32 | 33 | 47 | 48 | 49 |
    50 |
    51 | 54 |
    55 |

    Language Translator

    56 |

    The IBM Watson Language Translator service allows you to input text or documents in one language and see the output in another. 57 | Translation is available for over 70 languages: Afrikaans, Albanian, Arabic, Armenian, Azerbaijani, Bashkir, Basque, Belarusian, Bengali, Bosnian, Bulgarian, Catalan, Central Khmer, Chinese (Simplified), Chinese (Traditional), Chuvash, Croatian, Czech, Danish, Dutch, English, Esperanto, Estonian, Finnish, French, Georgian, German, Greek, Gujarati, Haitian, Hebrew, Hindi, Hungarian, Icelandic, Indonesian, Irish, Italian, Japanese, Kazakh, Kirghiz, Korean, Kurdish, Latvian, Lithuanian, Malay, Malayalam, Maltese, Mongolian, Norwegian Bokmal, Norwegian Nynorsk, Panjabi, Persian, Polish, Portuguese, Pushto, Romanian, Russian, Serbian, Slovakian, Slovenian, Somali, Spanish, Swedish, Tamil, Telugu Thai, Turkish, Ukrainian, Urdu, and Vietnamese. 58 |

    59 |

    Resources:
    60 |

    69 | 70 |

    71 |
    72 | 73 |
    74 | 75 |
    76 | <% } %> 77 | 78 | 79 |
    80 |
    81 | 84 | 85 | 96 | 97 |
    98 |
    99 |
    Would you like to help make this service better?

    100 |
    101 | Allow Watson 102 | to learn from this session
    Opt out 104 |
    105 |
    This system is for demonstration purposes only and is not intended to process Personal Data. No 106 | Personal Data is to be entered into this system as it may not have the necessary controls in place to meet 107 | the requirements of the General Data Protection Regulation (EU) 2016/679
    108 |
    109 |
    110 |
    111 | By using this application, you agree to the  112 | 114 | Terms of Use 115 | 116 |
    117 |
    118 |
    119 |
    120 |
    121 |
    122 | 123 | 124 |
    125 |
    126 |

    Translate Text

    127 |
    128 | 129 |
    130 |

    Input

    131 |

    Enter or paste text from a passage.

    132 |
    133 |
    134 | 143 |
    144 |
    145 | 146 | 147 |
    148 |
    149 |
    150 | 151 | 158 |
    159 |
    160 |
    161 |
    162 |
    163 |
    164 |
    177 | You have reached the character limit (10k), sign up for more at 178 | www.ibm.com/insert-url-here
    179 | 180 | 181 |
    182 |
    183 | 184 |
    185 |
    186 |
    187 | 188 |
    189 | 190 |
    191 | 192 |
    193 | 194 |
    195 | 196 |
    197 |
    198 | 199 |
    200 | Reset 201 |
    202 |
    203 | 204 | 205 |
    206 |
    207 |

    Output

    208 |

    Copy output from this field to clipboard.

    209 |
    210 |
    211 | 220 |
    221 |
    222 | 223 |
    224 |
    225 |
    226 | 227 | 233 |
    234 |
    235 |
    236 |
    237 |
    238 |
    239 | 240 |
    241 |
    242 | 243 |
    244 |
    245 |
    246 | 247 |
    248 | 249 |
    250 | 251 |
    252 | 253 |
    254 | 255 |
    256 | 257 |
    258 | 259 |
    260 | 261 | 262 | 263 | 264 | 265 | 267 | 268 | 269 |