Class: Latch

Inherits:
Object
  • Object
show all
Defined in:
lib/latchsdk.rb

Constant Summary collapse

API_HOST =
"https://latch.elevenpaths.com"
API_VERSION =
"0.6"
API_CHECK_STATUS_URL =
"/api/0.6/status"
API_PAIR_URL =
"/api/0.6/pair"
API_PAIR_WITH_ID_URL =
"/api/0.6/pairWithId"
API_UNPAIR_URL =
"/api/0.6/unpair"
AUTHORIZATION_HEADER_NAME =
"Authorization"
DATE_HEADER_NAME =
"X-11Paths-Date"
AUTHORIZATION_METHOD =
"11PATHS"
AUTHORIZATION_HEADER_FIELD_SEPARATOR =
" "
HMAC_ALGORITHM =
"sha1"
X_11PATHS_HEADER_PREFIX =
"X-11Paths-"
X_11PATHS_HEADER_SEPARATOR =
":"

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(appid, secret) ⇒ Latch

Create an instance of the class with the Application ID and secret obtained from Eleven Paths

Parameters:

  • $appId
  • $secretKey


89
90
91
92
93
# File 'lib/latchsdk.rb', line 89

def initialize(appid, secret)
	@appid = appid
	@secret = secret
  @api_host = API_HOST
end

Instance Attribute Details

#api_hostObject

Returns the value of attribute api_host.



29
30
31
# File 'lib/latchsdk.rb', line 29

def api_host
  @api_host
end

Instance Method Details

#authenticationHeaders(httpMethod, queryString, xHeaders = nil, utc = nil) ⇒ Object

Calculate the authentication headers to be sent with a request to the API

Parameters:

  • $HTTPMethod

    the HTTP Method, currently only GET is supported

  • $queryString

    the urlencoded string including the path (from the first forward slash) and the parameters

  • $xHeaders

    HTTP headers specific to the 11-paths API. null if not needed.

  • $utc

    the Universal Coordinated Time for the Date HTTP header

Returns:

  • array a map with the Authorization and Date headers needed to sign a Latch API request



161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
# File 'lib/latchsdk.rb', line 161

def authenticationHeaders(httpMethod, queryString, xHeaders=nil, utc=nil)
	if (utc == nil)
		utc = getCurrentUTC
	end

	stringToSign = (httpMethod.upcase).strip + "\n" +
					utc.to_s + "\n" +
					getSerializedHeaders(xHeaders) + "\n" +
					queryString.strip

	authorizationHeader = AUTHORIZATION_METHOD +
						   AUTHORIZATION_HEADER_FIELD_SEPARATOR +
						   @appid +
						   AUTHORIZATION_HEADER_FIELD_SEPARATOR +
						   signData(stringToSign).chop

	headers = {}
	headers[AUTHORIZATION_HEADER_NAME] = authorizationHeader
	headers[DATE_HEADER_NAME] = utc
	return headers
end

#getAppIdFromHeader(authorizationHeader) ⇒ Object

Returns string the requesting application Id. Identifies the application using the API.

Parameters:

  • $authorizationHeader

    Authorization HTTP Header

Returns:

  • string the requesting application Id. Identifies the application using the API



74
75
76
# File 'lib/latchsdk.rb', line 74

def getAppIdFromHeader(authorizationHeader)
	getPartFromHeader(1, authorizationHeader)
end

#getAuthMethodFromHeader(authorizationHeader) ⇒ Object

Returns string the Authorization method. Typical values are “Basic”, “Digest” or “11PATHS”.

Parameters:

  • $authorizationHeader

    Authorization HTTP Header

Returns:

  • string the Authorization method. Typical values are “Basic”, “Digest” or “11PATHS”



68
69
70
# File 'lib/latchsdk.rb', line 68

def getAuthMethodFromHeader(authorizationHeader)
		getPartFromHeader(0, authorizationHeader)
end

#getCurrentUTCObject

Returns a string representation of the current time in UTC to be used in a Date HTTP Header.

Returns:

  • a string representation of the current time in UTC to be used in a Date HTTP Header



214
215
216
# File 'lib/latchsdk.rb', line 214

def getCurrentUTC
	Time.now.utc
end

#getPartFromHeader(part, header) ⇒ Object

The custom header consists of three parts, the method, the appId and the signature. This method returns the specified part if it exists.

Parameters:

  • $part

    The zero indexed part to be returned

  • $header

    The HTTP header value from which to extract the part

Returns:

  • string the specified part from the header or an empty string if not existent



56
57
58
59
60
61
62
63
64
# File 'lib/latchsdk.rb', line 56

def getPartFromHeader(part, header)
	if (header.empty?)
		parts = header.split(AUTHORIZATION_HEADER_FIELD_SEPARATOR)
		if(parts.length > part)
			return parts[part]
		end
	end
	return ""
end

#getSerializedHeaders(xHeaders) ⇒ Object

Prepares and returns a string ready to be signed from the 11-paths specific HTTP headers received such as non 11paths specific headers

Parameters:

  • $xHeaders

    a non necessarily ordered map of the HTTP headers to be ordered without duplicates.

Returns:

  • a String with the serialized headers, an empty string if no headers are passed, or null if there’s a problem



189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
# File 'lib/latchsdk.rb', line 189

def getSerializedHeaders(xHeaders)
	if(xHeaders != nil)
		headers = xHeaders.inject({}) do |xHeaders, keys|
		  hash[keys[0].downcase] = keys[1]
		  hash
		end


		serializedHeaders = ''

		headers.sort.map do |key,value|
			if(key.downcase == X_11PATHS_HEADER_PREFIX.downcase)
				puts "Error serializing headers. Only specific " + X_11PATHS_HEADER_PREFIX + " headers need to be singed"
				return nil
			end
			serializedHeaders += key + X_11PATHS_HEADER_SEPARATOR + value + ' '
		end
		substitute = 'utf-8'
		return serializedHeaders.gsub(/^[#{substitute}]+|[#{substitute}]+$/, '')
	else
		return ""
	end
end

#getSignatureFromHeader(authorizationHeader) ⇒ Object

Returns string the signature of the current request. Verifies the identity of the application using the API.

Parameters:

  • $authorizationHeader

    Authorization HTTP Header

Returns:

  • string the signature of the current request. Verifies the identity of the application using the API



81
82
83
# File 'lib/latchsdk.rb', line 81

def getSignatureFromHeader(authorizationHeader)
	getPartFromHeader(2, authorizationHeader)
end

#http_get(url, headers) ⇒ Object



96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
# File 'lib/latchsdk.rb', line 96

def http_get(url, headers)
	     uri = URI.parse(url)
		http = Net::HTTP.new(uri.host, uri.port)

       if (uri.default_port == 443)
  http.use_ssl = true
  http.verify_mode = OpenSSL::SSL::VERIFY_NONE
       end


		request = Net::HTTP::Get.new(uri.request_uri)

		headers.map do |key,value|
			request[key] = value
		end

		response = http.request(request)
		response.body
end

#http_get_proxy(url) ⇒ Object



117
118
119
# File 'lib/latchsdk.rb', line 117

def http_get_proxy(url)
	LatchResponse.new(http_get(api_host + url, authenticationHeaders('GET', url, nil)))
end

#operationStatus(accountId, operationId) ⇒ Object



137
138
139
# File 'lib/latchsdk.rb', line 137

def operationStatus(accountId, operationId)
	http_get_proxy(API_CHECK_STATUS_URL + "/" + accountId + '/' + operationId)
end

#pair(token) ⇒ Object



127
128
129
# File 'lib/latchsdk.rb', line 127

def pair(token)
	http_get_proxy(API_PAIR_URL + '/' + token)
end

#pairWithId(accountId) ⇒ Object



122
123
124
# File 'lib/latchsdk.rb', line 122

def pairWithId(accountId)
	http_get_proxy(API_PAIR_WITH_ID_URL + '/' + accountId)
end

#signData(data) ⇒ Object

Returns string base64 encoding of the HMAC-SHA1 hash of the data parameter using secretKey as cipher key.

Parameters:

  • $data

    the string to sign

Returns:

  • string base64 encoding of the HMAC-SHA1 hash of the data parameter using secretKey as cipher key.



150
151
152
# File 'lib/latchsdk.rb', line 150

def signData(data)
	Base64.encode64(OpenSSL::HMAC.digest(HMAC_ALGORITHM, @secret, data))
end

#status(accountId) ⇒ Object



132
133
134
# File 'lib/latchsdk.rb', line 132

def status(accountId)
	http_get_proxy(API_CHECK_STATUS_URL + '/' + accountId)
end

#unpair(accountId) ⇒ Object



142
143
144
# File 'lib/latchsdk.rb', line 142

def unpair(accountId)
	http_get_proxy(API_UNPAIR_URL + '/' + accountId)
end