olek-paperclipftp 0.1.0.5 → 0.1.0.6

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. data/VERSION +1 -1
  2. data/lib/paperclipftp.rb +61 -30
  3. metadata +4 -4
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.1.0.5
1
+ 0.1.0.6
data/lib/paperclipftp.rb CHANGED
@@ -1,48 +1,60 @@
1
1
  module Paperclip
2
2
  module Storage
3
3
  module Ftp
4
+ class FtpTimeout < Timeout::Error; end
5
+
4
6
  def self.extended base
5
7
  require 'net/ftp'
6
8
  base.instance_eval do
7
9
  @ftp_credentials = parse_credentials(@options[:ftp_credentials])
8
10
  @passive_mode = !!@options[:ftp_passive_mode]
9
11
  @debug_mode = !!@options[:ftp_debug_mode]
12
+ @timeout = @options[:timeout] || 3600
10
13
  end
11
14
  end
12
15
 
13
16
  def ftp
14
17
  if @ftp.nil? || @ftp.closed?
15
- @ftp = Net::FTP.new(@ftp_credentials[:host], @ftp_credentials[:username], @ftp_credentials[:password])
16
- @ftp.passive = @passive_mode
17
- @ftp.debug_mode = @debug_mode
18
+ Timeout::timeout(@timeout, FtpTimeout) do
19
+ @ftp = Net::FTP.new(@ftp_credentials[:host], @ftp_credentials[:username], @ftp_credentials[:password])
20
+ @ftp.debug_mode = @debug_mode
21
+ @ftp.passive = @passive_mode
22
+ end
18
23
  end
19
24
  @ftp
20
25
  end
21
26
 
22
27
  def exists?(style = default_style)
23
- file_size(path(style)) > 0
28
+ Timeout::timeout(@timeout, FtpTimeout) do
29
+ file_size(ftp_path(style)) > 0
30
+ end
24
31
  end
25
32
 
26
33
  def to_file style = default_style
27
34
  return @queued_for_write[style] if @queued_for_write[style]
28
- file = Tempfile.new(path(style))
29
- ftp.getbinaryfile(path(style), file.path)
30
- file.rewind
31
- return file
35
+ Timeout::timeout(@timeout, FtpTimeout) do
36
+ file = Tempfile.new(ftp_path(style))
37
+ ftp.getbinaryfile(ftp_path(style), file.path)
38
+ file.rewind
39
+ return file
40
+ end
32
41
  end
33
42
 
34
43
  alias_method :to_io, :to_file
35
44
 
36
45
  def flush_writes
37
46
  @queued_for_write.each do |style, file|
38
- local_file_size = file.size
39
- file.close
40
- remote_path = path(style)
41
- ensure_parent_folder_for(remote_path)
42
- log("uploading #{remote_path}")
43
- ftp.putbinaryfile(file.path, remote_path)
44
- remote_file_size = file_size(remote_path)
45
- raise Net::FTPError.new "Uploaded #{remote_file_size} bytes instead of #{local_file_size} bytes" unless remote_file_size == local_file_size
47
+ Timeout::timeout(@timeout, FtpTimeout) do
48
+ file.close
49
+ # avoiding those weird occasional 0 file sizes by not using instance method file.size
50
+ local_file_size = File.size(file.path)
51
+ remote_path = ftp_path(style)
52
+ ensure_parent_folder_for(remote_path)
53
+ log("uploading #{remote_path}")
54
+ ftp.putbinaryfile(file.path, remote_path)
55
+ remote_file_size = file_size(remote_path)
56
+ raise Net::FTPError.new "Uploaded #{remote_file_size} bytes instead of #{local_file_size} bytes" unless remote_file_size == local_file_size
57
+ end
46
58
  end
47
59
  @queued_for_write = {}
48
60
  rescue Net::FTPReplyError => e
@@ -55,10 +67,12 @@ module Paperclip
55
67
 
56
68
  def flush_deletes
57
69
  @queued_for_delete.each do |path|
58
- begin
59
- log("deleting #{path}")
60
- ftp.delete(path)
61
- rescue Net::FTPPermError, Net::FTPReplyError
70
+ Timeout::timeout(@timeout, FtpTimeout) do
71
+ begin
72
+ log("deleting #{path}")
73
+ ftp.delete('/' + path)
74
+ rescue Net::FTPPermError, Net::FTPReplyError
75
+ end
62
76
  end
63
77
  end
64
78
  @queued_for_delete = []
@@ -70,23 +84,40 @@ module Paperclip
70
84
  ftp.close
71
85
  end
72
86
 
87
+ private
88
+
73
89
  def ensure_parent_folder_for(remote_path)
74
90
  dir_path = File.dirname(remote_path)
75
- ftp.chdir("/")
76
- dir_path.split(File::SEPARATOR).each do |rdir|
77
- rdir = rdir.strip
78
- unless rdir.blank?
79
- list = ftp.ls.collect { |f| f.split.last }
80
- unless list.include?(rdir)
81
- ftp.mkdir(rdir)
91
+ already_exists =
92
+ begin
93
+ ftp.chdir(dir_path)
94
+ true
95
+ rescue Net::FTPPermError
96
+ false
97
+ end
98
+ unless already_exists
99
+ ftp.chdir("/")
100
+ dir_path.split(File::SEPARATOR).each do |rdir|
101
+ next if rdir.blank?
102
+ first_time = true
103
+ begin
104
+ ftp.chdir(rdir)
105
+ rescue Net::FTPPermError => e
106
+ if first_time
107
+ ftp.mkdir(rdir)
108
+ first_time = false
109
+ retry
110
+ else
111
+ raise e
112
+ end
82
113
  end
83
- ftp.chdir(rdir)
84
114
  end
85
115
  end
86
- ftp.chdir("/")
87
116
  end
88
117
 
89
- private
118
+ def ftp_path(style)
119
+ '/' + path(style)
120
+ end
90
121
 
91
122
  def file_size(remote_path)
92
123
  ftp.size(remote_path)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: olek-paperclipftp
3
3
  version: !ruby/object:Gem::Version
4
- hash: 77
4
+ hash: 75
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
8
  - 1
9
9
  - 0
10
- - 5
11
- version: 0.1.0.5
10
+ - 6
11
+ version: 0.1.0.6
12
12
  platform: ruby
13
13
  authors:
14
14
  - Damian Caruso
@@ -16,7 +16,7 @@ autorequire:
16
16
  bindir: bin
17
17
  cert_chain: []
18
18
 
19
- date: 2011-05-05 00:00:00 -04:00
19
+ date: 2011-05-09 00:00:00 -04:00
20
20
  default_executable:
21
21
  dependencies:
22
22
  - !ruby/object:Gem::Dependency