Coder Social home page Coder Social logo

koral-- / android-gradle-localization-plugin Goto Github PK

View Code? Open in Web Editor NEW
109.0 9.0 20.0 1.04 MB

Gradle plugin for generating localized string resources

License: MIT License

Groovy 100.00%
gradle plugin i18n xml csv xls xlsx android internationalization l10n

android-gradle-localization-plugin's Introduction

android-gradle-localization-plugin

Maven Central Bintray Android Arsenal Build Status codecov

Gradle plugin for generating localized string resources

Overview

This plugin generates Android string resource XML files from CSV or XLS(X) file. Generation has to be invoked as additional gradle task. Java 1.8 is required.

Supported features

  • string arrays - see Arrays
  • plurals - see Plurals
  • non-translatable resources - translatable XML attribute
  • auto-escaping double quotes, apostrophes and newlines
  • auto-quoting leading and trailing spaces
  • syntax validation - duplicated, empty, invalid names detection
  • comments
  • formatted strings - formatted XML attribute
  • default locale specification - tools:locale
  • evaluate cell formulas

Applying plugin

Gradle 2.1+

In whichever build.gradle file.

plugins {
  id 'pl.droidsonroids.localization' version '1.0.19'
}

Note: exact version number must be specified, + cannot be used as wildcard.

All versions of Gradle

  1. Add dependency to the top-level build.gradle file.
 buildscript {
    repositories {
        mavenCentral()
        jcenter()
    }
    dependencies {
        classpath 'com.android.tools.build:gradle:3.5.3'
        classpath 'pl.droidsonroids.gradle.localization:android-gradle-localization-plugin:1.0.19'
    }
}

Note: mavenCentral() and/or jcenter() repository can be specified, + can be used as wildcard in version number.

  1. Apply plugin and add configuration to build.gradle of the application, eg:
apply plugin: 'pl.droidsonroids.localization'

Usage

Invoke localization gradle task. Task may be invoked from commandline or from Android Studio GUI.

  • from commandline: ./gradlew localization (or gradlew.bat localization on Windows)
  • from GUI: menu View->Tool Windows->Gradle and double click localization

Non existent folders will be created. WARNING existing XML files will be overwritten.

Example

The following CSV file:

name,default    ,pl       ,comment   ,translatable
file,File       ,"Plik"   ,file label,
app ,Application,,,false

will produce 2 XML files:

  • values/strings.xml:
<?xml version="1.0" encoding="utf-8"?>
<resources>
  <string name="file">File</string><!-- file label -->
  <string name="app" translatable="false">Application</string>
</resources>
  • values-pl/strings.xml:
<?xml version="1.0" encoding="utf-8"?>
<resources>
  <string name="file">Plik</string><!-- file label -->
</resources>

Configuration

Add localization extension in build.gradle of particular module.

localization {
        csvFile=file('translations.csv')
        OR
        csvFileURI='https://docs.google.com/spreadsheets/d/<key>/export?format=csv'
        OR
        csvGenerationCommand='/usr/bin/xlsx2csv translation.xlsx'
        OR
        xlsFile=file('translations.xlsx')
        OR
        xlsFileURI='https://docs.google.com/spreadsheets/d/<key>/export?format=xlsx'
}
  • csvFileURI and xlsFileURI can be any valid URI, not necessarily Google Docs' one
  • xlsFile and xlsFileURI accepts both XLSX and XLS files. If filename ends with xls file will be treated as XLS, XLSX otherwise

Sources, exactly one of them must be specified:

  • csvFile, xlsFile - CSV/XLS(X) file, Gradle's file() can be used to retrieve files by path relative to module location or absolute
  • csvFileURI, xlsFileURI - CSV/XLS(X) file URI
  • csvGenerationCommand - shell command which writes CSV as text to standard output. Command string should be specified like for Runtime#exec(). Standard error of the command is redirected to the standard error of the process executing Gradle, so it could be seen in the Gradle console.

Spreadsheet format:

  • defaultColumnName - default='default', name of the column which corresponds to default localization (values folder)
  • nameColumnIndex - default=unset (nameColumnName is taken into account), index of the column containing key names (source for the name XML attribute)
  • nameColumnName - default='name' (if nameColumnIndex is not present), name of the column containing key names (source for the name XML attribute)
  • translatableColumnName - default='translatable', name of the column containing translatable flags (source for the translatable XML attribute)
  • commentColumnName - default='comment', name of the column containing comments
  • formattedColumnName - default='formatted', name of the column formatted flags (source for the formatted XML attribute)

If both nameColumnIndex and nameColumnName are specified exception is thrown.

The following options turn off some character escaping and substitutions, can be useful if you have something already escaped in source:

  • escapeApostrophes - default=true, if set to false apostrophes (') won't be escaped
  • escapeQuotes - default=true, if set to false double quotes (") won't be escaped
  • escapeNewLines - default=true, if set to false newline characters won't be escaped
  • convertTripleDotsToHorizontalEllipsis - default=true, if set to false triple dots (...) won't be converted to ellipsis entity &#8230;
  • escapeSlashes - default=true, if set to false slashes (\) won't be escaped
  • normalizationForm - default=Normalizer.Form.NFC if set to null Unicode normalization won't be performed, see javadoc of Normalizer for more details

(X)HTML tags escaping

  • tagEscapingStrategy - default=IF_TAGS_ABSENT, defines X(H)TML tag brackets (< and >) escaping strategy possible values:
  • ALWAYS - brackets are always escaped. E.g. "<" in source becomes "&lt;" in output XML
  • NEVER - brackets are never escaped. E.g. "<" in source is passed without change to output XML
  • IF_TAGS_ABSENT - Brackets aren't escaped if text contains tags or CDATA section. E.g. <b>bold</b> will be passed without change, but "if x<4 then…" becomes "if x&lt;4 then…".
  • tagEscapingStrategyColumnName - default=unset (no column), name of the column containing non-default tag escaping strategy, if cell is non-empty then strategy defined there is used instead of global one

CSV format:

XLS(X) format:

  • sheetName - default=<name of the first sheet>, name of the sheet to be processed, only one can be specified, ignored if useAllSheets is set to true
  • useAllSheets - default=false, if set to true all sheets are processed and sheetName is ignored
  • evaluateFormulas - default=false, if set to true evaluates formulas in cells

Advanced options:

  • ignorableColumns - default=[], columns from that list will be ignored during parsing. List should contain column names e.g. ['Section', 'Notes']. Columns containing only empty cells are always ignored.
  • allowNonTranslatableTranslation - default=false, if set to true resources marked non-translatable but translated are permitted
  • allowEmptyTranslations - default=false, if set to true then empty values are permitted
  • handleEmptyTranslationsAsDefault - default=false, if set to true empty values do not result in entries in non-default languages, i.e. no empty XML entries for non-default languages are created. If set to true then allowEmptyTranslations is ignored for all but default language
  • outputFileName - default=strings.xml, XML file name (with extension) which should be generated as an output
  • outputIndent - default= (two spaces), character(s) used to indent each line in output XML files
  • skipInvalidName - default=false, if set to true then rows with invalid key names will be ignored instead of throwing an exception
  • skipDuplicatedName - default=false, if set to true then rows with duplicated key names will be ignored instead of throwing an exception. First rows with given key will be taken into account.
  • defaultLocaleQualifier - language (eg. es) and optionally region (eg. es_US) ISO codes of default translations. Default=null(unset) which effectively means English en, if set then value will be placed in tools:locale XML attribute. See Tools Attributes for more information.

Migration from versions < 1.0.19

Since version 1.0.19 completely empty (effectively empty in case of XLS(X)) rows and columns are ignored. Moreover if qualifier (usually language code) is empty exception is thrown. Previously behavior in such cases was undefined.

Migration from versions < 1.0.13:

Obsolete, non-scoped localization plugin id is no longer supported. The only valid id is pl.droidsonroids.localization.

Migration from versions < 1.0.7:

Versions older than 1.0.7 provided escapeBoundarySpaces option, which defaulted to true. Currently strings are always escaped when corresponding parsed cell contains leading or trailing spaces, but such spaces are stripped by default CSV strategy. So effectively strings are trimmed by default. If you want to include mentioned spaces in output set appropriate csvStrategy.

License

MIT License
See LICENSE file.

android-gradle-localization-plugin's People

Contributors

cryosleeper avatar ihrthk avatar koral-- avatar michallankof avatar nonda95 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

android-gradle-localization-plugin's Issues

Can I use this plugin with multiple flavours with different localizations ?

I have a project with 2 flavours. I want to have different strings for both flavours. We have small amount of strings that differ between the flavours so I want to have a single excel file with two spreadsheets - one containing all the strings used in the first flavour (the main one) and a second spreadsheet containing only the strings that differ in the second flavour, overriding the main strings (placing it inside the second flavour source sets). Is this possible with the current implementation ?

Reverse: xml to csv?

Any way we could do xml to csv?
Idea is for developers to have control over the strings and to be able to refactor them when necessary, next 'xml -> csv' and to the Google Docs for translation. When translation is finished 'csv -> xml' to update localization.

Are there any gradle command can display task properties?

PS:In order to make user of user the gradle plugin can be more conveniently and clearly to use the plugin.

Maybe Like this:

gradle -task localization properties

File sourceFile
File outRes;
File inRes;
Map<String, String> map;
boolean append = true
boolean replace = true
File report;
String csvFileURI
String csvGenerationCommand
ArrayList<String> ignorableColumns = []
CSVStrategy csvStrategy
String outputFileName = 'strings.xml'
String outputIndent = '    '
String name = "name";
String translatable = "translatable";
String comment = "comment"
boolean skipInvalidName = true
boolean skipDuplicatedName = true

Skip empty plural

What about applying allowEmptyTranslations to plurals? It is actually breaking my parsing since some of my language variants don't require specific translation to plurals.

Java version error

Error during build:

Error:(29) A problem occurred evaluating project ':app'.

pl/droidsonroids/gradle/localization/LocalizationPlugin : Unsupported major.minor version 52.0

about csvGenerationCommand

Assume i have a file in d:/language_append_CMSD_100_rev.xls ,How i use to about csvGenerationCommand? thanks.

Kotlin DSL configuration causes incorrect column parsing with xlsx intermediate format

Preconditions:

  • Newly created Google Sheet with columns "name" and "default" with a single entry ("test", "Test")
  • Plugin version 1.0.17
  • Kotlin DSL configuration as such (top-level in module-level build file):
localization {
    xlsFileURI = "https://docs.google.com/spreadsheets/d/REDACTED/export?format=xlsx"
    handleEmptyTranslationsAsDefault = true
    allowEmptyTranslations = true
    outputIndent = "    "
    skipInvalidName = true
}
  • ./gradlew localization executed

Expected results:

  • values/strings.xml created containing:
<?xml version="1.0" encoding="UTF-8"?>
<resources>
    <string name="test">Test</string>
</resources>

Actual results:

  • values/strings.xml created containing:
<?xml version="1.0" encoding="UTF-8"?>
<resources>
    <string name="test">Test</string>
</resources>
  • values-/strings.xml created containing:
<?xml version="1.0" encoding="UTF-8"?>
<resources/>

Steps taken to investigate:

  1. Tried reproducing the issue in a different project with:
  • Same XLSX uri
  • Same plugin version
  • Same project contents
  • Same gradle config
  • Only difference (As far as I can tell) is that instead of Gradle Kotlin DSL, traditional Gradle Groovy is used.
    The issue is not existent in this different project.
  1. Using existing sheets working properly in different (Groovy-based) projects. The issue persists in the Kotlin-DSL-based project

Workarounds that fix the issue

Either:

  • Adding ignorableColumns = listOf("") to config block fixes the issue. Seems like an unnecessary hack.
  • Changing xlsFileURI = "https://docs.google.com/spreadsheets/d/REDACTED/export?format=xlsx" to csvFileURI = "https://docs.google.com/spreadsheets/d/REDACTED/export?format=csv"

Notes

I might be wrong and the issue might stem from a different source. I think it's important the plugin is tested with Kotlin Gradle DSL projects.

If needed, I remain at your disposal to further investigate the issue

4 spaces instead of 2

I think there should be possibility to configure how many spaces will be added before "" tag.

Call new folder for res dir structure

Because In android gradle plugin,the res dir to be configured. You should consider res dir structure it something else such as "res" or giving us the option to configure the res dir but definitely should NOT default to "src/main/res".

ask two question

1.mBuilder.resources(MarkupBuilder),MarkupBuilder don't have resources method?
2.what mean is string(attrs)?

Default locale column not present

When I try to run task after added new strings in spreadsheets , I am getting this error

  • What went wrong:
    Execution failed for task ':app:localization'.

Default locale column not present

please, can somebody help me?

Call created file something else

If you are indeed overwriting strings.xml every time we run the gradle task, you should consider naming it something else such as "strings_generated.xml" or giving us the option to configure the file name but definitely should NOT default to strings.xml.

gradle localization failed

plugins {
id "pl.droidsonroids.localization" version "1.0.8"
}

localization {
xlsFile = file('language_iOS_append_ALL_343_RC_20150522v2.xlsx')
allowEmptyTranslations = true
defaultColumnName = "EN"
name = "Android"
ignorableColumns = ['WinPhone', 'iOS', 'END']
outputDirectory file('outRes')
sheetName "string table"
}

D:\studio_workspace\android\lite>gradle localization

FAILURE: Build failed with an exception.

column index instead of nameColumnName

Sometimes translators dont' use name for 'name column'. Also very often this is the first column.

The example:

en fr it fi
text en_text fr_text it_text fi_text

Could you add option to use column index instead of column name ?

Gradle 8 Support

The library does not support Gradle 8 and above, I ran into a few problems.

Task :app:localization FAILED
Caching disabled for task ':app:localization' because:
  Caching has not been enabled for the task
Task ':app:localization' is not up-to-date because:
  Task has not declared any outputs despite executing actions.

Execution failed for task ':app:localization'.
> Could not get unknown property 'outputDirectory' for task ':app:localization' of type pl.droidsonroids.gradle.localization.LocalizationTask.

Problem with question marks "?"

At some point, an issues surface that question marked are being "escaped" with a "" in front of them, I suspected this started when I started working on OSX

Any hints?

How can i avoid escaping newline character

In app.gradle

localization {
  csvFile = file('strings.csv')
  outputIndent = '  '
  defaultColumnName = 'en'
  escapeNewLines = false
  handleEmptyTranslationsAsDefault = 'true'
  outputFileName = 'strings.xml'
}

In strings.csv i have the next line
tutorial_analyses_title,"Analyses order \n DoctorOnline",,"",,,,,,,,,,

but after executing task localization i get such string after parsing in strings.xml

<string name="tutorial_analyses_title">Analyses order \\n DoctorOnline</string>

As a result string cannot be displayed in textView correctly. How can I avoid escaping this character? escapeNewLines = false config seems to be ignored. How can i avoid escaping this newline character?

Plugin version 1.0.19.

Thanks for help

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.