net-sftp-backports 4.0.0.backports
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.github/workflows/ci.yml +35 -0
- data/.gitignore +6 -0
- data/CHANGES.txt +67 -0
- data/Gemfile +15 -0
- data/LICENSE.txt +19 -0
- data/Manifest +55 -0
- data/README.rdoc +118 -0
- data/Rakefile +53 -0
- data/lib/net/sftp/constants.rb +187 -0
- data/lib/net/sftp/errors.rb +39 -0
- data/lib/net/sftp/operations/dir.rb +93 -0
- data/lib/net/sftp/operations/download.rb +365 -0
- data/lib/net/sftp/operations/file.rb +198 -0
- data/lib/net/sftp/operations/file_factory.rb +60 -0
- data/lib/net/sftp/operations/upload.rb +395 -0
- data/lib/net/sftp/packet.rb +21 -0
- data/lib/net/sftp/protocol/01/attributes.rb +315 -0
- data/lib/net/sftp/protocol/01/base.rb +268 -0
- data/lib/net/sftp/protocol/01/name.rb +43 -0
- data/lib/net/sftp/protocol/02/base.rb +31 -0
- data/lib/net/sftp/protocol/03/base.rb +35 -0
- data/lib/net/sftp/protocol/04/attributes.rb +152 -0
- data/lib/net/sftp/protocol/04/base.rb +94 -0
- data/lib/net/sftp/protocol/04/name.rb +67 -0
- data/lib/net/sftp/protocol/05/base.rb +66 -0
- data/lib/net/sftp/protocol/06/attributes.rb +107 -0
- data/lib/net/sftp/protocol/06/base.rb +63 -0
- data/lib/net/sftp/protocol/base.rb +50 -0
- data/lib/net/sftp/protocol.rb +32 -0
- data/lib/net/sftp/request.rb +91 -0
- data/lib/net/sftp/response.rb +76 -0
- data/lib/net/sftp/session.rb +954 -0
- data/lib/net/sftp/version.rb +68 -0
- data/lib/net/sftp.rb +78 -0
- data/net-sftp-public_cert.pem +20 -0
- data/net-sftp.gemspec +48 -0
- data/setup.rb +1331 -0
- metadata +132 -0
@@ -0,0 +1,91 @@
|
|
1
|
+
require 'net/sftp/constants'
|
2
|
+
require 'net/sftp/response'
|
3
|
+
|
4
|
+
module Net; module SFTP
|
5
|
+
|
6
|
+
# Encapsulates a single active SFTP request. This is instantiated
|
7
|
+
# automatically by the Net::SFTP::Session class when an operation is
|
8
|
+
# executed.
|
9
|
+
#
|
10
|
+
# request = sftp.open("/path/to/file")
|
11
|
+
# puts request.pending? #-> true
|
12
|
+
# request.wait
|
13
|
+
# puts request.pending? #-> false
|
14
|
+
# result = request.response
|
15
|
+
class Request
|
16
|
+
include Constants::PacketTypes
|
17
|
+
|
18
|
+
# The Net::SFTP session object that is servicing this request
|
19
|
+
attr_reader :session
|
20
|
+
|
21
|
+
# The SFTP packet identifier for this request
|
22
|
+
attr_reader :id
|
23
|
+
|
24
|
+
# The type of this request (e.g., :open, :symlink, etc.)
|
25
|
+
attr_reader :type
|
26
|
+
|
27
|
+
# The callback (if any) associated with this request. When the response
|
28
|
+
# is recieved for this request, the callback will be invoked.
|
29
|
+
attr_reader :callback
|
30
|
+
|
31
|
+
# The hash of properties associated with this request. Properties allow
|
32
|
+
# programmers to associate arbitrary data with a request, making state
|
33
|
+
# machines richer.
|
34
|
+
attr_reader :properties
|
35
|
+
|
36
|
+
# The response that was received for this request (see Net::SFTP::Response)
|
37
|
+
attr_reader :response
|
38
|
+
|
39
|
+
# Instantiate a new Request object, serviced by the given +session+, and
|
40
|
+
# being of the given +type+. The +id+ is the packet identifier for this
|
41
|
+
# request.
|
42
|
+
def initialize(session, type, id, &callback) #:nodoc:
|
43
|
+
@session, @id, @type, @callback = session, id, type, callback
|
44
|
+
@response = nil
|
45
|
+
@properties = {}
|
46
|
+
end
|
47
|
+
|
48
|
+
# Returns the value of property with the given +key+. If +key+ is not a
|
49
|
+
# symbol, it will be converted to a symbol before lookup.
|
50
|
+
def [](key)
|
51
|
+
properties[key.to_sym]
|
52
|
+
end
|
53
|
+
|
54
|
+
# Sets the value of the property with name +key+ to +value+. If +key+ is
|
55
|
+
# not a symbol, it will be converted to a symbol before lookup.
|
56
|
+
def []=(key, value)
|
57
|
+
properties[key.to_sym] = value
|
58
|
+
end
|
59
|
+
|
60
|
+
# Returns +true+ if the request is still waiting for a response from the
|
61
|
+
# server, and +false+ otherwise. The SSH event loop must be run in order
|
62
|
+
# for a request to be processed; see #wait.
|
63
|
+
def pending?
|
64
|
+
session.pending_requests.key?(id)
|
65
|
+
end
|
66
|
+
|
67
|
+
# Waits (blocks) until the server responds to this packet. If prior
|
68
|
+
# SFTP packets were also pending, they will be processed as well (since
|
69
|
+
# SFTP packets are processed in the order in which they are received by
|
70
|
+
# the server). Returns the request object itself.
|
71
|
+
def wait
|
72
|
+
session.loop { pending? }
|
73
|
+
self
|
74
|
+
end
|
75
|
+
|
76
|
+
public # but not "published". Internal use only
|
77
|
+
|
78
|
+
# When the server responds to this request, the packet is passed to
|
79
|
+
# this method, which parses the packet and builds a Net::SFTP::Response
|
80
|
+
# object to encapsulate it. If a #callback has been provided for this
|
81
|
+
# request, the callback is invoked with the new response object.
|
82
|
+
def respond_to(packet) #:nodoc:
|
83
|
+
data = session.protocol.parse(packet)
|
84
|
+
data[:type] = packet.type
|
85
|
+
@response = Response.new(self, data)
|
86
|
+
|
87
|
+
callback.call(@response) if callback
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
end; end
|
@@ -0,0 +1,76 @@
|
|
1
|
+
require 'net/sftp/constants'
|
2
|
+
|
3
|
+
module Net; module SFTP
|
4
|
+
|
5
|
+
# Encapsulates a response from the remote server, to a specific client
|
6
|
+
# request. Response objects are passed as parameters to callbacks when you
|
7
|
+
# are performing asynchronous operations; when you call Net::SFTP::Request#wait,
|
8
|
+
# you can get the corresponding response object via Net::SFTP::Request#response.
|
9
|
+
#
|
10
|
+
# sftp.open("/path/to/file") do |response|
|
11
|
+
# p response.ok?
|
12
|
+
# p response[:handle]
|
13
|
+
# end
|
14
|
+
#
|
15
|
+
# sftp.loop
|
16
|
+
class Response
|
17
|
+
include Net::SFTP::Constants::StatusCodes
|
18
|
+
|
19
|
+
# The request object that this object is in response to
|
20
|
+
attr_reader :request
|
21
|
+
|
22
|
+
# A hash of request-specific data, such as a file handle or attribute information
|
23
|
+
attr_reader :data
|
24
|
+
|
25
|
+
# The numeric code, one of the FX_* constants
|
26
|
+
attr_reader :code
|
27
|
+
|
28
|
+
# The textual message for this response (possibly blank)
|
29
|
+
attr_reader :message
|
30
|
+
|
31
|
+
# Create a new Response object for the given Net::SFTP::Request instance,
|
32
|
+
# and with the given data. If there is no :code key in the data, the
|
33
|
+
# code is assumed to be FX_OK.
|
34
|
+
def initialize(request, data={}) #:nodoc:
|
35
|
+
@request, @data = request, data
|
36
|
+
@code, @message = data[:code] || FX_OK, data[:message]
|
37
|
+
end
|
38
|
+
|
39
|
+
# Retrieve the data item with the given +key+. The key is converted to a
|
40
|
+
# symbol before being used to lookup the value.
|
41
|
+
def [](key)
|
42
|
+
data[key.to_sym]
|
43
|
+
end
|
44
|
+
|
45
|
+
# Returns a textual description of this response, including the status
|
46
|
+
# code and name.
|
47
|
+
def to_s
|
48
|
+
if message && !message.empty? && message.downcase != MAP[code]
|
49
|
+
"#{message} (#{MAP[code]}, #{code})"
|
50
|
+
else
|
51
|
+
"#{MAP[code]} (#{code})"
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
alias :to_str :to_s
|
56
|
+
|
57
|
+
# Returns +true+ if the status code is FX_OK; +false+ otherwise.
|
58
|
+
def ok?
|
59
|
+
code == FX_OK
|
60
|
+
end
|
61
|
+
|
62
|
+
# Returns +true+ if the status code is FX_EOF; +false+ otherwise.
|
63
|
+
def eof?
|
64
|
+
code == FX_EOF
|
65
|
+
end
|
66
|
+
|
67
|
+
#--
|
68
|
+
MAP = constants.inject({}) do |memo, name|
|
69
|
+
next memo unless name =~ /^FX_(.*)/
|
70
|
+
memo[const_get(name)] = $1.downcase.tr("_", " ")
|
71
|
+
memo
|
72
|
+
end
|
73
|
+
#++
|
74
|
+
end
|
75
|
+
|
76
|
+
end; end
|