applyrics 0.0.2 → 0.0.3.pre

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: b4ca2e8f98970107cda93dab4aa1319ce15eec97
4
- data.tar.gz: e5273c52d624cb091b1d062ee342b03650dbf308
3
+ metadata.gz: 7f8c09970f5298b306a1f05ff6c89f36fb8db206
4
+ data.tar.gz: d7226737efbd8949a1e5eaa135809d7a20457251
5
5
  SHA512:
6
- metadata.gz: 0eb761243e8dbd25564b16d3c5cee3e2aa67834d1adfed9c55ce3c3d33a67286a09502f97aaabe7489388c919740085ef2a110777fa213db121e783586d6443a
7
- data.tar.gz: 866a96e777269425eab3eb6750fb747e2572a48b96d2f0db6f4dae668c266517edf28882a76ac74467839c69a513082c5cef041a095831b5ff9d2881a1e4db4b
6
+ metadata.gz: 9c05ad2a2ee39d8854a7487f96ac1efaa4e70c4f7c828df7a8785a547a43bd430f0d7ca1f6a6eb629009e1cc218e6d03fa3359ac2f8489d2a5e35d1872a92180
7
+ data.tar.gz: a65d253e07a1cf8a45e2a9362073b9bc7114344321869cf47684583591bf58e3e0488854f62a8f0b4b5f917c091a3f569d4839e4903bf86f898aaece54f0abdb
data/README.md CHANGED
@@ -8,49 +8,64 @@ Manage your localization with confidence.
8
8
 
9
9
  ## Disclaimer
10
10
 
11
- ---
12
- This software should be considered ***pre-alpha*** and may thus be incomplete and contain bugs.
13
- ---
11
+ **This software should be considered _pre-alpha_ and may thus change at any time, be incomplete or contain bugs.**
12
+
13
+ ## Why Applyrics?
14
+
15
+ Managing translations for mobile projects can be a mess, especially if you are working with multiple platforms.
16
+ iOS projects use key-value \*.strings files, Android use xmls, and variables are defined differently.
17
+
18
+ *Applyrics* removes these obstacles and lets you manage languages using unified json files.
14
19
 
15
20
  ## Status
16
21
 
17
22
  | Feature | iOS | Android |
18
23
  | --------- | --- | --------|
19
- | init | :x: | :x: |
20
- | rebuild | :x: | :x: |
24
+ | extract | :x: | :x: |
21
25
  | apply | :x: | :x: |
22
- | sync | :x: | :x: |
23
26
 
24
27
  ## Installation
25
28
 
26
29
  Install using ruby gems:
27
30
 
28
- sudo gem install applyrics --verbose
31
+ sudo gem install applyrics --verbose
29
32
 
30
33
 
31
34
  ## Usage
32
35
 
33
- Initialize
34
- (iOS: :x: Android: :x:)
36
+ Usually you start out by extracting the strings from an existing project into a json file by running the following command in your projects directory:
35
37
 
36
- applyrics init
38
+ applyrics extract
37
39
 
38
40
 
39
- Rebuild language files
40
- (iOS: :x: Android: :x:)
41
+ After you've made changes to the translations you can apply those changes to the projects.
42
+ Notice the addition of the *--rebuild* flag. This will ensure that we don't miss any new keys that might have been added.
41
43
 
42
- applyrics rebuild
44
+ applyrics apply --rebuild
43
45
 
44
46
 
45
- Apply a json language file
47
+ ### Global flags
48
+
49
+ | Flag | Default | Description |
50
+ | --------------- | ------- | ---------------------------- |
51
+ | --verbose | false | Output more detailed logs |
52
+ | --rebuild | false | Rebuilds strings from source |
53
+ | --lang CODE | *All* | Language to work with |
54
+ | --project PATH | "./" | Path to project |
55
+
56
+
57
+ ### Actions
58
+
59
+ Extract strings from project and create strings.json file
46
60
  (iOS: :x: Android: :x:)
47
61
 
48
- applyrics apply
62
+ applyrics extract
49
63
 
50
- Sync languages
64
+
65
+ Apply a json language file
51
66
  (iOS: :x: Android: :x:)
52
67
 
53
- applyrics sync
68
+ applyrics apply
54
69
 
55
70
 
56
71
  ## License
@@ -1,5 +1,7 @@
1
1
  require 'commander'
2
+ require 'colored'
2
3
  require 'applyrics/setup'
4
+ require 'applyrics/languagefile'
3
5
 
4
6
  module Applyrics
5
7
  class CLI
@@ -14,48 +16,80 @@ module Applyrics
14
16
  program :version, Applyrics::VERSION
15
17
  program :description, Applyrics::DESCRIPTION
16
18
  program :help_formatter, :compact
19
+ global_option '--project PATH', String, 'Path to iOS or Android project'
20
+ global_option '--[no-]rebuild', TrueClass, 'Rebuild language files from source'
21
+ global_option '--lang CODE', String, 'Only perform the action for the specified language'
17
22
 
18
23
  command :init do |c|
19
24
  c.syntax = "applyrics init"
20
- c.description = "Sets up the project"
25
+ c.description = "Setup the project for applyrics"
21
26
  c.action do |args, options|
22
- puts "Not implemented yet... Sorry!"
27
+ project = Applyrics::Project.new()
28
+
29
+ if project.nil?
30
+ puts "Error"
31
+ else
32
+ case project.platform
33
+ when :ios
34
+ puts "Located ".green + "iOS".bold.green + " project".green
35
+ when :android
36
+ puts "Located ".green + "Android".bold.green + " project".green
37
+ end
38
+
39
+ langs = project.detected_languages
40
+ puts "Found #{langs.length} languages: #{langs.join(', ')}".green
41
+ puts ""
42
+
43
+ lang_files = project.language_files
44
+ langs.each do |lang|
45
+ if !lang_files.key?(lang)
46
+ puts "[#{lang}] No files detected for language!".yellow
47
+ next
48
+ end
49
+ end
50
+
51
+ end
23
52
  end
24
53
  end
25
54
 
26
- command :rebuild do |c|
27
- c.syntax = "applyrics rebuild"
28
- c.description = "Rebuilds language files for your project"
29
- c.option '--project STRING', String, 'Path to iOS or Android project'
55
+ command :extract do |c|
56
+ c.syntax = "applyrics extract"
57
+ c.description = "Pull strings from the project into a strings.json file"
58
+ c.option '--force-split', TrueClass, 'Saves one language file per language instead of a single one for all languages'
30
59
  c.action do |args, options|
31
- options.default :project => './'
32
- puts "rebuilding..."
60
+
33
61
  project = Applyrics::Project.new()
34
- project.rebuild_files()
62
+ detect_lang = project.detected_languages
63
+
64
+ langs = project.string_files()
65
+
66
+ puts "Found files for #{langs.length} languages".green
67
+
68
+ if options.rebuild
69
+ puts "Rebuilding...".blue
70
+ rebuilt = project.rebuild_files()
71
+ langs = langs.merge(rebuilt)
72
+ puts "Language \"#{project.default_language}\" is rebuilt from source into #{rebuilt[project.default_language].length} files".blue
73
+ end
74
+
75
+ puts "Writing #{langs.length} languages: #{langs.keys.join(', ')}".green
76
+
77
+ file = LanguageFile.new(File.join("./", "strings.json"), langs)
78
+ file.write
79
+
35
80
  end
36
81
  end
37
82
 
38
83
  command :apply do |c|
39
84
  c.syntax = "applyrics apply"
40
85
  c.description = "Applies language from a .json file"
41
- c.option '--project STRING', String, 'Path to iOS or Android project'
42
- c.option '--data STRING', String, 'Path to .json file (Default: lyrics.json)'
86
+ c.option '--data STRING', String, 'Path to .json file (Default: strings.json)'
43
87
  c.action do |args, options|
44
88
  options.default :project => './', :data => './lyrics.json'
45
89
  puts "Not implemented yet... Sorry!"
46
90
  end
47
91
  end
48
92
 
49
- command :sync do |c|
50
- c.syntax = "applyrics sync"
51
- c.description = "Syncs language from applyrics.io"
52
- c.option '--project STRING', String, 'Path to iOS or Android project'
53
- c.action do |args, options|
54
- options.default :project => './'
55
- puts "Not implemented yet... Sorry!"
56
- end
57
- end
58
-
59
93
  run!
60
94
  end
61
95
  end
@@ -49,7 +49,7 @@ module Applyrics
49
49
  status = $?.exitstatus
50
50
  if status != 0
51
51
  o = output.join("\n")
52
- puts o
52
+ puts "Status #{status} - #{o}"
53
53
  end
54
54
 
55
55
  return output.join("\n")
@@ -1,4 +1,4 @@
1
1
  module Applyrics
2
- VERSION = "0.0.2"
2
+ VERSION = "0.0.3.pre"
3
3
  DESCRIPTION = "Handle localization for all your mobile projects"
4
4
  end
@@ -0,0 +1,42 @@
1
+ require 'multi_json'
2
+
3
+ # encoding=utf-8
4
+ module Applyrics
5
+ class LanguageFile
6
+
7
+ def initialize(path, data=nil)
8
+ @path = path
9
+ @hash = data
10
+ if data.nil?
11
+ read
12
+ end
13
+ end
14
+
15
+ def [](key)
16
+ @hash[key]
17
+ end
18
+
19
+ def []=(key, value)
20
+ @hash[key] = value
21
+ end
22
+
23
+ def language?(key)
24
+ @hash.key?(key)
25
+ end
26
+
27
+ def languages
28
+ @hash.keys
29
+ end
30
+
31
+ def read
32
+ @hash = {}
33
+ data = File.read(@path)
34
+ @hash = MultiJson.load(data)
35
+ end
36
+
37
+ def write()
38
+ File.open(@path, 'w') { |file| file.write(MultiJson.dump(@hash, :pretty => true)) }
39
+ end
40
+
41
+ end
42
+ end
@@ -47,15 +47,33 @@ module Applyrics
47
47
  @project.detected_languages()
48
48
  end
49
49
 
50
+ def language_files
51
+ @project.language_files()
52
+ end
53
+
54
+ # @return [String] The language which are the default language in the project
55
+ def default_language
56
+ @project.default_language
57
+ end
58
+
50
59
  # @param [String] the name of the setting to read.
51
60
  # @return [String, nil] the value of the setting or nil if not found.
52
61
  def platform_project_settings(name)
53
62
  @project.platform_project_settings(name)
54
63
  end
55
64
 
65
+ # @return [Object, nil] the strings files found in the project
66
+ def string_files
67
+ @project.string_files()
68
+ end
69
+
56
70
  # Rebuild the language files.
57
71
  def rebuild_files
58
72
  @project.rebuild_files()
59
73
  end
74
+
75
+ def platform
76
+ @platform
77
+ end
60
78
  end
61
79
  end
@@ -1,6 +1,7 @@
1
1
  # encoding: utf-8
2
2
  require 'i18n_data'
3
3
  require 'multi_json'
4
+ require 'fileutils'
4
5
  require 'applyrics/tools/genstrings'
5
6
  require 'applyrics/tools/ibtool'
6
7
  require 'applyrics/stringsfile'
@@ -15,22 +16,47 @@ module Applyrics
15
16
  end
16
17
  @path = path
17
18
  @platform_settings = nil
18
- @langs = {}
19
+ @langs = []
20
+ @default_language = nil
19
21
  end
20
22
 
21
23
  # Return a list of detected languages in the project
22
24
  def detected_languages
25
+ @langs = []
23
26
  folder = self.platform_project_settings("SOURCE_ROOT")
24
- base_language = I18nData.language_code(self.platform_project_settings("DEVELOPMENT_LANGUAGE")).downcase
25
27
  lang_folders = Dir.glob(File.join(folder, "**", "*.lproj"))
26
28
  lang_folders.each do |lang_folder|
27
29
  lang = /([A-Za-z\-]*?)\.lproj/.match(lang_folder)[1]
28
- lang = (lang == "Base" ? base_language : lang)
29
- @langs[lang] = lang_folder
30
+ lang = (lang == "Base" ? default_language : lang)
31
+ @langs << lang
30
32
  end
31
33
  return @langs
32
34
  end
33
35
 
36
+ def language_files
37
+ folder = self.platform_project_settings("SOURCE_ROOT") unless !folder.nil?
38
+ out = {}
39
+ Dir[File.join(folder, "**","*.strings")].each do |file|
40
+ lang = /(\w*).lproj/.match(file)[1]
41
+ lang = (lang == "Base" ? default_language : lang)
42
+
43
+ if !out.key?(lang)
44
+ out[lang] = []
45
+ end
46
+
47
+ out[lang] << file
48
+ end
49
+
50
+ out
51
+ end
52
+
53
+ def default_language
54
+ if @default_language.nil?
55
+ @default_language = I18nData.language_code(self.platform_project_settings("DEVELOPMENT_LANGUAGE")).downcase
56
+ end
57
+ @default_language
58
+ end
59
+
34
60
  def platform_project_settings(name)
35
61
  if @platform_settings.nil?
36
62
  cmd = ["set -o pipefail && xcrun xcodebuild -showBuildSettings"]
@@ -42,9 +68,29 @@ module Applyrics
42
68
  return result.split(" = ").last
43
69
  end
44
70
 
71
+ def string_files(folder=nil)
72
+ folder = self.platform_project_settings("SOURCE_ROOT") unless !folder.nil?
73
+
74
+ out = {}
75
+
76
+ Dir[File.join(folder, "**", "*.lproj", "*.strings")].each do |file|
77
+ strings = StringsFile.new(file)
78
+ lang = /(\w*).lproj/.match(file)[1]
79
+
80
+ if !out.key?(lang)
81
+ out[lang] = {}
82
+ end
83
+
84
+ out[lang][File.basename(file)] = strings.hash
85
+ end
86
+
87
+ out
88
+ end
89
+
90
+ # NOTE: This will only rebuild the base language
45
91
  def rebuild_files
46
92
  folder = self.platform_project_settings("SOURCE_ROOT")
47
- tmp_folder = "./.tmp/"
93
+ tmp_folder = "./tmp/"
48
94
 
49
95
  if !Dir.exist?(tmp_folder)
50
96
  Dir.mkdir(tmp_folder, 0700)
@@ -53,16 +99,18 @@ module Applyrics
53
99
  GenStrings.run("#{folder}", tmp_folder)
54
100
  IBTool.run("#{folder}", tmp_folder)
55
101
 
56
- out = {}
102
+ lang = default_language
103
+ out = {"#{lang}" => {}}
104
+ langHash = out["#{lang}"]
105
+
57
106
  Dir[File.join(tmp_folder, "*.strings")].each do |file|
58
- puts file
59
107
  strings = StringsFile.new(file)
60
- out[File.basename(file)] = strings.hash
108
+ langHash[File.basename(file)] = strings.hash
61
109
  end
62
110
 
63
- File.open(File.join("./", "strings.json"), 'w') { |file| file.write(MultiJson.dump(out, :pretty => true)) }
64
-
111
+ FileUtils.remove_dir(tmp_folder)
65
112
 
113
+ out
66
114
  end
67
115
  end
68
116
  end
@@ -2,9 +2,9 @@
2
2
  module Applyrics
3
3
  class StringsFile
4
4
 
5
- def initialize(filename, data=nil)
6
- @filename = filename
7
- @hash = data.nil? ? {} : data
5
+ def initialize(path, data=nil)
6
+ @path = path
7
+ @hash = data
8
8
  if data.nil?
9
9
  read
10
10
  end
@@ -13,7 +13,7 @@ module Applyrics
13
13
  def read
14
14
  @hash = {}
15
15
  parser = Parser.new(@hash)
16
- File.open(@filename, 'rb:utf-16LE:utf-8') { |fd| parser.parse fd }
16
+ File.open(@path, 'rb:bom|utf-16LE:utf-8') { |fd| parser.parse fd }
17
17
  self
18
18
  end
19
19
 
@@ -44,16 +44,8 @@ module Applyrics
44
44
 
45
45
  def parse(data)
46
46
  @hash.clear
47
- found_bad_bytes = false
48
47
  data.each_line do |line|
49
48
  @line = line.chomp
50
- if !found_bad_bytes
51
- first_bytes = @line[0..1].bytes.to_a
52
- if first_bytes.length == 2 && first_bytes[0] == 255
53
- @line = @line[2,@line.length].force_encoding('UTF-8')
54
- found_bad_bytes = true
55
- end
56
- end
57
49
 
58
50
  case @line
59
51
  when @comment_regex
@@ -15,7 +15,7 @@ module Applyrics
15
15
  cmd << "-o " + Shellwords.escape("#{output_folder}")
16
16
  cmd << Shellwords.join(files(folder))
17
17
 
18
- puts Command.execute(cmd)
18
+ Command.execute(cmd)
19
19
  end
20
20
 
21
21
  def files(folder)
@@ -19,7 +19,7 @@ module Applyrics
19
19
  cmd << Command.which("ibtool")
20
20
  cmd << "--export-strings-file " + Shellwords.escape("#{output_file}")
21
21
  cmd << Shellwords.escape("#{file}")
22
- puts Command.execute(cmd)
22
+ Command.execute(cmd)
23
23
  end
24
24
  end
25
25
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: applyrics
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.2
4
+ version: 0.0.3.pre
5
5
  platform: ruby
6
6
  authors:
7
7
  - Frederik Wallner
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-03-28 00:00:00.000000000 Z
11
+ date: 2016-04-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: commander
@@ -125,6 +125,7 @@ files:
125
125
  - lib/applyrics/command.rb
126
126
  - lib/applyrics/environment.rb
127
127
  - lib/applyrics/info.rb
128
+ - lib/applyrics/languagefile.rb
128
129
  - lib/applyrics/lyricsfile.rb
129
130
  - lib/applyrics/project.rb
130
131
  - lib/applyrics/project_ios.rb
@@ -141,8 +142,10 @@ files:
141
142
  homepage: https://github.com/applyrics/applyrics-gem
142
143
  licenses:
143
144
  - MIT
144
- metadata: {}
145
- post_install_message:
145
+ metadata:
146
+ issue_tracker: https://github.com/applyrics/applyrics-gem/issues
147
+ post_install_message: Thank you for using applyrics! Please keep in mind that this
148
+ software is in early development, things might break.
146
149
  rdoc_options: []
147
150
  require_paths:
148
151
  - lib
@@ -153,9 +156,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
153
156
  version: '0'
154
157
  required_rubygems_version: !ruby/object:Gem::Requirement
155
158
  requirements:
156
- - - '>='
159
+ - - '>'
157
160
  - !ruby/object:Gem::Version
158
- version: '0'
161
+ version: 1.3.1
159
162
  requirements: []
160
163
  rubyforge_project:
161
164
  rubygems_version: 2.0.14