{"id":29068791,"url":"https://github.com/aspectron/iris-i18n","last_synced_at":"2025-06-27T11:09:26.605Z","repository":{"id":26984426,"uuid":"30448200","full_name":"aspectron/iris-i18n","owner":"aspectron","description":null,"archived":false,"fork":false,"pushed_at":"2018-08-22T09:57:09.000Z","size":604,"stargazers_count":1,"open_issues_count":0,"forks_count":2,"subscribers_count":9,"default_branch":"master","last_synced_at":"2025-05-19T01:17:28.320Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":"MinecraftForge/ForgeGradle","license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/aspectron.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2015-02-07T06:57:31.000Z","updated_at":"2018-08-22T09:57:11.000Z","dependencies_parsed_at":"2022-08-31T08:25:09.483Z","dependency_job_id":null,"html_url":"https://github.com/aspectron/iris-i18n","commit_stats":null,"previous_names":["aspectron/zetta-i18n"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/aspectron/iris-i18n","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aspectron%2Firis-i18n","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aspectron%2Firis-i18n/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aspectron%2Firis-i18n/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aspectron%2Firis-i18n/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/aspectron","download_url":"https://codeload.github.com/aspectron/iris-i18n/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aspectron%2Firis-i18n/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":261629945,"owners_count":23187143,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2025-06-27T11:09:25.021Z","updated_at":"2025-06-27T11:09:26.589Z","avatar_url":"https://github.com/aspectron.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# iris-i18n\n\nIRIS - Site Localisation Module\n-----\n\niris-i18n module is integrated within iris applications and provides tools for web site translation.  This module does not currently integrate with Transifex or any other translation services. It provides it's own translation backend, which function in real-time - any entry translated is immediately visible on the web site.\n\niris-i18n requires EJS rendering engine.\n\n## Configuration\n\n`your-app/config/` folder contains 3 files: \n* `i18n.conf` - configration settings\n* `i18n.users` - configuration for user accounts\n* `i18n.data` - data file containing all translation entries\n\n#### i18n.conf\n\n`i18n.conf` mainly contains list of supported languages and is automatically saved each time options are changed in the translation backend (enabling/disabling active languages).\n\n#### i18n.users\n\n`i18n.users` should be created locally when your application is deployed.  It must not be present in git (unless your project is a private repository)\n\nUser configuration is done as follows:\n```\n{\n\t\"\u003cusername\u003e\" : {\n\t\t\"locales\" : \"en fr\",\t// or \"*\" for all  (controls access to specific languages, space separated locale codes)\n\t\t\"pass\" : \"\u003csha256\u003e\"\t\t// hex sha256 of pass\n\t}\n}\n```\n\nUser login to the i18n backend uses geometric back-off algorithm, which means that each time incorrect login is made from a specific IP, the amount of seconds user has to wait doubles.\n\nTo generate a password, you can use simple hex output of sha256.  This can be easily done here: http://www.xorbin.com/tools/sha256-hash-calculator or in NodeJs: `console.log(require(\"crypto\").createHash(\"sha256\").update(\"\u003cpassword\u003e\").digest(\"hex\"))`\n\n#### i18n.data\n\n`i18n.data` is a custom data format that is kept in git and lives together with your project.  The file format is custom in order to allow easier merging when encountering git merge conflicts.\n\n\n## Translation Entries\n\nTranslation entries are generated using two phases.  During the first phase, iris-i18n module scans `html` and `ejs` files located in your project and extracts all visible entries.  Second phase is when translation entries are actually displayed on the web site.\n\nAll translation entries are kept in memory and when entries are translated, the database is delay-flushed to `i18n.data` file.\n\nTo check if any translation has been done, you can simply do `git diff` in your project to see if any modifications have been done to `i18n.data` file.\n\n## Usage\n\n`iris-i18n` provides a variable `_T` globally available within the EJS rendering context.  `_T` is a function and a variable container (object) at the same time.  Following fields are available under `_T`:\n\n* `_T.locale` - current locale code\n* `_T.languages` - list of active/enabled languages\n* `_T.availableLanguages` - list of available languages (including languages that have not been activated/enabled)\n* `_T.source` - source language of the site (typically \"en\")\n\nTo add a text entry to the translation database, user must pass it through a `_T()` function during EJS rendering phase (by embedding it into EJS view) as follows:\n\n```\n\u003c!-- without support for HTML entities --\u003e\n\u003c%= _T(\"Hello World\") %\u003e\n\n\u003c!-- with suppor for HTML entities --\u003e\n\u003c%- _T(\"Hello World\") %\u003e\n```\n\n**NOTE:** Using EJS escaping for HTML entities `\u003c%= %\u003e` tag is recommended as non-escaping output tag `\u003c%- %\u003e` allows HTML injection into the web page.  However, in some cases, especially when it comes to RTL languages and text envelopping links, it is desirable to re-position text around the link.  In this case, unescaped text is fine. Just make sure to review translated entries or make sure you trust people who are translating your content.\n\nFor security sensitive sites and applications, you can deploy your NodeJs server in an alternate location (or on an alternate port), have people do the translation and then validate it by reviewing `i18n.data` file.  Once done, commit the changes and pull them on the primary server.\n\nNote on escaping - when allowing for unescaped HTML entities, you must make sure that HTML entities in the original HTML are preserved, as otherwise this may break your HTML content. (i.e. `\u003ca href=\"abc\"\u003e` is preserved in original form - ommission of quotes will produce HTML with invalid syntax)\n\n**IMPORTANT:** When pulling `i18n.data` changes from git, you must restart your process, preferably stop, pull and start.  If site content is actively being translated, there is a risk of the running process to overwrite `i18n.data` file if someone translates an entry after the updated file has been pulled.  We may change this behavior in the future.\n\nIf you have text located in client-side JS objects, best way to handle this is to relocate these objects into the EJS space, transform them via the `_T()` function and re-publish them back to client JS objects.  Example:\n\n```\n\u003c% \n\tvar obj = [\n\t\t{ title : \"first\" },\n\t\t{ title : \"second\"}\n\t];\n\n\t_.each(obj, function(o) {\n\t\to.title = _T(o.title);\n\t})\n%\u003e\n\n\u003cscript\u003e\n\tvar obj = \u003c%= JSON.stringify(obj) %\u003e\n\u003c/script\u003e\n\n```\n\n## Translation backend\n\nTranslation backend can be accessed via `/i18n/` path in your iris application.  (for example: `http://your-site.com/i18n/`)\n\nDescription of the user interface is available here: https://github.com/aspectron/iris-i18n/blob/master/doc/iris-i18n-user-interface.pdf\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Faspectron%2Firis-i18n","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Faspectron%2Firis-i18n","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Faspectron%2Firis-i18n/lists"}