jasper-command-line 0.4.0 → 0.4.1

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/Gemfile CHANGED
@@ -1,7 +1,4 @@
1
- source :rubygems
1
+ source 'http://production.cf.rubygems.org'
2
+ # source :rubygems
2
3
 
3
- gemspec
4
-
5
- gem 'activesupport', '>= 3.2.0'
6
- gem 'rjb', '1.4.3'
7
- gem 'builder', '>= 3.0.3'
4
+ gemspec
data/README.md CHANGED
@@ -3,12 +3,18 @@ jasper-command-line
3
3
 
4
4
  Print a jasper document via the command line
5
5
 
6
- **Disclaimer**: This is almost completely based on the great work by [Fortes Informática](https://github.com/fortesinformatica), with the gem [jasper-rails](https://github.com/fortesinformatica/jasper-rails). I built this out of necessity for a project that wouldn't run [jasper-rails](https://github.com/fortesinformatica/jasper-rails) on top of Ubuntu + nginx + Passenger.
6
+ ### Disclaimer:
7
+ This is almost completely based on the great work by [Fortes Informática](https://github.com/fortesinformatica), with the gem [jasper-rails](https://github.com/fortesinformatica/jasper-rails). I built this out of necessity for a project that wouldn't run [jasper-rails](https://github.com/fortesinformatica/jasper-rails) on top of Ubuntu + nginx + Passenger.
7
8
 
8
9
  This gem embeds the .jar files provided by [jasper-rails](https://github.com/fortesinformatica/jasper-rails), so you don't need to include the gem ([jasper-rails](https://github.com/fortesinformatica/jasper-rails) requires the whole Ruby on Rails framework, which isn't necessary in this case).
9
10
 
10
11
  It also embeds the .jar files needed to digitally sign the PDF, if necessary. The PDF files are signed using [PortableSigner](http://portablesigner.sourceforge.net) by [Peter Pfläging](peter.pflaeging@wien.gv.at). All credit for the digital signature code goes to him.
11
12
 
13
+ ### Other acknowledgements:
14
+
15
+ * [Prawn](http://prawn.majesticseacreature.com), a "Fast, Nimble PDF Writer for Ruby"
16
+ * [Henrik Nyh](http://henrik.nyh.se/) for the auto-print addition to Prawn, [prawn-print](https://github.com/barsoom/prawn-print).
17
+
12
18
  ## Dependencies
13
19
 
14
20
  * You need a Java Virtual Machine installed and set up in order to use this gem.
@@ -34,24 +40,28 @@ gem "jasper-command-line"
34
40
  ## Using jasper-command-line
35
41
 
36
42
  ```
37
- jasper-command-line [options]
43
+ Usage: jasper-command-line [options]
38
44
 
39
45
  Options:
40
- --jasper /path/to/file The .jasper file to load (if one doesn't exist, it is
41
- compiled from the .jrxml file with the same name and
42
- on the same location)
43
- --data-file /path/to/file The .xml file to load the data from
44
- --copies number The number of copies to generate
45
- --locale locale The locale to use in the report (in the format xx-YY)
46
- --param key=value Adds the parameter with name key with the value value
47
- (can be defined multiple times)
46
+ -j, --jasper file The .jasper file to load (if one doesn't exist, it is compiled from the .jrxml file with the same name and on the same location)
47
+ -d, --data-file file The .xml file to load the data from
48
+ -c, --copies number The number of copies to generate
49
+ -l, --locale locale The locale to use in the report (in the format xx-YY)
50
+ --param name=value Adds the parameter with name key with the value value (can be defined multiple times)
51
+
52
+ Printing options:
53
+ -p, --print Whether to generate a PDF file that automatically opens the print dialog when opened in Acrobat Reader
54
+ -P, --print-silent Whether to generate a PDF file that automatically prints to the default printer when opened in Acrobat Reader
48
55
 
49
56
  Digital signature options:
50
- --sign-key-file /path/to/file The location of the PKCS12 file to
51
- digitally sign the PDF with
52
- --sign-password password The password for the PKCS12 file
53
- --sign-location location The location of the signature
54
- --sign-reason reason The reason for signing the PDF
57
+ --sign-key-file file The location of the PKCS12 file to digitally sign the PDF with
58
+ --sign-location location The location data for the signature
59
+ --sign-password password The password for the PKCS12 file
60
+ --sign-reason reason The reason for signing the PDF
61
+
62
+ Common options:
63
+ -h, --help Show this message
64
+ --version Show version
55
65
  ```
56
66
 
57
67
  ## LICENSE
@@ -13,14 +13,16 @@ Gem::Specification.new do |s|
13
13
  s.summary = "Use jasper-rails from the command line."
14
14
  s.description = "Use jasper-rails from the command line."
15
15
 
16
- s.add_dependency('rjb', '1.4.3')
17
- s.add_dependency('builder', '>= 3.0.2')
18
- s.add_dependency('activesupport', '>= 3.2.0')
19
- s.add_development_dependency("rspec", "~> 2.7")
20
- s.add_development_dependency("rake", "~> 0.9.2")
16
+ s.add_dependency 'rjb', '1.4.3'
17
+ s.add_dependency 'builder', '>= 3.0.3'
18
+ s.add_dependency 'activesupport', '>= 3.2.0'
19
+ s.add_dependency 'prawn', '>= 0.12.0'
20
+
21
+ s.add_development_dependency "rspec", "~> 2.7"
22
+ s.add_development_dependency "rake", "~> 0.9.2"
21
23
 
22
24
  s.files = `git ls-files`.split("\n")
23
25
  s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
24
26
  s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
25
27
  s.require_paths = ["lib"]
26
- end
28
+ end
@@ -7,6 +7,8 @@ require 'tempfile'
7
7
  require 'jasper-command-line/version'
8
8
  require 'jasper-command-line/command_line'
9
9
  require 'jasper-command-line/jasper'
10
+ require 'prawn'
11
+ require 'jasper-command-line/prawn-js'
10
12
 
11
13
  module JasperCommandLine
12
14
  def self.logger=(log)
@@ -4,141 +4,135 @@ module JasperCommandLine
4
4
  begin
5
5
  options = parse_arguments(args)
6
6
 
7
- if !options
8
- puts "Usage:"
9
- puts ""
10
- puts "jasper-command-line [options]"
11
- puts ""
12
- puts "Options:"
13
- puts ""
14
- puts "--jasper /path/to/file The .jasper file to load (if one doesn't exist, it is"
15
- puts " compiled from the .jrxml file with the same name and"
16
- puts " on the same location)"
17
- puts "--data-file /path/to/file The .xml file to load the data from"
18
- puts "--copies number The number of copies to generate"
19
- puts "--locale locale The locale to use in the report (in the format xx-YY)"
20
- puts "--param key=value Adds the parameter with name key with the value value"
21
- puts " (can be defined multiple times)"
22
- puts ""
23
- puts "Digital signature options:"
24
- puts "--sign-key-file /path/to/file The location of the PKCS12 file to"
25
- puts " digitally sign the PDF with"
26
- puts "--sign-password password The password for the PKCS12 file"
27
- puts "--sign-location location The location of the signature"
28
- puts "--sign-reason reason The reason for signing the PDF"
29
- else
30
- if options[:jasper_file]
31
- jasper_file = options.delete :jasper_file
32
- data = options.delete :data
33
- params = options.delete :params
34
-
35
- if options[:signature]
36
- if options[:signature][:key_file] && !options[:signature][:password]
37
- raise ArgumentError.new("Password not supplied for certificate")
38
- end
7
+ if options[:jasper_file]
8
+ jasper_file = options.delete :jasper_file
9
+ data = options.delete :data
10
+ params = options.delete :params
11
+
12
+ if options[:signature]
13
+ if options[:signature][:key_file] && !options[:signature][:password]
14
+ raise ArgumentError.new("Password not supplied for certificate")
39
15
  end
40
-
41
- puts JasperCommandLine::Jasper::render_pdf(jasper_file, data, params, options)
42
16
  end
17
+
18
+ puts JasperCommandLine::Jasper::render_pdf(jasper_file, data, params, options)
43
19
  end
44
- rescue ArgumentError => e
20
+
21
+ exit 0
22
+ rescue OptionParser::InvalidOption => e
45
23
  puts "Error: #{e.message}"
24
+ exit 1
46
25
  rescue => e
47
26
  puts "Error: #{e.message}"
48
- puts e.backtrace
27
+ exit 2
49
28
  end
50
29
  end
51
30
 
52
31
  private
53
32
 
54
33
  def parse_arguments(arguments)
34
+ require 'optparse'
35
+ require 'optparse/time'
36
+ require 'ostruct'
37
+
55
38
  data = {
56
39
  :params => {}
57
40
  }
58
41
 
59
- return false unless arguments.any?
60
-
61
- i = 0
62
-
63
- while i < arguments.length
64
- argument = arguments[i]
65
-
66
- case get_option(argument)
67
- when 'data'
68
- i = get_option_data(arguments, i) do |argument_data|
69
- raise ArgumentError.new("Data not found") if get_option(argument_data)
70
- data[:data] = argument_data
71
- end
72
-
73
- when 'data-file'
74
- i = get_option_data(arguments, i) do |argument_data|
75
- raise ArgumentError.new("Data file not found: #{argument_data}") unless File.exists?(argument_data)
76
- data[:data] = File.read argument_data
77
- end
78
-
79
- when 'param'
80
- i = get_option_data(arguments, i) do |argument_data|
81
- raise ArgumentError.new("Invalid param format: #{argument_data}") unless argument_data =~ /(.*?)=(.*)/
82
- data[:params][$1] = $2
83
- end
84
-
85
- when 'jasper'
86
- i = get_option_data(arguments, i) do |argument_data|
87
- raise ArgumentError.new("File not found: #{argument_data}") unless File.exists?(argument_data) || File.exists?(argument_data.gsub(/\.jasper$/, '.jrxml'))
88
- data[:jasper_file] = argument_data
89
- end
90
-
91
- when 'copies'
92
- i = get_option_data(arguments, i) do |argument_data|
93
- raise ArgumentError.new("Invalid number of copies: #{argument_data}") unless argument_data =~ /^[1-9][0-9]*$/
94
- data[:copies] = argument_data.to_i
95
-
96
- raise ArgumentError.new("Ghostscript isn't available. Merging is not possible") if data[:copies] > 1 && !JasperCommandLine.ghostscript_available?
97
- end
98
-
99
- when 'locale'
100
- i = get_option_data(arguments, i) do |argument_data|
101
- raise ArgumentError.new("Invalid locale: #{argument_data}") unless argument_data =~ /^[a-z]{2}-[A-Za-z0-9]{2,3}$/
102
- data[:locale] = {
103
- :language => argument_data.strip.split('-').first,
104
- :sub_language => argument_data.strip.split('-').last
105
- }
106
- end
107
-
108
- when 'sign-key-file'
109
- # Sign document with file
110
- i = get_option_data(arguments, i) do |argument_data|
111
- raise ArgumentError.new("Signature key file not found: #{argument_data}") unless File.exists?(argument_data)
112
- data[:signature] ||= {}
113
- data[:signature][:key_file] = argument_data
114
- end
115
-
116
- when 'sign-location'
117
- # Location to set on the signature
118
- i = get_option_data(arguments, i) do |argument_data|
119
- data[:signature] ||= {}
120
- data[:signature][:location] = argument_data
121
- end
122
-
123
- when 'sign-password'
124
- # Password to open the signature key file
125
- i = get_option_data(arguments, i) do |argument_data|
126
- data[:signature] ||= {}
127
- data[:signature][:password] = argument_data
128
- end
129
-
130
- when 'sign-reason'
131
- # Reason to set on the signature
132
- i = get_option_data(arguments, i) do |argument_data|
133
- data[:signature] ||= {}
134
- data[:signature][:reason] = argument_data
135
- end
136
-
137
- else
138
- i += 1
139
- end
42
+ # Default to the help message
43
+ arguments << '--help' if arguments.empty?
44
+
45
+ opts = OptionParser.new do |opts|
46
+ opts.banner = "Usage: jasper-command-line [options]"
140
47
  end
141
48
 
49
+ opts.separator ""
50
+ opts.separator "Options:"
51
+
52
+ opts.on('-j', '--jasper file', "The .jasper file to load (if one doesn't exist, it is compiled from the .jrxml file with the same name and on the same location)") do |file|
53
+ raise ArgumentError.new("File not found: #{file}") unless File.exists?(file) || File.exists?(file.gsub(/\.jasper$/, '.jrxml'))
54
+ data[:jasper_file] = file
55
+ end
56
+
57
+ opts.on('-d', '--data-file file', "The .xml file to load the data from") do |file|
58
+ raise ArgumentError.new("Data file not found: #{file}") unless File.exists?(file)
59
+ data[:data] = File.read file
60
+ end
61
+
62
+ opts.on('-c', '--copies number', Integer, "The number of copies to generate") do |i|
63
+ data[:copies] = i
64
+ raise ArgumentError.new("Ghostscript isn't available. Merging is not possible") if data[:copies] > 1 && !JasperCommandLine.ghostscript_available?
65
+ end
66
+
67
+ opts.on('-l', '--locale locale', "The locale to use in the report (in the format xx-YY)") do |locale|
68
+ raise ArgumentError.new("Invalid locale format: #{locale}") unless locale =~ /([a-z]{2})-([A-Z]{2})/
69
+ data[:locale] = { language: $1, sub_language: $2 }
70
+ end
71
+
72
+ opts.on('--param name=value', "Adds the parameter with name key with the value value (can be defined multiple times)") do |parameter|
73
+ raise ArgumentError.new("Invalid param format: #{parameter}") unless parameter =~ /([^\s]+)=(.*)/
74
+ data[:params][$1] = $2
75
+ end
76
+
77
+ opts.separator ""
78
+ opts.separator "Printing options:"
79
+
80
+ opts.on('-p', '--print', "Whether to generate a PDF file that automatically opens the print dialog when opened in Acrobat Reader") do
81
+ raise ArgumentError.new("Can't supply both --print and --print-silent") if data[:print_silent]
82
+ data[:print] = true
83
+ end
84
+
85
+ opts.on('-P', '--print-silent', "Whether to generate a PDF file that automatically prints to the default printer when opened in Acrobat Reader") do
86
+ raise ArgumentError.new("Can't supply both --print and --print-silent") if data[:print]
87
+ data[:print_silent] = true
88
+ end
89
+
90
+ opts.separator ""
91
+ opts.separator "Digital signature options:"
92
+
93
+ opts.on('--sign-key-file file', "The location of the PKCS12 file to digitally sign the PDF with") do |file|
94
+ # Sign document with file
95
+ raise ArgumentError.new("Signature key file not found: #{file}") unless File.exists?(file)
96
+ data[:signature] ||= {}
97
+ data[:signature][:key_file] = file
98
+ end
99
+
100
+ opts.on('--sign-location location', "The location data for the signature") do |location|
101
+ # Location to set on the signature
102
+ data[:signature] ||= {}
103
+ data[:signature][:location] = location
104
+ end
105
+
106
+ opts.on('--sign-password password', "The password for the PKCS12 file") do |password|
107
+ # Password to open the signature key file
108
+ data[:signature] ||= {}
109
+ data[:signature][:password] = password
110
+ end
111
+
112
+ opts.on('--sign-reason reason', "The reason for signing the PDF") do |reason|
113
+ # Reason to set on the signature
114
+ data[:signature] ||= {}
115
+ data[:signature][:reason] = reason
116
+ end
117
+
118
+ opts.separator ""
119
+ opts.separator "Common options:"
120
+
121
+ # No argument, shows at tail. This will print an options summary.
122
+ # Try it and see!
123
+ opts.on_tail("-h", "--help", "Show this message") do
124
+ puts opts
125
+ exit
126
+ end
127
+
128
+ # Another typical switch to print the version.
129
+ opts.on_tail("--version", "Show version") do
130
+ puts JasperCommandLine::VERSION
131
+ exit
132
+ end
133
+
134
+ opts.parse! arguments
135
+
142
136
  return data
143
137
  end
144
138
 
@@ -20,8 +20,6 @@
20
20
  # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
21
  # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
22
  # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23
-
24
-
25
23
  module JasperCommandLine
26
24
  module Jasper
27
25
  def self.render_pdf(jasper_file, datasource, parameters, options)
@@ -95,6 +93,19 @@ module JasperCommandLine
95
93
  file = copy_file
96
94
  end
97
95
 
96
+ if options[:print] || options[:print_silent]
97
+ temp_file = Tempfile.new(['pdf-', '.pdf'])
98
+ file2 = temp_file.path
99
+ temp_file.close!
100
+
101
+ ::Prawn::Document.generate(file2, template: file) do |pdf|
102
+ pdf.print if options[:print]
103
+ pdf.print_silent if options[:print_silent]
104
+ end
105
+
106
+ file = file2
107
+ end
108
+
98
109
  # Digitally sign the file, if necessary
99
110
  if sign_options
100
111
  temp_signed_file = Tempfile.new(['signed-pdf-', '.pdf'])
@@ -0,0 +1,78 @@
1
+ # encoding: utf-8
2
+ #
3
+ # js.rb : Implements embeddable Javascript support for PDF
4
+ #
5
+ # Copyright March 2009, James Healy. All Rights Reserved.
6
+ #
7
+ # This is free software. Please see the LICENSE file for details.
8
+
9
+ module JasperCommandLine
10
+ module Prawn
11
+ module JS
12
+ # The maximum number of children to fit into a single node in the JavaScript tree.
13
+ NAME_TREE_CHILDREN_LIMIT = 20 #:nodoc:
14
+
15
+ # add a Javascript fragment that will execute when the document is opened.
16
+ #
17
+ # There can only be as many fragments as required. Calling this function
18
+ # multiple times will append the new fragment to the list.
19
+ #
20
+ def add_docopen_js(name, script)
21
+ obj = ref!(:S => :JavaScript, :JS => script)
22
+ javascript.data.add(name, obj)
23
+ end
24
+
25
+ def print
26
+ print_with_auto_to_printer false, nil
27
+ end
28
+
29
+ def print_silent
30
+ print_with_auto_to_printer true, nil
31
+ end
32
+
33
+ def print_with_auto_to_printer(auto, printer)
34
+ js = [
35
+ 'var pp = this.getPrintParams();',
36
+ interactive_js(auto),
37
+ select_printer_js(printer),
38
+ 'this.print(pp);'
39
+ ]
40
+
41
+ add_docopen_js "print", js.join(' ')
42
+ end
43
+
44
+ def interactive_js(auto)
45
+ "pp.interactive = pp.constants.interactionLevel.silent;" if auto
46
+ end
47
+
48
+ def select_printer_js(printer)
49
+ if printer
50
+ escaped_printer = printer.gsub('"') { "\\#$0" }
51
+
52
+ [
53
+ 'var names = app.printerNames;',
54
+ 'var regex = new RegExp("#{escaped_printer}", "i");',
55
+ 'for (var i = 0; i < names.length; i++) {',
56
+ 'if (names[i].match(regex)) {',
57
+ 'pp.printerName = names[i];',
58
+ 'break;',
59
+ '}',
60
+ '}'
61
+ ].join(' ')
62
+ else
63
+ 'pp.printerName = "";'
64
+ end
65
+ end
66
+
67
+ # create or access the Javascript Name Tree in the document names dict.
68
+ # See section 3.6.3 and table 3.28 in the PDF spec.
69
+ #
70
+ def javascript
71
+ names.data[:JavaScript] ||= ref!(::Prawn::Core::NameTree::Node.new(self, NAME_TREE_CHILDREN_LIMIT))
72
+ end
73
+ end
74
+ end
75
+ end
76
+
77
+ require 'prawn/document'
78
+ ::Prawn::Document.send(:include, JasperCommandLine::Prawn::JS)
@@ -1,3 +1,3 @@
1
1
  module JasperCommandLine
2
- VERSION = "0.4.0"
2
+ VERSION = "0.4.1"
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: jasper-command-line
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.0
4
+ version: 0.4.1
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2013-03-18 00:00:00.000000000 Z
12
+ date: 2013-04-11 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rjb
@@ -34,7 +34,7 @@ dependencies:
34
34
  requirements:
35
35
  - - ! '>='
36
36
  - !ruby/object:Gem::Version
37
- version: 3.0.2
37
+ version: 3.0.3
38
38
  type: :runtime
39
39
  prerelease: false
40
40
  version_requirements: !ruby/object:Gem::Requirement
@@ -42,7 +42,7 @@ dependencies:
42
42
  requirements:
43
43
  - - ! '>='
44
44
  - !ruby/object:Gem::Version
45
- version: 3.0.2
45
+ version: 3.0.3
46
46
  - !ruby/object:Gem::Dependency
47
47
  name: activesupport
48
48
  requirement: !ruby/object:Gem::Requirement
@@ -59,6 +59,22 @@ dependencies:
59
59
  - - ! '>='
60
60
  - !ruby/object:Gem::Version
61
61
  version: 3.2.0
62
+ - !ruby/object:Gem::Dependency
63
+ name: prawn
64
+ requirement: !ruby/object:Gem::Requirement
65
+ none: false
66
+ requirements:
67
+ - - ! '>='
68
+ - !ruby/object:Gem::Version
69
+ version: 0.12.0
70
+ type: :runtime
71
+ prerelease: false
72
+ version_requirements: !ruby/object:Gem::Requirement
73
+ none: false
74
+ requirements:
75
+ - - ! '>='
76
+ - !ruby/object:Gem::Version
77
+ version: 0.12.0
62
78
  - !ruby/object:Gem::Dependency
63
79
  name: rspec
64
80
  requirement: !ruby/object:Gem::Requirement
@@ -125,6 +141,7 @@ files:
125
141
  - lib/jasper-command-line/java/jcommon-1.0.15.jar
126
142
  - lib/jasper-command-line/java/jfreechart-1.0.12.jar
127
143
  - lib/jasper-command-line/java/xalan.jar
144
+ - lib/jasper-command-line/prawn-js.rb
128
145
  - lib/jasper-command-line/version.rb
129
146
  homepage: http://github.com/gokuu/jasper-command-line
130
147
  licenses: []