logaling-command 0.1.7 → 0.1.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.travis.yml +2 -8
- data/CHANGES +8 -0
- data/lib/logaling/command/application.rb +57 -22
- data/lib/logaling/command/version.rb +1 -1
- data/lib/logaling/glossary.rb +14 -2
- data/lib/logaling/glossary_db.rb +15 -6
- data/lib/logaling/glossary_sources/glossary_yaml_source.rb +5 -1
- data/lib/logaling/project.rb +35 -0
- data/lib/logaling/repository.rb +29 -0
- data/spec/logaling/command_spec.rb +74 -1
- metadata +2 -2
data/.travis.yml
CHANGED
@@ -5,11 +5,5 @@ notifications:
|
|
5
5
|
language: ruby
|
6
6
|
rvm:
|
7
7
|
- 1.9.3
|
8
|
-
|
9
|
-
-
|
10
|
-
- sudo apt-get update
|
11
|
-
- sudo apt-get -y --allow-unauthenticated install groonga-keyring
|
12
|
-
- sudo apt-get -y purge zeromq
|
13
|
-
- sudo apt-get update
|
14
|
-
- sudo apt-get -y install groonga libgroonga-dev
|
15
|
-
- bundle install
|
8
|
+
before_install:
|
9
|
+
- curl https://raw.github.com/groonga/groonga/master/data/travis/setup.sh | sh
|
data/CHANGES
CHANGED
@@ -54,7 +54,8 @@ module Logaling::Command
|
|
54
54
|
'-U' => :unregister,
|
55
55
|
'-L' => :list,
|
56
56
|
'-s' => :show,
|
57
|
-
'-v' => :version
|
57
|
+
'-v' => :version,
|
58
|
+
'-c' => :copy
|
58
59
|
|
59
60
|
class_option "glossary", type: :string, aliases: "-g"
|
60
61
|
class_option "source-language", type: :string, aliases: "-S"
|
@@ -64,24 +65,35 @@ module Logaling::Command
|
|
64
65
|
|
65
66
|
desc 'new [PROJECT NAME] [SOURCE LANGUAGE] [TARGET LANGUAGE(optional)]', 'Create .logaling'
|
66
67
|
method_option "no-register", type: :boolean, default: false
|
68
|
+
method_option "personal", type: :boolean, default: false
|
67
69
|
def new(project_name, source_language, target_language=nil)
|
68
|
-
unless
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
70
|
+
unless options['personal']
|
71
|
+
unless File.exist?(logaling_config_path)
|
72
|
+
FileUtils.mkdir_p(File.join(logaling_config_path, "glossary"))
|
73
|
+
|
74
|
+
config = Logaling::Config.new("glossary" => project_name, "source-language" => source_language)
|
75
|
+
config.merge!("target-language" => target_language) if target_language
|
76
|
+
config.save(File.join(logaling_config_path, "config"))
|
77
|
+
|
78
|
+
unless options["no-register"]
|
79
|
+
@dotfile_path = options["logaling-config"] || Logaling::Project.find_dotfile
|
80
|
+
@project_config_path = File.join(@dotfile_path, 'config')
|
81
|
+
@config.load(@project_config_path)
|
82
|
+
register_and_index
|
83
|
+
end
|
84
|
+
say "Successfully created #{logaling_config_path}"
|
85
|
+
else
|
86
|
+
say "#{logaling_config_path} already exists."
|
80
87
|
end
|
81
|
-
say "Successfully created #{logaling_config_path}"
|
82
88
|
else
|
83
|
-
|
89
|
+
raise Logaling::CommandFailed, "[TARGET-LANGUAGE] is required when you use '--personal'" unless target_language
|
90
|
+
personal_project = @repository.create_personal_project(project_name, source_language, target_language)
|
91
|
+
say "Successfully created #{personal_project.path}"
|
84
92
|
end
|
93
|
+
rescue Logaling::CommandFailed => e
|
94
|
+
say e.message
|
95
|
+
rescue Logaling::GlossaryAlreadyRegistered => e
|
96
|
+
say e.message
|
85
97
|
end
|
86
98
|
|
87
99
|
desc 'import', 'Import external glossary'
|
@@ -176,6 +188,7 @@ module Logaling::Command
|
|
176
188
|
check_logaling_home_exists
|
177
189
|
project = @repository.find_project(@config.glossary)
|
178
190
|
raise Logaling::ProjectNotFound unless project
|
191
|
+
raise Logaling::ProjectNotFound if project.class.name == 'Logaling::ImportedProject'
|
179
192
|
glossary = project.glossary(@config.source_language, @config.target_language)
|
180
193
|
if glossary.bilingual_pair_exists?(source_term, target_term)
|
181
194
|
raise Logaling::TermError, "term '#{source_term}: #{target_term}' already exists in '#{@config.glossary}'"
|
@@ -296,6 +309,7 @@ module Logaling::Command
|
|
296
309
|
|
297
310
|
desc 'show', 'Show terms in glossary.'
|
298
311
|
method_option "no-pager", type: :boolean, default: false
|
312
|
+
method_option "annotation", type: :string, aliases: "-A"
|
299
313
|
def show
|
300
314
|
required_options = {
|
301
315
|
"glossary" => "input glossary name '-g <glossary name>'",
|
@@ -304,10 +318,9 @@ module Logaling::Command
|
|
304
318
|
}
|
305
319
|
@config.check_required_option(required_options)
|
306
320
|
check_logaling_home_exists
|
307
|
-
|
308
|
-
raise Logaling::
|
309
|
-
|
310
|
-
terms = glossary.terms
|
321
|
+
glossary = @repository.find_glossary(@config.glossary, @config.source_language, @config.target_language)
|
322
|
+
raise Logaling::GlossaryNotFound unless glossary
|
323
|
+
terms = glossary.terms(options["annotation"])
|
311
324
|
unless terms.empty?
|
312
325
|
run_pager
|
313
326
|
terms.each do |term|
|
@@ -321,7 +334,7 @@ module Logaling::Command
|
|
321
334
|
end
|
322
335
|
rescue Logaling::CommandFailed, Logaling::GlossaryDBNotFound => e
|
323
336
|
say e.message
|
324
|
-
rescue Logaling::
|
337
|
+
rescue Logaling::GlossaryNotFound
|
325
338
|
say "glossary <#{@config.glossary}> not found."
|
326
339
|
say "Try 'loga list' and confirm glossary name."
|
327
340
|
end
|
@@ -334,8 +347,13 @@ module Logaling::Command
|
|
334
347
|
projects = @repository.projects
|
335
348
|
unless projects.empty?
|
336
349
|
run_pager
|
337
|
-
|
338
|
-
|
350
|
+
# 用語集の一覧といいつつプロジェクトの一覧を出していて、
|
351
|
+
# かつ個人用のプロジェクトと .logaling によるプロジェクトで
|
352
|
+
# プロジェクトとして表現しているスコープが異なっているために、
|
353
|
+
# 重複した名前のプロジェクトが表示されるケースが存在する
|
354
|
+
#TODO 表示する情報の単位を整理後に見直す
|
355
|
+
projects.map(&:name).uniq.each do |project_name|
|
356
|
+
printf(" %s\n", project_name)
|
339
357
|
end
|
340
358
|
else
|
341
359
|
"There is no registered glossary."
|
@@ -344,6 +362,23 @@ module Logaling::Command
|
|
344
362
|
say e.message
|
345
363
|
end
|
346
364
|
|
365
|
+
desc 'copy [GLOSSARY NAME] [SOURCE LANGUAGE] [TARGET LANGUAGE] [NEW GLOSSARY NAME] [NEW SOURCE LANGUAGE] [NEW TARGET LANGUAGE]', 'Copy personal glossary'
|
366
|
+
def copy(project_name, source_language, target_language, new_project_name, new_source_language, new_target_language)
|
367
|
+
check_logaling_home_exists
|
368
|
+
|
369
|
+
src_glossary = @repository.find_glossary(project_name, source_language, target_language)
|
370
|
+
unless src_glossary
|
371
|
+
raise Logaling::GlossaryNotFound, "Can't found #{project_name}.#{source_language}.#{target_language}"
|
372
|
+
end
|
373
|
+
|
374
|
+
dest_project = @repository.create_personal_project(new_project_name, new_source_language, new_target_language)
|
375
|
+
dest_glossary = dest_project.glossary(new_source_language, new_target_language)
|
376
|
+
|
377
|
+
dest_glossary.merge!(src_glossary)
|
378
|
+
rescue Logaling::CommandFailed, Logaling::GlossaryAlreadyRegistered, Logaling::GlossaryNotFound => e
|
379
|
+
say e.message
|
380
|
+
end
|
381
|
+
|
347
382
|
private
|
348
383
|
def error(msg)
|
349
384
|
STDERR.puts(msg)
|
data/lib/logaling/glossary.rb
CHANGED
@@ -17,6 +17,7 @@
|
|
17
17
|
module Logaling
|
18
18
|
class Glossary
|
19
19
|
SUPPORTED_FILE_TYPE = %w(yml tsv csv)
|
20
|
+
SUPPORTED_ANNOTATION = %w(wip)
|
20
21
|
|
21
22
|
attr_reader :name, :source_language, :target_language
|
22
23
|
|
@@ -27,12 +28,13 @@ module Logaling
|
|
27
28
|
@project = project
|
28
29
|
end
|
29
30
|
|
30
|
-
def terms
|
31
|
+
def terms(annotation_word=nil)
|
31
32
|
raise Logaling::GlossaryDBNotFound unless File.exist?(@project.glossary_db_path)
|
32
33
|
index
|
33
34
|
terms = []
|
35
|
+
filter_option = annotation_word ? '@' + annotation_word : annotation_word
|
34
36
|
Logaling::GlossaryDB.open(@project.glossary_db_path, "utf8") do |db|
|
35
|
-
terms = db.translation_list(self)
|
37
|
+
terms = db.translation_list(self, filter_option)
|
36
38
|
end
|
37
39
|
terms
|
38
40
|
end
|
@@ -75,6 +77,16 @@ module Logaling
|
|
75
77
|
end
|
76
78
|
end
|
77
79
|
|
80
|
+
def merge!(glossary)
|
81
|
+
glossary.terms.each do |term|
|
82
|
+
add(term[:source_term], term[:target_term], term[:note])
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
def initialize_glossary_source
|
87
|
+
glossary_source.initialize_source
|
88
|
+
end
|
89
|
+
|
78
90
|
def to_s
|
79
91
|
[@name, @source_language, @target_language].join('.')
|
80
92
|
end
|
data/lib/logaling/glossary_db.rb
CHANGED
@@ -168,13 +168,22 @@ module Logaling
|
|
168
168
|
struct_result(records, snippet)
|
169
169
|
end
|
170
170
|
|
171
|
-
def translation_list(glossary, order='ascending')
|
171
|
+
def translation_list(glossary, filter_option, order='ascending')
|
172
172
|
records_raw = Groonga["translations"].select do |record|
|
173
|
-
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
173
|
+
if filter_option
|
174
|
+
[
|
175
|
+
record.glossary == glossary.name,
|
176
|
+
record.source_language == glossary.source_language,
|
177
|
+
record.target_language == glossary.target_language,
|
178
|
+
record.note =~ filter_option
|
179
|
+
]
|
180
|
+
else
|
181
|
+
[
|
182
|
+
record.glossary == glossary.name,
|
183
|
+
record.source_language == glossary.source_language,
|
184
|
+
record.target_language == glossary.target_language
|
185
|
+
]
|
186
|
+
end
|
178
187
|
end
|
179
188
|
|
180
189
|
records = records_raw.sort([
|
@@ -34,7 +34,7 @@ module Logaling::GlossarySources
|
|
34
34
|
end
|
35
35
|
|
36
36
|
def add(source_term, target_term, note)
|
37
|
-
|
37
|
+
initialize_source unless File.exist?(source_path)
|
38
38
|
|
39
39
|
glossary_source = self.load
|
40
40
|
glossary_source << build_term(source_term, target_term, note)
|
@@ -88,6 +88,10 @@ module Logaling::GlossarySources
|
|
88
88
|
end
|
89
89
|
end
|
90
90
|
|
91
|
+
def initialize_source
|
92
|
+
dump_glossary_source([])
|
93
|
+
end
|
94
|
+
|
91
95
|
private
|
92
96
|
def build_term(source_term, target_term, note)
|
93
97
|
note ||= ''
|
data/lib/logaling/project.rb
CHANGED
@@ -72,6 +72,10 @@ module Logaling
|
|
72
72
|
end
|
73
73
|
end
|
74
74
|
|
75
|
+
def has_glossary?(source_language, target_language)
|
76
|
+
glossaries.any? {|glossary| glossary.to_s == [name, source_language, target_language].join('.') }
|
77
|
+
end
|
78
|
+
|
75
79
|
private
|
76
80
|
def all_glossary_source_path
|
77
81
|
Dir.glob(File.join(glossary_source_path, "*"))
|
@@ -87,5 +91,36 @@ module Logaling
|
|
87
91
|
name, source_language, target_language, type = File.basename(@path).split(/\./)
|
88
92
|
[GlossarySource.create(@path, glossary(source_language, target_language))]
|
89
93
|
end
|
94
|
+
|
95
|
+
def glossary_source_path
|
96
|
+
File.dirname(@path)
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
class PersonalProject < Project
|
101
|
+
def self.create(root_path, glossary_name, source_language, target_language)
|
102
|
+
project_name = [glossary_name, source_language, target_language, 'yml'].join('.')
|
103
|
+
project_path = File.join(root_path, project_name)
|
104
|
+
project = PersonalProject.new(project_path)
|
105
|
+
project.initialize_glossary(source_language, target_language)
|
106
|
+
project
|
107
|
+
end
|
108
|
+
|
109
|
+
def name
|
110
|
+
File.basename(@path).split(/\./).first
|
111
|
+
end
|
112
|
+
|
113
|
+
def glossary_sources
|
114
|
+
name, source_language, target_language, type = File.basename(@path).split(/\./)
|
115
|
+
[GlossarySource.create(@path, glossary(source_language, target_language))]
|
116
|
+
end
|
117
|
+
|
118
|
+
def glossary_source_path
|
119
|
+
File.dirname(@path)
|
120
|
+
end
|
121
|
+
|
122
|
+
def initialize_glossary(source_language, target_language)
|
123
|
+
glossary(source_language, target_language).initialize_glossary_source
|
124
|
+
end
|
90
125
|
end
|
91
126
|
end
|
data/lib/logaling/repository.rb
CHANGED
@@ -44,6 +44,13 @@ module Logaling
|
|
44
44
|
FileUtils.rm_rf(project.path, :secure => true)
|
45
45
|
end
|
46
46
|
|
47
|
+
def create_personal_project(project_name, source_language, target_language)
|
48
|
+
if glossary_exists?(project_name, source_language, target_language)
|
49
|
+
raise Logaling::GlossaryAlreadyRegistered, "The glossary '#{project_name}' already exists."
|
50
|
+
end
|
51
|
+
PersonalProject.create(personal_glossary_root_path, project_name, source_language, target_language)
|
52
|
+
end
|
53
|
+
|
47
54
|
def import(glossary_source)
|
48
55
|
FileUtils.mkdir_p(cache_path)
|
49
56
|
Dir.chdir(cache_path) do
|
@@ -82,6 +89,9 @@ module Logaling
|
|
82
89
|
projects = registered_project_paths.map do |project_path|
|
83
90
|
Logaling::Project.new(project_path, self)
|
84
91
|
end
|
92
|
+
projects += personal_glossary_paths.map do |personal_glossary_path|
|
93
|
+
Logaling::PersonalProject.new(personal_glossary_path, self)
|
94
|
+
end
|
85
95
|
projects += imported_glossary_paths.map do |imported_project_path|
|
86
96
|
Logaling::ImportedProject.new(imported_project_path, self)
|
87
97
|
end
|
@@ -121,6 +131,13 @@ module Logaling
|
|
121
131
|
project = projects.detect{|project| project.name == project_name}
|
122
132
|
end
|
123
133
|
|
134
|
+
def find_glossary(project_name, source_language, target_language)
|
135
|
+
project = projects.detect do |project|
|
136
|
+
project.name == project_name and project.has_glossary?(source_language, target_language)
|
137
|
+
end
|
138
|
+
project ? project.glossary(source_language, target_language) : nil
|
139
|
+
end
|
140
|
+
|
124
141
|
def logaling_db_home
|
125
142
|
File.join(@path, "db")
|
126
143
|
end
|
@@ -130,6 +147,10 @@ module Logaling
|
|
130
147
|
File.join(@path, "projects")
|
131
148
|
end
|
132
149
|
|
150
|
+
def personal_glossary_root_path
|
151
|
+
File.join(@path, "personal")
|
152
|
+
end
|
153
|
+
|
133
154
|
def cache_path
|
134
155
|
File.join(@path, "cache")
|
135
156
|
end
|
@@ -138,8 +159,16 @@ module Logaling
|
|
138
159
|
Dir[File.join(logaling_projects_path, "*")]
|
139
160
|
end
|
140
161
|
|
162
|
+
def personal_glossary_paths
|
163
|
+
Dir[File.join(personal_glossary_root_path, "*")]
|
164
|
+
end
|
165
|
+
|
141
166
|
def imported_glossary_paths
|
142
167
|
Dir[File.join(cache_path, "*")]
|
143
168
|
end
|
169
|
+
|
170
|
+
def glossary_exists?(project_name, source_language, target_language)
|
171
|
+
not find_glossary(project_name, source_language, target_language).nil?
|
172
|
+
end
|
144
173
|
end
|
145
174
|
end
|
@@ -463,7 +463,7 @@ describe Logaling::Command::Application do
|
|
463
463
|
context 'when .logaling exists' do
|
464
464
|
before do
|
465
465
|
command.options = base_options.merge("no-pager" => true)
|
466
|
-
@stdout = capture(:stdout) {command.show}
|
466
|
+
@stdout = capture(:stdout) { command.show }
|
467
467
|
end
|
468
468
|
|
469
469
|
it 'should show translation list' do
|
@@ -477,6 +477,49 @@ describe Logaling::Command::Application do
|
|
477
477
|
end
|
478
478
|
end
|
479
479
|
|
480
|
+
describe "#show with annotation option" do
|
481
|
+
before do
|
482
|
+
command.new('spec', 'en', 'ja')
|
483
|
+
command.add("spec-test2", "スペックてすと2", "@wip")
|
484
|
+
command.add("spec-test", "スペックてすと1", "備考")
|
485
|
+
end
|
486
|
+
|
487
|
+
context 'when glossary contains annotated word' do
|
488
|
+
before do
|
489
|
+
command.options = base_options.merge("no-pager" => true)
|
490
|
+
command.options.merge!("annotation" => "wip")
|
491
|
+
@stdout = capture(:stdout) { command.show }
|
492
|
+
end
|
493
|
+
|
494
|
+
it 'should show annotated word' do
|
495
|
+
@stdout.should include "スペックてすと2"
|
496
|
+
end
|
497
|
+
|
498
|
+
context 'after annotation removed' do
|
499
|
+
before do
|
500
|
+
command.options = base_options.clone
|
501
|
+
command.update("spec-test2", "スペックてすと2", "スペックてすと2", "")
|
502
|
+
end
|
503
|
+
|
504
|
+
it 'should not show annotated word' do
|
505
|
+
@stdout.should_not include "スペックてすと1"
|
506
|
+
end
|
507
|
+
end
|
508
|
+
end
|
509
|
+
|
510
|
+
context 'when glossary does not contain annotated word' do
|
511
|
+
before do
|
512
|
+
command.options = base_options.merge("no-pager" => true)
|
513
|
+
command.options.merge!("annotation" => "wip")
|
514
|
+
@stdout = capture(:stdout) { command.show }
|
515
|
+
end
|
516
|
+
|
517
|
+
it 'should not show un-annotated word' do
|
518
|
+
@stdout.should_not include "スペックてすと1"
|
519
|
+
end
|
520
|
+
end
|
521
|
+
end
|
522
|
+
|
480
523
|
describe '#list' do
|
481
524
|
before do
|
482
525
|
command.new('spec', 'en', 'ja')
|
@@ -508,8 +551,38 @@ describe Logaling::Command::Application do
|
|
508
551
|
end
|
509
552
|
end
|
510
553
|
|
554
|
+
describe '#copy' do
|
555
|
+
let(:copied_glossary_path) { File.join(logaling_home, 'personal', 'spec.en.fr.yml') }
|
556
|
+
before do
|
557
|
+
command.new('spec', 'en', 'ja')
|
558
|
+
command.add('spec logaling', 'すぺっくろがりん')
|
559
|
+
end
|
560
|
+
|
561
|
+
context 'when new glossary does not exist' do
|
562
|
+
before do
|
563
|
+
command.copy('spec', 'en', 'ja', 'spec', 'en', 'fr')
|
564
|
+
@yaml = YAML::load_file(copied_glossary_path).find{|h| h["source_term"] == "spec logaling" }
|
565
|
+
end
|
566
|
+
|
567
|
+
it 'should copy from original glossary' do
|
568
|
+
@yaml.should == {"source_term"=>"spec logaling", "target_term"=>"すぺっくろがりん", "note"=>""}
|
569
|
+
end
|
570
|
+
end
|
571
|
+
|
572
|
+
context 'when same glossary exists in glossary list' do
|
573
|
+
before do
|
574
|
+
@stdout = capture(:stdout) {command.copy('spec', 'en', 'ja', 'spec', 'en', 'ja')}
|
575
|
+
end
|
576
|
+
|
577
|
+
it 'should not copy glossary' do
|
578
|
+
@stdout.should include "already exists"
|
579
|
+
end
|
580
|
+
end
|
581
|
+
end
|
582
|
+
|
511
583
|
after do
|
512
584
|
FileUtils.rm_rf(logaling_config)
|
513
585
|
FileUtils.rm_rf(File.join(logaling_home, 'projects', 'spec'))
|
586
|
+
FileUtils.rm_rf(File.join(logaling_home, 'personal'))
|
514
587
|
end
|
515
588
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: logaling-command
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.8
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -13,7 +13,7 @@ authors:
|
|
13
13
|
autorequire:
|
14
14
|
bindir: bin
|
15
15
|
cert_chain: []
|
16
|
-
date: 2012-
|
16
|
+
date: 2012-08-30 00:00:00.000000000 Z
|
17
17
|
dependencies:
|
18
18
|
- !ruby/object:Gem::Dependency
|
19
19
|
name: thor
|