pdfmd 1.9.1 → 2.0.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +22 -2
- data/README.md +2 -2
- data/TODO.mkd +26 -0
- data/bin/pdfmd +267 -1
- data/lib/pdfmd.rb +242 -634
- data/lib/pdfmd/explain.hiera.md +25 -4
- data/lib/pdfmd/long_desc.pdfmdconfig.txt +40 -0
- data/lib/pdfmd/long_desc.pdfmdedit.txt +166 -0
- data/lib/pdfmd/long_desc.pdfmdexplain.txt +16 -0
- data/lib/pdfmd/long_desc.pdfmdrename.txt +206 -0
- data/lib/pdfmd/long_desc.pdfmdshow.txt +92 -0
- data/lib/pdfmd/long_desc.pdfmdsort.txt +111 -0
- data/lib/pdfmd/long_desc.pdfmdstat.txt +23 -0
- data/lib/pdfmd/pdfmdconfig.rb +30 -0
- data/lib/pdfmd/pdfmdedit.rb +201 -0
- data/lib/pdfmd/pdfmdmethods.rb +125 -0
- data/lib/pdfmd/pdfmdrename.rb +243 -0
- data/lib/pdfmd/pdfmdshow.rb +88 -0
- data/lib/pdfmd/pdfmdsort.rb +115 -0
- data/lib/pdfmd/pdfmdstat.rb +117 -0
- data/lib/{string_extend.rb → pdfmd/string_extend.rb} +0 -0
- data/lib/run.rb +235 -0
- data/pdfmd.gemspec +3 -2
- metadata +23 -11
- data/lib/pdfmd/check.rb +0 -10
- data/lib/pdfmd/config.rb +0 -59
- data/lib/pdfmd/edit.rb +0 -144
- data/lib/pdfmd/rename.rb +0 -295
- data/lib/pdfmd/show.rb +0 -164
- data/lib/pdfmd/sort.rb +0 -199
data/lib/pdfmd/show.rb
DELETED
@@ -1,164 +0,0 @@
|
|
1
|
-
#
|
2
|
-
# Show function of pdfmd
|
3
|
-
#
|
4
|
-
filename = ENV.fetch('PDFMD_FILENAME')
|
5
|
-
optTag = ENV['PDFMD_TAGS'] || nil
|
6
|
-
optAll = ENV['PDFMD_ALL'] == 'true' ? true : nil
|
7
|
-
opt_format = ENV['PDFMD_FORMAT']
|
8
|
-
opt_includepdf = ENV['PDFMD_INCLUDEPDF']
|
9
|
-
hieraDefaults = queryHiera('pdfmd::config')
|
10
|
-
|
11
|
-
# Determine includepdf from Hiera if possible
|
12
|
-
if not opt_includepdf.nil? and
|
13
|
-
opt_includepdf == 'true'
|
14
|
-
|
15
|
-
opt_includepdf = true
|
16
|
-
|
17
|
-
elsif opt_includepdf.nil? and
|
18
|
-
not hieraDefaults['show'].nil? and
|
19
|
-
not hieraDefaults['show']['includepdf'].nil? and
|
20
|
-
hieraDefaults['show']['includepdf'] == true
|
21
|
-
|
22
|
-
opt_includepdf = true
|
23
|
-
|
24
|
-
else
|
25
|
-
|
26
|
-
opt_includepdf = false
|
27
|
-
|
28
|
-
end
|
29
|
-
|
30
|
-
# Determine format from Hiera if possible
|
31
|
-
if opt_format.nil? and
|
32
|
-
!hieraDefaults.nil? and
|
33
|
-
not hieraDefaults['show'].nil? and
|
34
|
-
not hieraDefaults['show']['format'].nil? and
|
35
|
-
hieraDefaults['show']['format'] != ''
|
36
|
-
|
37
|
-
opt_format = hieraDefaults['show']['format']
|
38
|
-
|
39
|
-
end
|
40
|
-
|
41
|
-
|
42
|
-
# Determine tags from Hiera if possible
|
43
|
-
if optTag.nil? and
|
44
|
-
!hieraDefaults.nil? and
|
45
|
-
!hieraDefaults['show'].nil? and
|
46
|
-
!hieraDefaults['show']['tag'].nil? and
|
47
|
-
hieraDefaults['show']['tag'] != ''
|
48
|
-
|
49
|
-
optTag = hieraDefaults['show']['tag']
|
50
|
-
|
51
|
-
end
|
52
|
-
|
53
|
-
metadata = readMetadata(filename)
|
54
|
-
|
55
|
-
if optAll or optTag.nil?
|
56
|
-
|
57
|
-
# Sort the keys in the hash in a specific order, so it becomes predictable
|
58
|
-
sortedHash = Hash.new
|
59
|
-
sortedHash['author'] = metadata['author']
|
60
|
-
sortedHash['creator'] = metadata['creator']
|
61
|
-
sortedHash['createdate'] = metadata['createdate']
|
62
|
-
sortedHash['title'] = metadata['title']
|
63
|
-
sortedHash['subject'] = metadata['subject']
|
64
|
-
sortedHash['keywords'] = metadata['keywords']
|
65
|
-
metadata = sortedHash
|
66
|
-
|
67
|
-
tags = metadata.keys.join(',').split(',')
|
68
|
-
else
|
69
|
-
tags = optTag.split(',')
|
70
|
-
end
|
71
|
-
|
72
|
-
# Format the output according to the spefications.
|
73
|
-
# Default output is for Human readable
|
74
|
-
#
|
75
|
-
case opt_format
|
76
|
-
when /yaml/i
|
77
|
-
|
78
|
-
# Format the output as YAML
|
79
|
-
|
80
|
-
require 'yaml'
|
81
|
-
yamlData = Hash.new
|
82
|
-
tags.each do |tagname|
|
83
|
-
yamlData[tagname] = metadata[tagname.downcase]
|
84
|
-
end
|
85
|
-
|
86
|
-
# Include the filename if required
|
87
|
-
if opt_includepdf
|
88
|
-
fullHash = Hash.new
|
89
|
-
fullHash[filename] = yamlData
|
90
|
-
puts fullHash.to_yaml
|
91
|
-
else
|
92
|
-
puts yamlData.to_yaml
|
93
|
-
end
|
94
|
-
|
95
|
-
when /hash/i
|
96
|
-
|
97
|
-
# Format the output as Ruby Hash
|
98
|
-
|
99
|
-
hashData = Hash.new
|
100
|
-
tags.each do |tagname|
|
101
|
-
hashData[tagname] = metadata[tagname.downcase]
|
102
|
-
end
|
103
|
-
|
104
|
-
# Include filename if required
|
105
|
-
if opt_includepdf
|
106
|
-
fullHash = Hash.new
|
107
|
-
fullHash[filename] = hashData
|
108
|
-
puts fullHash
|
109
|
-
else
|
110
|
-
puts hashData
|
111
|
-
end
|
112
|
-
|
113
|
-
when /csv/i
|
114
|
-
|
115
|
-
# Format the output as CSV data (or what could be interpreted as something
|
116
|
-
# similar
|
117
|
-
|
118
|
-
# Format the fields as CSV
|
119
|
-
csvData = Hash.new
|
120
|
-
tags.each do |tagname|
|
121
|
-
csvData[tagname] = '"' + metadata[tagname.downcase].to_s.gsub(/"/,'""') + '"'
|
122
|
-
end
|
123
|
-
|
124
|
-
# Include the filename if required
|
125
|
-
if opt_includepdf
|
126
|
-
# Hash to array and joined to CSV compatible string
|
127
|
-
puts "\"#{filename}\"," + csvData.values.join(',')
|
128
|
-
else
|
129
|
-
# Hash to array and joined to CSV compatible string
|
130
|
-
puts csvData.values.join(',')
|
131
|
-
end
|
132
|
-
|
133
|
-
|
134
|
-
when /json/i
|
135
|
-
|
136
|
-
# Format the output as JSON
|
137
|
-
|
138
|
-
require 'json'
|
139
|
-
jsonData = Hash.new
|
140
|
-
tags.each do |tagname|
|
141
|
-
jsonData[tagname] = metadata[tagname.downcase]
|
142
|
-
end
|
143
|
-
|
144
|
-
# Include the filename if required
|
145
|
-
if opt_includepdf
|
146
|
-
fullHash = Hash.new
|
147
|
-
fullHash[filename] = jsonData
|
148
|
-
puts fullHash.to_json
|
149
|
-
else
|
150
|
-
puts jsonData.to_json
|
151
|
-
end
|
152
|
-
|
153
|
-
else
|
154
|
-
|
155
|
-
# Default output for humans to read
|
156
|
-
if opt_includepdf
|
157
|
-
puts 'File: ' + filename
|
158
|
-
end
|
159
|
-
tags.each do |key,tag|
|
160
|
-
puts key.capitalize + ': ' + metadata[key.downcase]
|
161
|
-
end
|
162
|
-
|
163
|
-
end
|
164
|
-
|
data/lib/pdfmd/sort.rb
DELETED
@@ -1,199 +0,0 @@
|
|
1
|
-
#
|
2
|
-
# == File: sort.rb
|
3
|
-
#
|
4
|
-
# Actions for the sort command
|
5
|
-
#
|
6
|
-
# TODO: Put in file overwrite parameter
|
7
|
-
#
|
8
|
-
inputDir = ENV.fetch('PDFMD_INPUTDIR')
|
9
|
-
|
10
|
-
require_relative('./methods.rb')
|
11
|
-
require_relative '../string_extend.rb'
|
12
|
-
require 'fileutils'
|
13
|
-
|
14
|
-
opt_destination = ENV.fetch('PDFMD_DESTINATION')
|
15
|
-
opt_dryrun = ENV.fetch('PDFMD_DRYRUN') == 'true' ? true : false
|
16
|
-
opt_copy = ENV.fetch('PDFMD_COPY')
|
17
|
-
opt_log = ENV.fetch('PDFMD_LOG')
|
18
|
-
opt_logfilepath = ENV.fetch('PDFMD_LOGFILEPATH')
|
19
|
-
opt_interactive = ENV.fetch('PDFMD_INTERACTIVE')
|
20
|
-
hieraDefaults = queryHiera('pdfmd::config')
|
21
|
-
|
22
|
-
# Determin the setting for the copy/move action when sorting
|
23
|
-
# Use HieraDefaults if nothing has been set.
|
24
|
-
copyAction = opt_copy
|
25
|
-
if copyAction.blank? and
|
26
|
-
!hieraDefaults.nil? and
|
27
|
-
!hieraDefaults['sort'].nil? and
|
28
|
-
!hieraDefaults['sort']['copy'].nil? and
|
29
|
-
hieraDefaults['sort']['copy'] == true
|
30
|
-
copyAction = true
|
31
|
-
elsif copyAction.blank? or copyAction == 'false'
|
32
|
-
copyAction = false
|
33
|
-
end
|
34
|
-
|
35
|
-
# Determine the setting for interaction
|
36
|
-
if opt_interactive.blank? and
|
37
|
-
!hieraDefaults.nil? and
|
38
|
-
!hieraDefaults['sort'].nil? and
|
39
|
-
!hieraDefaults['sort']['interactive'].nil? and
|
40
|
-
hieraDefaults['sort']['interactive'] == true
|
41
|
-
puts 'Setting interactive from hiera'
|
42
|
-
interactiveAction = true
|
43
|
-
elsif opt_interactive == 'true'
|
44
|
-
interactiveAction = true
|
45
|
-
elsif opt_interactive.blank? or opt_interactive == 'false'
|
46
|
-
interactiveAction = false
|
47
|
-
end
|
48
|
-
|
49
|
-
# Fetch alternate destination from hiera if available
|
50
|
-
destination = opt_destination
|
51
|
-
if destination.nil? or destination == ''
|
52
|
-
|
53
|
-
hieraHash = queryHiera('pdfmd::config')
|
54
|
-
if !hieraHash.nil? and
|
55
|
-
!hieraHash['sort'].nil? and
|
56
|
-
!hieraHash['sort']['destination'].nil?
|
57
|
-
destination = hieraHash['sort']['destination']
|
58
|
-
else
|
59
|
-
puts 'No information about destination found.'
|
60
|
-
puts 'Set parameter -d or configure hiera.'
|
61
|
-
puts 'Abort.'
|
62
|
-
exit 1
|
63
|
-
end
|
64
|
-
end
|
65
|
-
|
66
|
-
# Determine the state of the logging
|
67
|
-
if (opt_log.blank? and
|
68
|
-
!hieraDefaults.nil? and
|
69
|
-
!hieraDefaults['sort'].nil? and
|
70
|
-
!hieraDefaults['sort']['log'].nil? and
|
71
|
-
hieraDefaults['sort']['log'] == true) or
|
72
|
-
opt_log == 'true'
|
73
|
-
logenable = true
|
74
|
-
elsif opt_log.blank? or opt_log == 'false'
|
75
|
-
logenable = false
|
76
|
-
end
|
77
|
-
|
78
|
-
if logenable
|
79
|
-
|
80
|
-
if opt_logfilepath.blank? and
|
81
|
-
( hieraDefaults['sort']['logfile'].nil? or
|
82
|
-
hieraDefaults['sort']['logfile'].blank? or
|
83
|
-
hieraDefaults['sort'].nil? )
|
84
|
-
|
85
|
-
logfile = Dir.pwd.chomp('/') + '/' + File.basename(ENV['PDFMD'], '.*') + '.log'
|
86
|
-
|
87
|
-
elsif not opt_logfilepath.blank?
|
88
|
-
|
89
|
-
if File.directory? opt_logfilepath
|
90
|
-
abort('Logfilepath is a directory. Abort.')
|
91
|
-
exit 1
|
92
|
-
end
|
93
|
-
|
94
|
-
logfile = opt_logfilepath
|
95
|
-
|
96
|
-
elsif opt_logfilepath.blank? and
|
97
|
-
not hieraDefaults['sort']['logfile'].blank?
|
98
|
-
|
99
|
-
logfile = hieraDefaults['sort']['logfile']
|
100
|
-
|
101
|
-
else
|
102
|
-
|
103
|
-
logfile = Dir.pwd.chomp('/') + '/' + File.basename(ENV['PDFMD'], '.*') + '.log'
|
104
|
-
|
105
|
-
end
|
106
|
-
|
107
|
-
$logger = Logger.new(logfile)
|
108
|
-
end
|
109
|
-
|
110
|
-
# Create array of Files to iterate through
|
111
|
-
pdfDocuments = File.directory?(inputDir) ? Dir[inputDir.chomp('/') + '/*.pdf'].sort : inputDir.split
|
112
|
-
|
113
|
-
|
114
|
-
# Input validation
|
115
|
-
!File.exist?(inputDir) ? abort('Input does not exist. Abort.'): ''
|
116
|
-
File.file?(destination) ? abort("Output '#{destination}' is an existing file. Cannot create directory with the same name. Abort") : ''
|
117
|
-
|
118
|
-
if not File.directory?(destination)
|
119
|
-
|
120
|
-
# Do nothing on a dry-run
|
121
|
-
if opt_dryrun
|
122
|
-
logenable ? $logger.info("Dryrun: Destination '#{destination}' has been created.") : ''
|
123
|
-
else
|
124
|
-
FileUtils.mkdir_p(destination)
|
125
|
-
logenable ? $logger.info("Destination '#{destination}' has been created.") : ''
|
126
|
-
end
|
127
|
-
|
128
|
-
end
|
129
|
-
|
130
|
-
# Iterate through all files
|
131
|
-
pdfDocuments.each do |file|
|
132
|
-
|
133
|
-
if interactiveAction
|
134
|
-
answer = readUserInput("Process '#{file}' ([y]/n): ")
|
135
|
-
answer = answer.empty? ? 'y' : answer
|
136
|
-
logenable ? $logger.info("Interactive answer for file '#{file}' : #{answer}") : ''
|
137
|
-
answer.match(/y/) ? '' : next
|
138
|
-
end
|
139
|
-
|
140
|
-
metadata = readMetadata(file)
|
141
|
-
|
142
|
-
# The author information is used to create a subdirectory
|
143
|
-
# where all the files will end up in.
|
144
|
-
if metadata['author'] and not metadata['author'].empty?
|
145
|
-
author = metadata['author'].gsub(' ','_').gsub('.','_').gsub('&','').gsub('__','_')
|
146
|
-
I18n.enforce_available_locales = false # Serialize special characters
|
147
|
-
author = I18n.transliterate(author).downcase
|
148
|
-
folderdestination = destination.chomp('/') + '/' + author
|
149
|
-
|
150
|
-
if not File.directory?(folderdestination)
|
151
|
-
|
152
|
-
# Do nothing when it's a dry-run
|
153
|
-
if opt_dryrun
|
154
|
-
logenable ? $logger.info("Dryrun: Folder '#{folderdestination}' has been created."): ''
|
155
|
-
else
|
156
|
-
FileUtils.mkdir_p(folderdestination)
|
157
|
-
logenable ? $logger.info("Folder '#{folderdestination}' has been created."): ''
|
158
|
-
end
|
159
|
-
|
160
|
-
end
|
161
|
-
|
162
|
-
filedestination = destination.chomp('/') + '/' + author + '/' + Pathname.new(file).basename.to_s
|
163
|
-
|
164
|
-
puts filedestination
|
165
|
-
|
166
|
-
|
167
|
-
# Final check before touching the filesystem
|
168
|
-
if not File.exist?(filedestination)
|
169
|
-
|
170
|
-
# Move/Copy the file
|
171
|
-
if copyAction
|
172
|
-
if opt_dryrun
|
173
|
-
logenable ? $logger.info("Dryrun: File copied '#{file}' => '#{filedestination}'") : ''
|
174
|
-
else
|
175
|
-
FileUtils.cp(file, filedestination)
|
176
|
-
logenable ? $logger.info("File copied '#{file}' => '#{filedestination}'") : ''
|
177
|
-
end
|
178
|
-
|
179
|
-
else
|
180
|
-
|
181
|
-
if opt_dryrun
|
182
|
-
logenable ? $logger.info("Dryrun: File moved '#{file}' => '#{filedestination}'") : ''
|
183
|
-
else
|
184
|
-
FileUtils.mv(file,filedestination)
|
185
|
-
logenable ? $logger.info("File moved '#{file}' => '#{filedestination}'") : ''
|
186
|
-
end
|
187
|
-
|
188
|
-
end
|
189
|
-
|
190
|
-
else
|
191
|
-
|
192
|
-
logenable ? $logger.warn("File '#{filedestination}' already exists. Ignoring.") : ''
|
193
|
-
|
194
|
-
end
|
195
|
-
else
|
196
|
-
logenable ? $logger.warn("Missing tag 'Author' for file '#{file}'. Skipping.") : (puts "Missing tag 'Author' for file '#{file}'. Skipping")
|
197
|
-
next
|
198
|
-
end
|
199
|
-
end
|