stickyflag 0.2.0
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/.gitignore +7 -0
- data/.rspec +4 -0
- data/.simplecov +9 -0
- data/.travis.yml +13 -0
- data/Gemfile +2 -0
- data/LICENSE.md +7 -0
- data/README.md +49 -0
- data/Rakefile +19 -0
- data/TODO.md +3 -0
- data/bin/stickyflag +6 -0
- data/features/clear.feature +14 -0
- data/features/clear_quietly.feature +23 -0
- data/features/configuration.feature +14 -0
- data/features/get.feature +14 -0
- data/features/get_quietly.feature +23 -0
- data/features/set.feature +14 -0
- data/features/set_quietly.feature +22 -0
- data/features/step_definitions/configuration_steps.rb +31 -0
- data/features/step_definitions/database_steps.rb +41 -0
- data/features/step_definitions/pending_steps.rb +5 -0
- data/features/step_definitions/tag_steps.rb +62 -0
- data/features/support/cukegem.rb +82 -0
- data/features/support/env.rb +37 -0
- data/features/tags.feature +18 -0
- data/features/unset.feature +14 -0
- data/features/unset_quietly.feature +23 -0
- data/lib/stickyflag/configuration.rb +66 -0
- data/lib/stickyflag/database.rb +162 -0
- data/lib/stickyflag/external_cmds.rb +64 -0
- data/lib/stickyflag/patches/tempfile_encoding.rb +22 -0
- data/lib/stickyflag/patches/tmpnam.rb +38 -0
- data/lib/stickyflag/paths.rb +47 -0
- data/lib/stickyflag/tag_factory.rb +108 -0
- data/lib/stickyflag/tags/c.rb +25 -0
- data/lib/stickyflag/tags/mmd.rb +168 -0
- data/lib/stickyflag/tags/pdf.rb +119 -0
- data/lib/stickyflag/tags/png.rb +61 -0
- data/lib/stickyflag/tags/source_code.rb +99 -0
- data/lib/stickyflag/tags/tex.rb +25 -0
- data/lib/stickyflag/version.rb +12 -0
- data/lib/stickyflag.rb +253 -0
- data/spec/spec_helper.rb +22 -0
- data/spec/stickyflag/configuration_spec.rb +132 -0
- data/spec/stickyflag/database_spec.rb +331 -0
- data/spec/stickyflag/external_cmds_spec.rb +175 -0
- data/spec/stickyflag/patches/tempfile_encoding_spec.rb +26 -0
- data/spec/stickyflag/patches/tmpnam_spec.rb +35 -0
- data/spec/stickyflag/paths_spec.rb +29 -0
- data/spec/stickyflag/tag_factory_spec.rb +185 -0
- data/spec/stickyflag/tags/c_spec.rb +14 -0
- data/spec/stickyflag/tags/mmd_spec.rb +40 -0
- data/spec/stickyflag/tags/pdf_spec.rb +39 -0
- data/spec/stickyflag/tags/png_spec.rb +6 -0
- data/spec/stickyflag/tags/tex_spec.rb +6 -0
- data/spec/stickyflag_spec.rb +482 -0
- data/spec/support/examples/c_all_comments.c +3 -0
- data/spec/support/examples/c_no_tags.c +5 -0
- data/spec/support/examples/c_with_tag.c +6 -0
- data/spec/support/examples/mmd_all_meta.mmd +6 -0
- data/spec/support/examples/mmd_crazy_keys.mmd +8 -0
- data/spec/support/examples/mmd_crazy_tags.mmd +9 -0
- data/spec/support/examples/mmd_no_tags.mmd +1 -0
- data/spec/support/examples/mmd_with_tag.mmd +3 -0
- data/spec/support/examples/pdf_no_tags.pdf +0 -0
- data/spec/support/examples/pdf_with_tag.pdf +0 -0
- data/spec/support/examples/png_no_tags.png +0 -0
- data/spec/support/examples/png_with_tag.png +0 -0
- data/spec/support/examples/tex_no_tags.tex +10 -0
- data/spec/support/examples/tex_with_tag.tex +11 -0
- data/spec/support/examples/untaggable.txt +0 -0
- data/spec/support/examples.rb +32 -0
- data/spec/support/run_with_args.rb +36 -0
- data/spec/support/silence_stream.rb +12 -0
- data/spec/support/tag_handler_behavior.rb +125 -0
- data/stickyflag.gemspec +48 -0
- metadata +399 -0
@@ -0,0 +1,29 @@
|
|
1
|
+
# -*- encoding : utf-8 -*-
|
2
|
+
require 'stickyflag/paths'
|
3
|
+
|
4
|
+
class PathsTester
|
5
|
+
include StickyFlag::Paths
|
6
|
+
end
|
7
|
+
|
8
|
+
describe 'StickyFlag::Paths' do
|
9
|
+
describe '.config_path' do
|
10
|
+
it 'includes the config.yml file name' do
|
11
|
+
PathsTester.new.config_path.should include('config.yml')
|
12
|
+
end
|
13
|
+
|
14
|
+
it "doesn't include any tildes" do
|
15
|
+
PathsTester.new.config_path.should_not include('~')
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
describe '.database_path' do
|
20
|
+
it 'includes the db.sqlite file name' do
|
21
|
+
PathsTester.new.database_path.should include('db.sqlite')
|
22
|
+
end
|
23
|
+
|
24
|
+
it "doesn't include any tildes" do
|
25
|
+
PathsTester.new.database_path.should_not include('~')
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
@@ -0,0 +1,185 @@
|
|
1
|
+
# -*- encoding : utf-8 -*-
|
2
|
+
require 'thor'
|
3
|
+
require 'stickyflag/patches/tempfile_encoding'
|
4
|
+
require 'stickyflag/paths'
|
5
|
+
require 'stickyflag/configuration'
|
6
|
+
require 'stickyflag/tag_factory'
|
7
|
+
require 'stickyflag/external_cmds'
|
8
|
+
require 'stickyflag/database'
|
9
|
+
|
10
|
+
class TagFactoryTester < Thor
|
11
|
+
include StickyFlag::Paths
|
12
|
+
include StickyFlag::Configuration
|
13
|
+
include StickyFlag::TagFactory
|
14
|
+
include StickyFlag::ExternalCmds
|
15
|
+
include StickyFlag::Database
|
16
|
+
end
|
17
|
+
|
18
|
+
describe 'StickyFlag::TagFactory' do
|
19
|
+
before(:each) do
|
20
|
+
@obj = TagFactoryTester.new
|
21
|
+
|
22
|
+
@obj.stub(:load_config!) { }
|
23
|
+
@obj.stub(:save_config!) { }
|
24
|
+
|
25
|
+
@obj.stub(:load_database) { }
|
26
|
+
@obj.stub(:update_database_from_files) { }
|
27
|
+
@obj.stub(:set_database_tag) { }
|
28
|
+
@obj.stub(:unset_database_tag) { }
|
29
|
+
@obj.stub(:clear_database_tags) { }
|
30
|
+
@obj.stub(:files_for_tags) { [] }
|
31
|
+
|
32
|
+
@obj.find_external_cmds
|
33
|
+
end
|
34
|
+
|
35
|
+
describe '.available_tagging_extensions' do
|
36
|
+
# Some extensions require the presence of actual, good files, not
|
37
|
+
# just empty shells, so we can't test them in this way. Skip those.
|
38
|
+
CANNOT_TEST = [ '.pdf', '.png' ]
|
39
|
+
|
40
|
+
it 'should call get for every good extension' do
|
41
|
+
(@obj.available_tagging_extensions - CANNOT_TEST).each do |ext|
|
42
|
+
file = Tempfile.new_with_encoding(['ext', ext])
|
43
|
+
file.puts('test')
|
44
|
+
file.close
|
45
|
+
|
46
|
+
expect { @obj.get_tags_for(file.path) }.to_not raise_error
|
47
|
+
file.unlink
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
it 'should call get for other extensions' do
|
52
|
+
CANNOT_TEST.each do |ext|
|
53
|
+
path = copy_example "#{ext[1..-1]}_with_tag#{ext}"
|
54
|
+
expect { @obj.clear_tags_for(path) }.to_not raise_error
|
55
|
+
File.unlink(path)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
it 'should call set/unset for every good extension' do
|
60
|
+
(@obj.available_tagging_extensions - CANNOT_TEST).each do |ext|
|
61
|
+
file = Tempfile.new_with_encoding(['ext', ext])
|
62
|
+
file.puts('test')
|
63
|
+
file.close
|
64
|
+
|
65
|
+
expect {
|
66
|
+
@obj.set_tag_for(file.path, 'test')
|
67
|
+
@obj.unset_tag_for(file.path, 'test')
|
68
|
+
}.to_not raise_error
|
69
|
+
file.unlink
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
it 'should call set/unset for other extensions' do
|
74
|
+
CANNOT_TEST.each do |ext|
|
75
|
+
path = copy_example "#{ext[1..-1]}_with_tag#{ext}"
|
76
|
+
expect {
|
77
|
+
@obj.set_tag_for(path, 'test2')
|
78
|
+
@obj.unset_tag_for(path, 'test2')
|
79
|
+
}.to_not raise_error
|
80
|
+
File.unlink(path)
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
84
|
+
it 'should call clear for every good extension' do
|
85
|
+
(@obj.available_tagging_extensions - CANNOT_TEST).each do |ext|
|
86
|
+
file = Tempfile.new_with_encoding(['ext', ext])
|
87
|
+
file.puts('test')
|
88
|
+
file.close
|
89
|
+
|
90
|
+
expect { @obj.clear_tags_for(file.path) }.to_not raise_error
|
91
|
+
file.unlink
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
it 'should call clear for other extensions' do
|
96
|
+
CANNOT_TEST.each do |ext|
|
97
|
+
path = copy_example "#{ext[1..-1]}_with_tag#{ext}"
|
98
|
+
expect { @obj.clear_tags_for(path) }.to_not raise_error
|
99
|
+
File.unlink(path)
|
100
|
+
end
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
104
|
+
describe '.get_tags_for' do
|
105
|
+
it 'should delegate to PDF' do
|
106
|
+
path = example_path('pdf_no_tags.pdf')
|
107
|
+
|
108
|
+
StickyFlag::Tags::PDF.should_receive(:get).with(path, kind_of(String))
|
109
|
+
@obj.get_tags_for(path)
|
110
|
+
end
|
111
|
+
|
112
|
+
it 'should raise error for unknown extensions' do
|
113
|
+
expect {
|
114
|
+
@obj.get_tags_for('asdf.zzy')
|
115
|
+
}.to raise_error(Thor::Error)
|
116
|
+
end
|
117
|
+
end
|
118
|
+
|
119
|
+
describe '.set_tag_for' do
|
120
|
+
it 'should delegate to PDF' do
|
121
|
+
path = example_path('pdf_no_tags.pdf')
|
122
|
+
|
123
|
+
StickyFlag::Tags::PDF.should_receive(:set).with(path, 'lol', kind_of(String))
|
124
|
+
@obj.set_tag_for(path, 'lol')
|
125
|
+
end
|
126
|
+
|
127
|
+
it 'should not call through if the tag is already set' do
|
128
|
+
path = example_path('pdf_with_tag.pdf')
|
129
|
+
|
130
|
+
StickyFlag::Tags::PDF.should_not_receive(:set)
|
131
|
+
@obj.set_tag_for(path, 'test')
|
132
|
+
end
|
133
|
+
|
134
|
+
it 'should raise error for unknown extensions' do
|
135
|
+
@obj.stub(:get_tags_for) { [] }
|
136
|
+
expect {
|
137
|
+
@obj.set_tag_for('asdf.zzy', 'lol')
|
138
|
+
}.to raise_error(Thor::Error)
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
describe '.unset_tag_for' do
|
143
|
+
it 'should delegate to PDF' do
|
144
|
+
path = copy_example('pdf_with_tag.pdf')
|
145
|
+
|
146
|
+
StickyFlag::Tags::PDF.should_receive(:unset).with(path, 'test', kind_of(String))
|
147
|
+
@obj.unset_tag_for(path, 'test')
|
148
|
+
|
149
|
+
File.delete(path)
|
150
|
+
end
|
151
|
+
|
152
|
+
it 'should not call through if the tag is not set' do
|
153
|
+
path = example_path('pdf_no_tags.pdf')
|
154
|
+
|
155
|
+
StickyFlag::Tags::PDF.should_not_receive(:unset)
|
156
|
+
expect {
|
157
|
+
@obj.unset_tag_for(path, 'test')
|
158
|
+
}.to raise_error(Thor::Error)
|
159
|
+
end
|
160
|
+
|
161
|
+
it 'should raise error for unknown extensions' do
|
162
|
+
@obj.stub(:get_tags_for) { [ 'lol' ] }
|
163
|
+
expect {
|
164
|
+
@obj.unset_tag_for('asdf.zzy', 'lol')
|
165
|
+
}.to raise_error(Thor::Error)
|
166
|
+
end
|
167
|
+
end
|
168
|
+
|
169
|
+
describe '.clear_tags_for' do
|
170
|
+
it 'should delegate to PDF' do
|
171
|
+
path = copy_example('pdf_with_tag.pdf')
|
172
|
+
|
173
|
+
StickyFlag::Tags::PDF.should_receive(:clear).with(path, kind_of(String))
|
174
|
+
@obj.clear_tags_for(path)
|
175
|
+
|
176
|
+
File.delete(path)
|
177
|
+
end
|
178
|
+
|
179
|
+
it 'should raise error for unknown extensions' do
|
180
|
+
expect {
|
181
|
+
@obj.clear_tags_for('asdf.zzy')
|
182
|
+
}.to raise_error(Thor::Error)
|
183
|
+
end
|
184
|
+
end
|
185
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
# -*- encoding : utf-8 -*-
|
2
|
+
require 'stickyflag/tags/c'
|
3
|
+
|
4
|
+
describe StickyFlag::Tags::C do
|
5
|
+
it_behaves_like 'a tag handler'
|
6
|
+
|
7
|
+
it 'can open a file with all comments and no tags' do
|
8
|
+
ret = nil
|
9
|
+
expect {
|
10
|
+
ret = StickyFlag::Tags::C.get(example_path('c_all_comments.c'))
|
11
|
+
}.to_not raise_error
|
12
|
+
ret.should be_empty
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
# -*- encoding : utf-8 -*-
|
2
|
+
require 'stickyflag/tags/mmd'
|
3
|
+
|
4
|
+
describe StickyFlag::Tags::MMD do
|
5
|
+
it_behaves_like 'a tag handler'
|
6
|
+
|
7
|
+
it 'handles multiline metadata documents' do
|
8
|
+
StickyFlag::Tags::MMD.get(example_path('mmd_crazy_keys.mmd')).should include('test')
|
9
|
+
end
|
10
|
+
|
11
|
+
it 'handles multiline tag documents' do
|
12
|
+
StickyFlag::Tags::MMD.get(example_path('mmd_crazy_tags.mmd')).should include('sdfg')
|
13
|
+
end
|
14
|
+
|
15
|
+
it 'handles all-metadata documents' do
|
16
|
+
StickyFlag::Tags::MMD.get(example_path('mmd_all_meta.mmd')).should be_empty
|
17
|
+
end
|
18
|
+
|
19
|
+
it 'can edit multiline metadata documents' do
|
20
|
+
path = copy_example('mmd_crazy_keys.mmd')
|
21
|
+
|
22
|
+
StickyFlag::Tags::MMD.set(path, 'test2')
|
23
|
+
StickyFlag::Tags::MMD.get(path).should include('test2')
|
24
|
+
|
25
|
+
File.open(path, 'r:UTF-8').each_line.to_a.should include("Tags: test, test2 \n")
|
26
|
+
|
27
|
+
File.delete path
|
28
|
+
end
|
29
|
+
|
30
|
+
it 'can edit multiline tag documents' do
|
31
|
+
path = copy_example('mmd_crazy_tags.mmd')
|
32
|
+
|
33
|
+
StickyFlag::Tags::MMD.set(path, 'test2')
|
34
|
+
StickyFlag::Tags::MMD.get(path).should include('test2')
|
35
|
+
|
36
|
+
File.open(path, 'r:UTF-8').each_line.to_a.should include("Tags: asdf, sdfg, dfgh, fghj, qwer, test2 \n")
|
37
|
+
|
38
|
+
File.delete path
|
39
|
+
end
|
40
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
# -*- encoding : utf-8 -*-
|
2
|
+
require 'stickyflag/tags/pdf'
|
3
|
+
require 'stickyflag/paths'
|
4
|
+
require 'stickyflag/configuration'
|
5
|
+
require 'stickyflag/external_cmds'
|
6
|
+
|
7
|
+
class GetConfiguration
|
8
|
+
include StickyFlag::Paths
|
9
|
+
include StickyFlag::Configuration
|
10
|
+
include StickyFlag::ExternalCmds
|
11
|
+
end
|
12
|
+
|
13
|
+
describe StickyFlag::Tags::PDF do
|
14
|
+
it_behaves_like 'a tag handler' do
|
15
|
+
let(:params) {
|
16
|
+
config = GetConfiguration.new
|
17
|
+
config.stub(:load_config!) { }
|
18
|
+
config.stub(:save_config!) { }
|
19
|
+
|
20
|
+
config.find_external_cmds
|
21
|
+
|
22
|
+
[ config.get_config(:pdftk_path) ]
|
23
|
+
}
|
24
|
+
end
|
25
|
+
|
26
|
+
context 'with a bad pdftk path' do
|
27
|
+
it 'raises errors for everything' do
|
28
|
+
expect { StickyFlag::Tags::PDF.get(example_path("pdf_with_tag.pdf"), '/wut/bad') }.to raise_error(Thor::Error)
|
29
|
+
expect { StickyFlag::Tags::PDF.clear(example_path("pdf_with_tag.pdf"), '/wut/bad') }.to raise_error(Thor::Error)
|
30
|
+
|
31
|
+
# If get doesn't succeed, we won't get all the way into set or unset
|
32
|
+
# with the bad pdftk path.
|
33
|
+
StickyFlag::Tags::PDF.stub(:get) { [ 'test' ] }
|
34
|
+
expect { StickyFlag::Tags::PDF.set(example_path("pdf_with_tag.pdf"), 'test2', '/wut/bad') }.to raise_error(Thor::Error)
|
35
|
+
expect { StickyFlag::Tags::PDF.unset(example_path("pdf_with_tag.pdf"), 'test', '/wut/bad') }.to raise_error(Thor::Error)
|
36
|
+
StickyFlag::Tags::PDF.unstub(:get)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|