doxieland 0.1.0 → 0.9.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/.gitignore +1 -0
 - data/.ruby-gemset +1 -0
 - data/.ruby-version +1 -0
 - data/doxieland.gemspec +5 -2
 - data/exe/doxieland +198 -15
 - data/lib/doxieland.rb +26 -2
 - data/lib/doxieland/actions/delete_scans.rb +17 -0
 - data/lib/doxieland/actions/get_info.rb +8 -0
 - data/lib/doxieland/actions/get_scan.rb +20 -0
 - data/lib/doxieland/actions/list_scans.rb +16 -0
 - data/lib/doxieland/api.rb +3 -1
 - data/lib/doxieland/client.rb +94 -0
 - data/lib/doxieland/handlers/file_request.rb +43 -0
 - data/lib/doxieland/logger.rb +47 -0
 - data/lib/doxieland/scan.rb +101 -0
 - data/lib/doxieland/version.rb +1 -1
 - metadata +59 -11
 - data/doxieland.sublime-project +0 -8
 - data/doxieland.sublime-workspace +0 -1729
 - data/lib/doxieland/handlers/json.rb +0 -27
 
    
        checksums.yaml
    CHANGED
    
    | 
         @@ -1,7 +1,7 @@ 
     | 
|
| 
       1 
1 
     | 
    
         
             
            ---
         
     | 
| 
       2 
2 
     | 
    
         
             
            SHA1:
         
     | 
| 
       3 
     | 
    
         
            -
              metadata.gz:  
     | 
| 
       4 
     | 
    
         
            -
              data.tar.gz:  
     | 
| 
      
 3 
     | 
    
         
            +
              metadata.gz: 3a8265c8aef3acb73110d4c084c45ee809391bb6
         
     | 
| 
      
 4 
     | 
    
         
            +
              data.tar.gz: a6636e435c48b7a47fc0035a3d08635083b44c9c
         
     | 
| 
       5 
5 
     | 
    
         
             
            SHA512:
         
     | 
| 
       6 
     | 
    
         
            -
              metadata.gz:  
     | 
| 
       7 
     | 
    
         
            -
              data.tar.gz:  
     | 
| 
      
 6 
     | 
    
         
            +
              metadata.gz: bbc20ab3361ffadbc3d710b9a8c4e8d384470de16d3b86c6db1926d6542dc67aa2314e24f78de9c0bf51be927e0c81c332c8087c87089b86029d5f55e54276cf
         
     | 
| 
      
 7 
     | 
    
         
            +
              data.tar.gz: f3128eb67754c15858636561f8b1588dd76271ca06414ab0a2a8ef39c03ee00a43a6c5293d4e34d343228666e26e92f813b9a757f2a1502899c6fdc06032f4d0
         
     | 
    
        data/.gitignore
    CHANGED
    
    
    
        data/.ruby-gemset
    ADDED
    
    | 
         @@ -0,0 +1 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            doxieland
         
     | 
    
        data/.ruby-version
    ADDED
    
    | 
         @@ -0,0 +1 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            ruby-2.3.0
         
     | 
    
        data/doxieland.gemspec
    CHANGED
    
    | 
         @@ -20,8 +20,11 @@ Gem::Specification.new do |spec| 
     | 
|
| 
       20 
20 
     | 
    
         
             
              spec.require_paths = ["lib"]
         
     | 
| 
       21 
21 
     | 
    
         | 
| 
       22 
22 
     | 
    
         
             
              spec.add_runtime_dependency 'activesupport', '>= 4.2'
         
     | 
| 
       23 
     | 
    
         
            -
              spec.add_runtime_dependency 'apidiesel', '>= 0. 
     | 
| 
       24 
     | 
    
         
            -
              spec.add_runtime_dependency ' 
     | 
| 
      
 23 
     | 
    
         
            +
              spec.add_runtime_dependency 'apidiesel', '>= 0.12'
         
     | 
| 
      
 24 
     | 
    
         
            +
              spec.add_runtime_dependency 'thor', '>= 0.19'
         
     | 
| 
      
 25 
     | 
    
         
            +
              spec.add_runtime_dependency 'ruby-progressbar', '>= 1.7'
         
     | 
| 
      
 26 
     | 
    
         
            +
              spec.add_runtime_dependency 'hirb', '>= 0.7'
         
     | 
| 
      
 27 
     | 
    
         
            +
              spec.add_runtime_dependency 'rainbow', '>= 2.1'
         
     | 
| 
       25 
28 
     | 
    
         | 
| 
       26 
29 
     | 
    
         
             
              spec.add_development_dependency "bundler", "~> 1.11"
         
     | 
| 
       27 
30 
     | 
    
         
             
              spec.add_development_dependency "rake", "~> 10.0"
         
     | 
    
        data/exe/doxieland
    CHANGED
    
    | 
         @@ -1,23 +1,206 @@ 
     | 
|
| 
       1 
1 
     | 
    
         
             
            #!/usr/bin/env ruby
         
     | 
| 
       2 
     | 
    
         
            -
             
     | 
| 
       3 
2 
     | 
    
         
             
            require "doxieland"
         
     | 
| 
       4 
     | 
    
         
            -
            require  
     | 
| 
      
 3 
     | 
    
         
            +
            require "thor"
         
     | 
| 
      
 4 
     | 
    
         
            +
            require "ruby-progressbar"
         
     | 
| 
      
 5 
     | 
    
         
            +
            require 'hirb'
         
     | 
| 
      
 6 
     | 
    
         
            +
             
     | 
| 
      
 7 
     | 
    
         
            +
            class CLI < Thor
         
     | 
| 
      
 8 
     | 
    
         
            +
              include Thor::Actions
         
     | 
| 
       5 
9 
     | 
    
         | 
| 
       6 
     | 
    
         
            -
             
     | 
| 
       7 
     | 
    
         
            -
             
     | 
| 
       8 
     | 
    
         
            -
            program :description, 'A command line tool for downloading scans from the doxie go wi-fi'
         
     | 
| 
      
 10 
     | 
    
         
            +
              class_option 'scanner-ip', desc:'your scanners network address', banner: 'xxx.xxx.xxx.xxx', type: :string, aliases: '-i'
         
     | 
| 
      
 11 
     | 
    
         
            +
              class_option :password, desc:'your scanners password', type: :string, aliases: '-p'
         
     | 
| 
       9 
12 
     | 
    
         | 
| 
       10 
     | 
    
         
            -
             
     | 
| 
      
 13 
     | 
    
         
            +
              def initialize(*args, **kargs)
         
     | 
| 
      
 14 
     | 
    
         
            +
                super
         
     | 
| 
      
 15 
     | 
    
         
            +
             
     | 
| 
      
 16 
     | 
    
         
            +
                @config = (options || HashWithIndifferentAccess.new).reverse_merge(Doxieland.config)
         
     | 
| 
      
 17 
     | 
    
         
            +
                @client = Doxieland::Client.new(@config)
         
     | 
| 
      
 18 
     | 
    
         
            +
              end
         
     | 
| 
      
 19 
     | 
    
         
            +
             
     | 
| 
      
 20 
     | 
    
         
            +
              desc "info", "show information about your scanner"
         
     | 
| 
      
 21 
     | 
    
         
            +
              def info
         
     | 
| 
      
 22 
     | 
    
         
            +
                response =
         
     | 
| 
      
 23 
     | 
    
         
            +
                  @client.api do |api|
         
     | 
| 
      
 24 
     | 
    
         
            +
                    api.get_info.result
         
     | 
| 
      
 25 
     | 
    
         
            +
                  end
         
     | 
| 
      
 26 
     | 
    
         
            +
             
     | 
| 
      
 27 
     | 
    
         
            +
                  puts Hirb::Helpers::AutoTable.render(
         
     | 
| 
      
 28 
     | 
    
         
            +
                      response,
         
     | 
| 
      
 29 
     | 
    
         
            +
                      description:  false,
         
     | 
| 
      
 30 
     | 
    
         
            +
                      headers:      false
         
     | 
| 
      
 31 
     | 
    
         
            +
                    )
         
     | 
| 
      
 32 
     | 
    
         
            +
              end
         
     | 
| 
       11 
33 
     | 
    
         | 
| 
       12 
     | 
    
         
            -
             
     | 
| 
       13 
     | 
    
         
            -
               
     | 
| 
       14 
     | 
    
         
            -
             
     | 
| 
       15 
     | 
    
         
            -
              c.action do |args, options|
         
     | 
| 
       16 
     | 
    
         
            -
                Doxieland::Api.url "http://#{@ip}:8080"
         
     | 
| 
       17 
     | 
    
         
            -
                api = Doxieland::Api.new
         
     | 
| 
      
 34 
     | 
    
         
            +
              desc "list", "list all scans saved in your scanners memory"
         
     | 
| 
      
 35 
     | 
    
         
            +
              def list
         
     | 
| 
      
 36 
     | 
    
         
            +
                scans = @client.api { |api| api.list_scans.result }
         
     | 
| 
       18 
37 
     | 
    
         | 
| 
       19 
     | 
    
         
            -
                 
     | 
| 
       20 
     | 
    
         
            -
                   
     | 
| 
      
 38 
     | 
    
         
            +
                if scans.none?
         
     | 
| 
      
 39 
     | 
    
         
            +
                  log.info "no scans found"
         
     | 
| 
      
 40 
     | 
    
         
            +
                  exit
         
     | 
| 
       21 
41 
     | 
    
         
             
                end
         
     | 
| 
      
 42 
     | 
    
         
            +
             
     | 
| 
      
 43 
     | 
    
         
            +
                puts Hirb::Helpers::AutoTable.render(
         
     | 
| 
      
 44 
     | 
    
         
            +
                  scans,
         
     | 
| 
      
 45 
     | 
    
         
            +
                  fields: [:name, :path],
         
     | 
| 
      
 46 
     | 
    
         
            +
                  description: false
         
     | 
| 
      
 47 
     | 
    
         
            +
                )
         
     | 
| 
      
 48 
     | 
    
         
            +
             
     | 
| 
      
 49 
     | 
    
         
            +
                log.info "#{scans.length} scans available"
         
     | 
| 
       22 
50 
     | 
    
         
             
              end
         
     | 
| 
       23 
     | 
    
         
            -
             
     | 
| 
      
 51 
     | 
    
         
            +
             
     | 
| 
      
 52 
     | 
    
         
            +
              desc "download", <<-EOT.strip_heredoc
         
     | 
| 
      
 53 
     | 
    
         
            +
                download all scans from your scanner to your computer
         
     | 
| 
      
 54 
     | 
    
         
            +
             
     | 
| 
      
 55 
     | 
    
         
            +
                Available placeholders for filename format strings:
         
     | 
| 
      
 56 
     | 
    
         
            +
                  %{number} - the image number
         
     | 
| 
      
 57 
     | 
    
         
            +
                  %{date} - the current date as DD.MM.YYYY
         
     | 
| 
      
 58 
     | 
    
         
            +
                  %{time} - the current time as HH:MM:SS
         
     | 
| 
      
 59 
     | 
    
         
            +
             
     | 
| 
      
 60 
     | 
    
         
            +
                You can further format date and time by passing format options inside the placeholders, separated by a colon:
         
     | 
| 
      
 61 
     | 
    
         
            +
             
     | 
| 
      
 62 
     | 
    
         
            +
                  %{date:%Y-%m-%d}
         
     | 
| 
      
 63 
     | 
    
         
            +
             
     | 
| 
      
 64 
     | 
    
         
            +
                See http://ruby-doc.org/core-2.2.0/Time.html#method-i-strftime for all available date and time formatting options.
         
     | 
| 
      
 65 
     | 
    
         
            +
             
     | 
| 
      
 66 
     | 
    
         
            +
              EOT
         
     | 
| 
      
 67 
     | 
    
         
            +
              method_option :to, desc: "the directory to save the scans to. Defaults to .", type: :string, aliases: '-t'
         
     | 
| 
      
 68 
     | 
    
         
            +
              method_option :filenames,
         
     | 
| 
      
 69 
     | 
    
         
            +
                            type: :string,
         
     | 
| 
      
 70 
     | 
    
         
            +
                            aliases: '-f',
         
     | 
| 
      
 71 
     | 
    
         
            +
                            banner: '"FORMAT_STRING"',
         
     | 
| 
      
 72 
     | 
    
         
            +
                            desc: 'filename format string. Default: "doxie_scan_%{date}-%{number}"'
         
     | 
| 
      
 73 
     | 
    
         
            +
              method_option :pdf, desc: "convert scans to PDF. Requires ImageMagick to be installed", type: :boolean
         
     | 
| 
      
 74 
     | 
    
         
            +
              method_option :delete, desc: "delete scans from scanner after download", type: :boolean, aliases: '-d'
         
     | 
| 
      
 75 
     | 
    
         
            +
              def download
         
     | 
| 
      
 76 
     | 
    
         
            +
                if @config[:pdf]
         
     | 
| 
      
 77 
     | 
    
         
            +
                  unless command_available?('convert')
         
     | 
| 
      
 78 
     | 
    
         
            +
                    log.fatal "could not find the 'convert' command. PDF conversion requires ImageMagick to be installed"
         
     | 
| 
      
 79 
     | 
    
         
            +
                    exit(false)
         
     | 
| 
      
 80 
     | 
    
         
            +
                  end
         
     | 
| 
      
 81 
     | 
    
         
            +
                end
         
     | 
| 
      
 82 
     | 
    
         
            +
             
     | 
| 
      
 83 
     | 
    
         
            +
                @client.create_save_path
         
     | 
| 
      
 84 
     | 
    
         
            +
             
     | 
| 
      
 85 
     | 
    
         
            +
                Doxieland::Scan.save_path   = @client.save_path
         
     | 
| 
      
 86 
     | 
    
         
            +
                Doxieland::Scan.name_format = @config[:filenames] if @config[:filenames]
         
     | 
| 
      
 87 
     | 
    
         
            +
             
     | 
| 
      
 88 
     | 
    
         
            +
                scans = @client.api do |api|
         
     | 
| 
      
 89 
     | 
    
         
            +
                  api.list_scans.result
         
     | 
| 
      
 90 
     | 
    
         
            +
                end
         
     | 
| 
      
 91 
     | 
    
         
            +
             
     | 
| 
      
 92 
     | 
    
         
            +
                if scans.none?
         
     | 
| 
      
 93 
     | 
    
         
            +
                  log.info "0 scans available for download on scanner"
         
     | 
| 
      
 94 
     | 
    
         
            +
                  exit
         
     | 
| 
      
 95 
     | 
    
         
            +
                end
         
     | 
| 
      
 96 
     | 
    
         
            +
             
     | 
| 
      
 97 
     | 
    
         
            +
                log.info "downloading #{scans.length} scans to " + Rainbow(@client.save_path).cyan.bright
         
     | 
| 
      
 98 
     | 
    
         
            +
             
     | 
| 
      
 99 
     | 
    
         
            +
                progressbar = create_progressbar(starting_at: 0, total: scans.length)
         
     | 
| 
      
 100 
     | 
    
         
            +
             
     | 
| 
      
 101 
     | 
    
         
            +
                deletable_paths = []
         
     | 
| 
      
 102 
     | 
    
         
            +
                save_count      = 0
         
     | 
| 
      
 103 
     | 
    
         
            +
             
     | 
| 
      
 104 
     | 
    
         
            +
                scans.each do |remote_scan|
         
     | 
| 
      
 105 
     | 
    
         
            +
                  progressbar.title = "downloading #{remote_scan[:name]}".truncate(22).ljust(25)
         
     | 
| 
      
 106 
     | 
    
         
            +
             
     | 
| 
      
 107 
     | 
    
         
            +
                  scan = @client.api { |api| api.get_scan(path: remote_scan[:path]).result }
         
     | 
| 
      
 108 
     | 
    
         
            +
             
     | 
| 
      
 109 
     | 
    
         
            +
                  if @config[:pdf]
         
     | 
| 
      
 110 
     | 
    
         
            +
                    scan.file_type = 'pdf'
         
     | 
| 
      
 111 
     | 
    
         
            +
                    progressbar.title = "saving #{remote_scan[:name]} as PDF".truncate(22).ljust(25)
         
     | 
| 
      
 112 
     | 
    
         
            +
                  else
         
     | 
| 
      
 113 
     | 
    
         
            +
                    progressbar.title = "saving #{remote_scan[:name]}".truncate(22).ljust(25)
         
     | 
| 
      
 114 
     | 
    
         
            +
                  end
         
     | 
| 
      
 115 
     | 
    
         
            +
             
     | 
| 
      
 116 
     | 
    
         
            +
                  if scan.save
         
     | 
| 
      
 117 
     | 
    
         
            +
                    save_count += 1
         
     | 
| 
      
 118 
     | 
    
         
            +
                    deletable_paths << remote_scan[:delete_path]
         
     | 
| 
      
 119 
     | 
    
         
            +
                  else
         
     | 
| 
      
 120 
     | 
    
         
            +
                    log.progress_warn "skipped existing file #{scan.path}", progressbar
         
     | 
| 
      
 121 
     | 
    
         
            +
                  end
         
     | 
| 
      
 122 
     | 
    
         
            +
             
     | 
| 
      
 123 
     | 
    
         
            +
                  progressbar.increment
         
     | 
| 
      
 124 
     | 
    
         
            +
                end
         
     | 
| 
      
 125 
     | 
    
         
            +
             
     | 
| 
      
 126 
     | 
    
         
            +
                if options[:delete] && deletable_paths.any?
         
     | 
| 
      
 127 
     | 
    
         
            +
                  progressbar = create_progressbar(title: "deleting scans".ljust(20))
         
     | 
| 
      
 128 
     | 
    
         
            +
             
     | 
| 
      
 129 
     | 
    
         
            +
                  @client.api { |api| api.delete_scans(paths: deletable_paths).result }
         
     | 
| 
      
 130 
     | 
    
         
            +
             
     | 
| 
      
 131 
     | 
    
         
            +
                  progressbar.progress = 1
         
     | 
| 
      
 132 
     | 
    
         
            +
                  progressbar.total    = 1
         
     | 
| 
      
 133 
     | 
    
         
            +
                  progressbar.finish
         
     | 
| 
      
 134 
     | 
    
         
            +
                end
         
     | 
| 
      
 135 
     | 
    
         
            +
             
     | 
| 
      
 136 
     | 
    
         
            +
                log.success "#{save_count} scans downloaded"
         
     | 
| 
      
 137 
     | 
    
         
            +
              end
         
     | 
| 
      
 138 
     | 
    
         
            +
             
     | 
| 
      
 139 
     | 
    
         
            +
              desc "defaults", "show or set default options for doxieland"
         
     | 
| 
      
 140 
     | 
    
         
            +
              method_option :to, desc: "the directory to save the scans to. Defaults to .", type: :string, aliases: '-t'
         
     | 
| 
      
 141 
     | 
    
         
            +
              method_option :filenames,
         
     | 
| 
      
 142 
     | 
    
         
            +
                            type: :string,
         
     | 
| 
      
 143 
     | 
    
         
            +
                            aliases: '-f',
         
     | 
| 
      
 144 
     | 
    
         
            +
                            banner: '"FORMAT_STRING"'
         
     | 
| 
      
 145 
     | 
    
         
            +
              method_option :pdf, desc: "convert scans to PDF. Requires ImageMagick to be installed", type: :boolean
         
     | 
| 
      
 146 
     | 
    
         
            +
              method_option :delete, desc: "delete scans from scanner after download", type: :boolean, aliases: '-d'
         
     | 
| 
      
 147 
     | 
    
         
            +
              def defaults
         
     | 
| 
      
 148 
     | 
    
         
            +
                if options.none?
         
     | 
| 
      
 149 
     | 
    
         
            +
                  config = Doxieland.config
         
     | 
| 
      
 150 
     | 
    
         
            +
             
     | 
| 
      
 151 
     | 
    
         
            +
                  if config.any?
         
     | 
| 
      
 152 
     | 
    
         
            +
                    puts Hirb::Helpers::AutoTable.render(
         
     | 
| 
      
 153 
     | 
    
         
            +
                      config,
         
     | 
| 
      
 154 
     | 
    
         
            +
                      description:  false,
         
     | 
| 
      
 155 
     | 
    
         
            +
                      headers:      { 0 => 'option', 1 => 'value' }
         
     | 
| 
      
 156 
     | 
    
         
            +
                    )
         
     | 
| 
      
 157 
     | 
    
         
            +
                  else
         
     | 
| 
      
 158 
     | 
    
         
            +
                    log.info "no defaults set"
         
     | 
| 
      
 159 
     | 
    
         
            +
                  end
         
     | 
| 
      
 160 
     | 
    
         
            +
             
     | 
| 
      
 161 
     | 
    
         
            +
                else
         
     | 
| 
      
 162 
     | 
    
         
            +
                  File.open(Doxieland.config_path, 'w') { |file| file << YAML.dump(options) }
         
     | 
| 
      
 163 
     | 
    
         
            +
             
     | 
| 
      
 164 
     | 
    
         
            +
                  puts Hirb::Helpers::AutoTable.render(
         
     | 
| 
      
 165 
     | 
    
         
            +
                    config,
         
     | 
| 
      
 166 
     | 
    
         
            +
                    description:  false,
         
     | 
| 
      
 167 
     | 
    
         
            +
                    headers:      { 0 => 'option', 1 => 'value' }
         
     | 
| 
      
 168 
     | 
    
         
            +
                  )
         
     | 
| 
      
 169 
     | 
    
         
            +
             
     | 
| 
      
 170 
     | 
    
         
            +
                  log.success "new default settings saved"
         
     | 
| 
      
 171 
     | 
    
         
            +
                end
         
     | 
| 
      
 172 
     | 
    
         
            +
              end
         
     | 
| 
      
 173 
     | 
    
         
            +
             
     | 
| 
      
 174 
     | 
    
         
            +
              desc "console", "starts a Pry REPL session", hide: true
         
     | 
| 
      
 175 
     | 
    
         
            +
              def console
         
     | 
| 
      
 176 
     | 
    
         
            +
                begin
         
     | 
| 
      
 177 
     | 
    
         
            +
                  require 'pry'
         
     | 
| 
      
 178 
     | 
    
         
            +
                rescue LoadError
         
     | 
| 
      
 179 
     | 
    
         
            +
                  log.fatal "doxieland console requires Pry to be installed: gem install pry"
         
     | 
| 
      
 180 
     | 
    
         
            +
                  exit
         
     | 
| 
      
 181 
     | 
    
         
            +
                end
         
     | 
| 
      
 182 
     | 
    
         
            +
                binding.pry
         
     | 
| 
      
 183 
     | 
    
         
            +
              end
         
     | 
| 
      
 184 
     | 
    
         
            +
             
     | 
| 
      
 185 
     | 
    
         
            +
              no_commands do
         
     | 
| 
      
 186 
     | 
    
         
            +
                def log
         
     | 
| 
      
 187 
     | 
    
         
            +
                  @client.log
         
     | 
| 
      
 188 
     | 
    
         
            +
                end
         
     | 
| 
      
 189 
     | 
    
         
            +
             
     | 
| 
      
 190 
     | 
    
         
            +
                def create_progressbar(**kargs)
         
     | 
| 
      
 191 
     | 
    
         
            +
                  kargs.reverse_merge!({
         
     | 
| 
      
 192 
     | 
    
         
            +
                    total: nil,
         
     | 
| 
      
 193 
     | 
    
         
            +
                    format: "%t (%c of %C) |%b\u{1F431}%i| %E",
         
     | 
| 
      
 194 
     | 
    
         
            +
                    progress_mark: "\u{2728}",
         
     | 
| 
      
 195 
     | 
    
         
            +
                    remainder_mark: " ", title: ' ' * 25
         
     | 
| 
      
 196 
     | 
    
         
            +
                  })
         
     | 
| 
      
 197 
     | 
    
         
            +
                  ProgressBar.create(**kargs)
         
     | 
| 
      
 198 
     | 
    
         
            +
                end
         
     | 
| 
      
 199 
     | 
    
         
            +
             
     | 
| 
      
 200 
     | 
    
         
            +
                def command_available?(command)
         
     | 
| 
      
 201 
     | 
    
         
            +
                  `which #{command}`.present? && $?.exitstatus == 0
         
     | 
| 
      
 202 
     | 
    
         
            +
                end
         
     | 
| 
      
 203 
     | 
    
         
            +
              end
         
     | 
| 
      
 204 
     | 
    
         
            +
            end
         
     | 
| 
      
 205 
     | 
    
         
            +
             
     | 
| 
      
 206 
     | 
    
         
            +
            CLI.start( ARGV.any? ? ARGV : ['help'] )
         
     | 
    
        data/lib/doxieland.rb
    CHANGED
    
    | 
         @@ -2,11 +2,35 @@ require "doxieland/version" 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            require 'active_support/all'
         
     | 
| 
       4 
4 
     | 
    
         
             
            require 'apidiesel'
         
     | 
| 
      
 5 
     | 
    
         
            +
            require 'rainbow'
         
     | 
| 
      
 6 
     | 
    
         
            +
            require 'open-uri'
         
     | 
| 
      
 7 
     | 
    
         
            +
            require 'cgi'
         
     | 
| 
      
 8 
     | 
    
         
            +
            require 'pathname'
         
     | 
| 
      
 9 
     | 
    
         
            +
            require 'fileutils'
         
     | 
| 
      
 10 
     | 
    
         
            +
            require 'open3'
         
     | 
| 
       5 
11 
     | 
    
         | 
| 
       6 
     | 
    
         
            -
            require 'doxieland/handlers/ 
     | 
| 
      
 12 
     | 
    
         
            +
            require 'doxieland/handlers/file_request'
         
     | 
| 
       7 
13 
     | 
    
         
             
            require 'doxieland/actions/list_scans'
         
     | 
| 
      
 14 
     | 
    
         
            +
            require 'doxieland/actions/get_info'
         
     | 
| 
      
 15 
     | 
    
         
            +
            require 'doxieland/actions/get_scan'
         
     | 
| 
      
 16 
     | 
    
         
            +
            require 'doxieland/actions/delete_scans'
         
     | 
| 
       8 
17 
     | 
    
         
             
            require 'doxieland/api'
         
     | 
| 
      
 18 
     | 
    
         
            +
            require 'doxieland/scan'
         
     | 
| 
      
 19 
     | 
    
         
            +
            require 'doxieland/logger'
         
     | 
| 
      
 20 
     | 
    
         
            +
            require 'doxieland/client'
         
     | 
| 
       9 
21 
     | 
    
         | 
| 
       10 
22 
     | 
    
         
             
            module Doxieland
         
     | 
| 
       11 
     | 
    
         
            -
               
     | 
| 
      
 23 
     | 
    
         
            +
              class AuthenticationError < StandardError; end
         
     | 
| 
      
 24 
     | 
    
         
            +
             
     | 
| 
      
 25 
     | 
    
         
            +
              def self.config_path
         
     | 
| 
      
 26 
     | 
    
         
            +
                Pathname.new('~/.doxieland').expand_path
         
     | 
| 
      
 27 
     | 
    
         
            +
              end
         
     | 
| 
      
 28 
     | 
    
         
            +
             
     | 
| 
      
 29 
     | 
    
         
            +
              def self.config
         
     | 
| 
      
 30 
     | 
    
         
            +
                if File.file?(config_path)
         
     | 
| 
      
 31 
     | 
    
         
            +
                  YAML.load( File.read(config_path) ).with_indifferent_access
         
     | 
| 
      
 32 
     | 
    
         
            +
                else
         
     | 
| 
      
 33 
     | 
    
         
            +
                  HashWithIndifferentAccess.new
         
     | 
| 
      
 34 
     | 
    
         
            +
                end
         
     | 
| 
      
 35 
     | 
    
         
            +
              end
         
     | 
| 
       12 
36 
     | 
    
         
             
            end
         
     | 
| 
         @@ -0,0 +1,17 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Doxieland
         
     | 
| 
      
 2 
     | 
    
         
            +
              module Actions
         
     | 
| 
      
 3 
     | 
    
         
            +
                class DeleteScans < ::Apidiesel::Action
         
     | 
| 
      
 4 
     | 
    
         
            +
                  url path: '/scans/delete.json'
         
     | 
| 
      
 5 
     | 
    
         
            +
             
     | 
| 
      
 6 
     | 
    
         
            +
                  http_method :post
         
     | 
| 
      
 7 
     | 
    
         
            +
             
     | 
| 
      
 8 
     | 
    
         
            +
                  expects do
         
     | 
| 
      
 9 
     | 
    
         
            +
                    object :paths, klass: Array
         
     | 
| 
      
 10 
     | 
    
         
            +
                  end
         
     | 
| 
      
 11 
     | 
    
         
            +
             
     | 
| 
      
 12 
     | 
    
         
            +
                  format_parameters do |params|
         
     | 
| 
      
 13 
     | 
    
         
            +
                    params[:paths]
         
     | 
| 
      
 14 
     | 
    
         
            +
                  end
         
     | 
| 
      
 15 
     | 
    
         
            +
                end
         
     | 
| 
      
 16 
     | 
    
         
            +
              end
         
     | 
| 
      
 17 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,20 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Doxieland
         
     | 
| 
      
 2 
     | 
    
         
            +
              module Actions
         
     | 
| 
      
 3 
     | 
    
         
            +
                class GetScan < ::Apidiesel::Action
         
     | 
| 
      
 4 
     | 
    
         
            +
                  use Apidiesel::Handlers::ActionResponseProcessor
         
     | 
| 
      
 5 
     | 
    
         
            +
                  use Handlers::FileRequest
         
     | 
| 
      
 6 
     | 
    
         
            +
             
     | 
| 
      
 7 
     | 
    
         
            +
                  url ->(base_url, request) {
         
     | 
| 
      
 8 
     | 
    
         
            +
                    base_url.path = request.parameters.delete(:path)
         
     | 
| 
      
 9 
     | 
    
         
            +
             
     | 
| 
      
 10 
     | 
    
         
            +
                    base_url
         
     | 
| 
      
 11 
     | 
    
         
            +
                  }
         
     | 
| 
      
 12 
     | 
    
         
            +
             
     | 
| 
      
 13 
     | 
    
         
            +
                  http_method :get
         
     | 
| 
      
 14 
     | 
    
         
            +
             
     | 
| 
      
 15 
     | 
    
         
            +
                  expects do
         
     | 
| 
      
 16 
     | 
    
         
            +
                    string :path
         
     | 
| 
      
 17 
     | 
    
         
            +
                  end
         
     | 
| 
      
 18 
     | 
    
         
            +
                end
         
     | 
| 
      
 19 
     | 
    
         
            +
              end
         
     | 
| 
      
 20 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -3,6 +3,22 @@ module Doxieland 
     | 
|
| 
       3 
3 
     | 
    
         
             
                class ListScans < ::Apidiesel::Action
         
     | 
| 
       4 
4 
     | 
    
         
             
                  http_method :get
         
     | 
| 
       5 
5 
     | 
    
         
             
                  url path: '/scans.json'
         
     | 
| 
      
 6 
     | 
    
         
            +
             
     | 
| 
      
 7 
     | 
    
         
            +
                  responds_with do
         
     | 
| 
      
 8 
     | 
    
         
            +
                    array do
         
     | 
| 
      
 9 
     | 
    
         
            +
                      string :path,
         
     | 
| 
      
 10 
     | 
    
         
            +
                              at: :name,
         
     | 
| 
      
 11 
     | 
    
         
            +
                              filter: ->(s) { "/scans#{s}" }
         
     | 
| 
      
 12 
     | 
    
         
            +
                      string :delete_path,
         
     | 
| 
      
 13 
     | 
    
         
            +
                              at: :name
         
     | 
| 
      
 14 
     | 
    
         
            +
                      string :thumbnail_path,
         
     | 
| 
      
 15 
     | 
    
         
            +
                              at: :name,
         
     | 
| 
      
 16 
     | 
    
         
            +
                              filter: ->(s) { "/thumbnails#{s}" }
         
     | 
| 
      
 17 
     | 
    
         
            +
                      string :name,
         
     | 
| 
      
 18 
     | 
    
         
            +
                              filter: ->(s) { s.match(/[0-9]{4,}/)[0] }
         
     | 
| 
      
 19 
     | 
    
         
            +
                      integer :size
         
     | 
| 
      
 20 
     | 
    
         
            +
                    end
         
     | 
| 
      
 21 
     | 
    
         
            +
                  end
         
     | 
| 
       6 
22 
     | 
    
         
             
                end
         
     | 
| 
       7 
23 
     | 
    
         
             
              end
         
     | 
| 
       8 
24 
     | 
    
         
             
            end
         
     | 
    
        data/lib/doxieland/api.rb
    CHANGED
    
    
| 
         @@ -0,0 +1,94 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Doxieland
         
     | 
| 
      
 2 
     | 
    
         
            +
              class Client
         
     | 
| 
      
 3 
     | 
    
         
            +
                attr_reader :save_path
         
     | 
| 
      
 4 
     | 
    
         
            +
             
     | 
| 
      
 5 
     | 
    
         
            +
                def initialize(options)
         
     | 
| 
      
 6 
     | 
    
         
            +
                  @options       = options
         
     | 
| 
      
 7 
     | 
    
         
            +
                  @save_path     = Pathname.new(options[:to] || '.').expand_path
         
     | 
| 
      
 8 
     | 
    
         
            +
                end
         
     | 
| 
      
 9 
     | 
    
         
            +
             
     | 
| 
      
 10 
     | 
    
         
            +
                def api(&block)
         
     | 
| 
      
 11 
     | 
    
         
            +
                  Doxieland::Api.url "http://#{scanner_ip}:8080"
         
     | 
| 
      
 12 
     | 
    
         
            +
             
     | 
| 
      
 13 
     | 
    
         
            +
                  if @options[:password]
         
     | 
| 
      
 14 
     | 
    
         
            +
                    Doxieland::Api.http_basic_auth 'doxie', @options[:password]
         
     | 
| 
      
 15 
     | 
    
         
            +
                  end
         
     | 
| 
      
 16 
     | 
    
         
            +
             
     | 
| 
      
 17 
     | 
    
         
            +
                  api = Doxieland::Api.new
         
     | 
| 
      
 18 
     | 
    
         
            +
             
     | 
| 
      
 19 
     | 
    
         
            +
                  begin
         
     | 
| 
      
 20 
     | 
    
         
            +
                    yield api
         
     | 
| 
      
 21 
     | 
    
         
            +
                  rescue AuthenticationError => e
         
     | 
| 
      
 22 
     | 
    
         
            +
                    log.fatal e.message
         
     | 
| 
      
 23 
     | 
    
         
            +
                    exit(false)
         
     | 
| 
      
 24 
     | 
    
         
            +
                  end
         
     | 
| 
      
 25 
     | 
    
         
            +
                end
         
     | 
| 
      
 26 
     | 
    
         
            +
             
     | 
| 
      
 27 
     | 
    
         
            +
                def create_save_path
         
     | 
| 
      
 28 
     | 
    
         
            +
                  raise ArgumentError, "#{@save_path} is a file" if @save_path.file?
         
     | 
| 
      
 29 
     | 
    
         
            +
             
     | 
| 
      
 30 
     | 
    
         
            +
                  unless @save_path.directory? || @save_path == Pathname.new('.')
         
     | 
| 
      
 31 
     | 
    
         
            +
                    FileUtils.mkdir_p(@save_path)
         
     | 
| 
      
 32 
     | 
    
         
            +
                  end
         
     | 
| 
      
 33 
     | 
    
         
            +
                end
         
     | 
| 
      
 34 
     | 
    
         
            +
             
     | 
| 
      
 35 
     | 
    
         
            +
                def loglevel
         
     | 
| 
      
 36 
     | 
    
         
            +
                  @options[:verbose] ? :debug : :info
         
     | 
| 
      
 37 
     | 
    
         
            +
                end
         
     | 
| 
      
 38 
     | 
    
         
            +
             
     | 
| 
      
 39 
     | 
    
         
            +
                def log
         
     | 
| 
      
 40 
     | 
    
         
            +
                  @logger ||= Logger.new(loglevel)
         
     | 
| 
      
 41 
     | 
    
         
            +
                end
         
     | 
| 
      
 42 
     | 
    
         
            +
             
     | 
| 
      
 43 
     | 
    
         
            +
                def scanner_ip
         
     | 
| 
      
 44 
     | 
    
         
            +
                  @scanner_ip ||= begin
         
     | 
| 
      
 45 
     | 
    
         
            +
                    if @options['scanner-ip']
         
     | 
| 
      
 46 
     | 
    
         
            +
                      @options['scanner-ip']
         
     | 
| 
      
 47 
     | 
    
         
            +
                    elsif @options[:ap]
         
     | 
| 
      
 48 
     | 
    
         
            +
                      '192.168.1.100'
         
     | 
| 
      
 49 
     | 
    
         
            +
                    else
         
     | 
| 
      
 50 
     | 
    
         
            +
                      discovered_ip = ssdp_discover
         
     | 
| 
      
 51 
     | 
    
         
            +
             
     | 
| 
      
 52 
     | 
    
         
            +
                      unless discovered_ip
         
     | 
| 
      
 53 
     | 
    
         
            +
                        log.fatal "… sorry, your scanner could not be found. Is WiFi turned on and the status light blue?"
         
     | 
| 
      
 54 
     | 
    
         
            +
                        log.info "If you know it, you can also provide the IP address manually via the --scanner-ip flag."
         
     | 
| 
      
 55 
     | 
    
         
            +
                        exit
         
     | 
| 
      
 56 
     | 
    
         
            +
                      end
         
     | 
| 
      
 57 
     | 
    
         
            +
             
     | 
| 
      
 58 
     | 
    
         
            +
                      discovered_ip
         
     | 
| 
      
 59 
     | 
    
         
            +
                    end
         
     | 
| 
      
 60 
     | 
    
         
            +
                  end
         
     | 
| 
      
 61 
     | 
    
         
            +
                end
         
     | 
| 
      
 62 
     | 
    
         
            +
             
     | 
| 
      
 63 
     | 
    
         
            +
                def ssdp_discover
         
     | 
| 
      
 64 
     | 
    
         
            +
                  socket = UDPSocket.new
         
     | 
| 
      
 65 
     | 
    
         
            +
                  socket.setsockopt Socket::SOL_SOCKET, Socket::SO_BROADCAST, true
         
     | 
| 
      
 66 
     | 
    
         
            +
                  socket.setsockopt :IPPROTO_IP, :IP_MULTICAST_TTL, 1
         
     | 
| 
      
 67 
     | 
    
         
            +
             
     | 
| 
      
 68 
     | 
    
         
            +
                  query = [
         
     | 
| 
      
 69 
     | 
    
         
            +
                    'M-SEARCH * HTTP/1.1',
         
     | 
| 
      
 70 
     | 
    
         
            +
                    'HOST: 239.255.255.250:1900',
         
     | 
| 
      
 71 
     | 
    
         
            +
                    'MAN: "ssdp:discover"',
         
     | 
| 
      
 72 
     | 
    
         
            +
                    'ST: urn:schemas-getdoxie-com:device:Scanner:1',
         
     | 
| 
      
 73 
     | 
    
         
            +
                    # 'ST: ssdp:all',
         
     | 
| 
      
 74 
     | 
    
         
            +
                    'MX: 3',
         
     | 
| 
      
 75 
     | 
    
         
            +
                    '',
         
     | 
| 
      
 76 
     | 
    
         
            +
                    ''
         
     | 
| 
      
 77 
     | 
    
         
            +
                  ].join("\r\n")
         
     | 
| 
      
 78 
     | 
    
         
            +
             
     | 
| 
      
 79 
     | 
    
         
            +
                  log.info "trying to find your scanner on the network. Here, Doxie Doxie…"
         
     | 
| 
      
 80 
     | 
    
         
            +
             
     | 
| 
      
 81 
     | 
    
         
            +
                  socket.send(query, 0, '239.255.255.250', 1900)
         
     | 
| 
      
 82 
     | 
    
         
            +
             
     | 
| 
      
 83 
     | 
    
         
            +
                  ready = IO.select([socket], nil, nil, 10)
         
     | 
| 
      
 84 
     | 
    
         
            +
             
     | 
| 
      
 85 
     | 
    
         
            +
                  if ready
         
     | 
| 
      
 86 
     | 
    
         
            +
                    _, message_sender = socket.recvfrom(65507)
         
     | 
| 
      
 87 
     | 
    
         
            +
             
     | 
| 
      
 88 
     | 
    
         
            +
                    log.success "found the little rascal hiding at #{message_sender.last}"
         
     | 
| 
      
 89 
     | 
    
         
            +
             
     | 
| 
      
 90 
     | 
    
         
            +
                    message_sender.last
         
     | 
| 
      
 91 
     | 
    
         
            +
                  end
         
     | 
| 
      
 92 
     | 
    
         
            +
                end
         
     | 
| 
      
 93 
     | 
    
         
            +
              end
         
     | 
| 
      
 94 
     | 
    
         
            +
            end
         
     |