quickbase 0.0.12 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: bb7aa9ed00a1e58a91709c83c6071dc3a8d7a533
4
+ data.tar.gz: 8b727513e2f934821254293bec240a16ca25eb9b
5
+ SHA512:
6
+ metadata.gz: 93dbb3372277f563332168f9a34259b895461ce595cd99cebb1939eade4c722f8a40c8326c6457b8b3d804e4bf89bce752651dea4b10e05ddb3e758a989c3409
7
+ data.tar.gz: 35f9785c73be1def7d3902a418351df6f7888ff7378aeaca230d9a818773644f2f3d892bd6d83e050009f65989c333e07684f8db8ed893a4ef328e29ccc80809
@@ -44,13 +44,20 @@ or, in your Gemfile
44
44
  quickbase.api.delete_record(7)
45
45
 
46
46
  == Setting a proxy
47
-
47
+
48
48
  quickbase = Quickbase::Connection.new(:apptoken => "apptoken", :dbid => "dbid", :http_proxy => "http://my.proxy.com:80")
49
49
 
50
50
  the sytem http_proxy, https_proxy and no_proxy environment variable will be respected if you don't explicity pass a proxy
51
51
 
52
52
  == Changes
53
53
 
54
+ 11/11/2016 - version 0.1.0
55
+ - fix security vulnerabilities to xml injections
56
+ - add vcr to tests
57
+ - add MIT license
58
+ - remove deprecated classes
59
+ - fix warnings with gemspec
60
+
54
61
  04/01/2015
55
62
  - Added proxy support
56
63
 
@@ -1,11 +1,11 @@
1
1
  module Quickbase
2
2
  class API
3
3
  attr_accessor :connection
4
-
4
+
5
5
  def initialize(connection)
6
- instance_variable_set "@connection", connection
6
+ @connection = connection
7
7
  end
8
-
8
+
9
9
  # Documentation at http://www.quickbase.com/api-guide/do_query.html
10
10
  def do_query(params)
11
11
  params[:fmt] = 'structured' if params[:fmt].nil? or params[:fmt].empty?
@@ -17,49 +17,44 @@ module Quickbase
17
17
  records = array_of_records.empty? ? response.xpath("//record") : array_of_records
18
18
  return [] if records.empty?
19
19
 
20
- records.map{|record|
20
+ records.map do |record|
21
21
  array_of_fields = record.xpath("f[@type='array']/f")
22
22
  fields = array_of_fields.empty? ? record.xpath("f") : array_of_fields
23
- Hash[fields.to_enum(:each_with_index).collect{|field,index|
23
+ Hash[fields.to_enum(:each_with_index).collect { |field,index|
24
24
  field_val = ""
25
25
  field_val_xpath = field.xpath("__content__").first
26
26
  field_val = field_val_xpath.content unless field_val_xpath.nil?
27
27
  Hash[keys[index],field_val]
28
28
  }.map(&:flatten)]
29
- }
29
+ end
30
30
  end
31
-
31
+
32
32
  def do_query_return_nokogiri_obj(params)
33
33
  #useful method for debugging
34
34
  params[:fmt] = 'structured' if params[:fmt].nil? or params[:fmt].empty?
35
35
  clist = params[:clist].to_s.split(".")
36
36
  friendly = params[:friendly].to_s.split(".")
37
37
  keys = friendly.empty? ? clist : friendly.map(&:to_sym)
38
- response = connection.http.post("API_DoQuery", Quickbase::Helper.hash_to_xml(params))
39
- return response
38
+ connection.http.post("API_DoQuery", Quickbase::Helper.hash_to_xml(params))
40
39
  end
41
-
40
+
42
41
  # Documentation at http://www.quickbase.com/api-guide/add_record.html
43
42
  def add_record(fields)
44
43
  fields = Quickbase::Helper.generate_fields(fields)
45
44
  connection.http.post("API_AddRecord", fields)
46
45
  end
47
-
46
+
48
47
  # Documentation at http://www.quickbase.com/api-guide/edit_record.html
49
48
  def edit_record(rid, fields)
50
49
  tags = Quickbase::Helper.generate_fields(fields)
51
50
  tags << Quickbase::Helper.hash_to_xml({:rid => rid.to_s})
52
51
  connection.http.post("API_EditRecord", tags)
53
52
  end
54
-
53
+
55
54
  # Documentation at http://www.quickbase.com/api-guide/delete_record.html
56
55
  def delete_record(rid)
57
56
  tags = Quickbase::Helper.hash_to_xml({:rid => rid.to_s})
58
57
  connection.http.post("API_DeleteRecord", tags)
59
58
  end
60
59
  end
61
-
62
- class Api < API
63
- puts "Class Api will be deprecated. Please use API instead."
64
- end
65
- end
60
+ end
@@ -1,9 +1,9 @@
1
1
  module Quickbase
2
2
  class Connection
3
3
  class << self
4
- attr_writer :username, :password, :hours, :apptoken, :dbid, :org, :http_proxy
4
+ attr_writer :username, :password, :hours, :apptoken, :dbid, :org, :http_proxy, :usertoken
5
5
  end
6
- attr_reader :username, :password, :hours, :apptoken, :dbid, :org, :http_proxy
6
+ attr_reader :username, :password, :hours, :apptoken, :dbid, :org, :http_proxy, :usertoken
7
7
 
8
8
  def self.expectant_reader(*attributes)
9
9
  attributes.each do |attribute|
@@ -13,24 +13,25 @@ module Quickbase
13
13
  end
14
14
  end
15
15
  end
16
- expectant_reader :username, :password, :hours, :apptoken, :dbid, :org, :http_proxy
16
+ expectant_reader :username, :password, :hours, :apptoken, :dbid, :org, :http_proxy, :usertoken
17
17
 
18
18
  def initialize(options = {})
19
- [:username, :password, :hours, :apptoken, :dbid, :org, :http_proxy].each do |attr|
19
+ [:username, :password, :hours, :apptoken, :dbid, :org, :http_proxy, :usertoken].each do |attr|
20
20
  instance_variable_set "@#{attr}", (options[attr].nil? ? Quickbase::Connection.send(attr) : options[attr])
21
21
  end
22
22
  instance_variable_set "@org", "www" if org.nil?
23
23
  end
24
24
 
25
25
  def instantiate
26
- config = {
27
- :username => username,
28
- :password => password,
29
- :hours => hours,
30
- :apptoken => apptoken,
31
- :dbid => dbid,
32
- :org => org,
33
- :http_proxy => http_proxy
26
+ {
27
+ username: username,
28
+ password: password,
29
+ hours: hours,
30
+ apptoken: apptoken,
31
+ dbid: dbid,
32
+ org: org,
33
+ http_proxy: http_proxy,
34
+ usertoken: usertoken
34
35
  }
35
36
  end
36
37
 
@@ -42,4 +43,4 @@ module Quickbase
42
43
  Quickbase::API.new(self)
43
44
  end
44
45
  end
45
- end
46
+ end
@@ -1,21 +1,24 @@
1
1
  module Quickbase
2
2
  class Helper
3
- def self.hash_to_xml(hash)
4
- hash.map{|key,value|
3
+ def self.hash_to_xml(my_hash)
4
+ my_hash.map do |k,v|
5
+ key = k.to_s.encode(xml: :text)
6
+ value = v.to_s.encode(xml: :text)
5
7
  "<#{key}>#{value}</#{key}>"
6
- }
8
+ end
7
9
  end
8
-
9
- def self.generate_xml(params)
10
- Nokogiri::XML("<qdbapi>#{params.join}</qdbapi>")
10
+
11
+ def self.generate_xml(xml_input)
12
+ # xml_input is an array of xml strings
13
+ # you can use hash_to_xml to generate it
14
+ Nokogiri::XML("<qdbapi>#{xml_input.join}</qdbapi>")
11
15
  end
12
-
16
+
13
17
  def self.generate_fields(fields)
14
- fields.map{|key,value|
15
- field = "<field "
16
- fid = (key =~ /^[-+]?[0-9]+$/) ? field.concat('fid="'+key.to_s+'"') : field.concat('name="'+key.to_s+'"')
17
- field.concat(">#{value}</field>")
18
- }
18
+ fields.map do |key,value|
19
+ attr_name = (key =~ /^[-+]?[0-9]+$/) ? 'fid' : 'name'
20
+ "<field #{attr_name}=#{key.to_s.encode(xml: :attr)}>#{value.to_s.encode(xml: :text)}</field>"
21
+ end
19
22
  end
20
23
  end
21
- end
24
+ end
@@ -11,9 +11,8 @@ module Quickbase
11
11
  http_proxy = config[:http_proxy] || ENV['http_proxy']
12
12
  setup_proxy(http_proxy) if http_proxy
13
13
 
14
- qb_params[:ticket] = auth_ticket config
15
- qb_params[:apptoken] = config[:apptoken]
16
14
  qb_params[:dbid] = config[:dbid]
15
+ qb_params[:usertoken] = config[:usertoken]
17
16
  end
18
17
 
19
18
  def post(quickbase_action, params = [])
@@ -59,8 +58,4 @@ module Quickbase
59
58
  end
60
59
  end
61
60
  end
62
-
63
- class Http < HTTP
64
- puts "Class Http will be deprecated. Please use HTTP instead."
65
- end
66
- end
61
+ end
@@ -1,6 +1,6 @@
1
1
  Gem::Specification.new do |s|
2
2
  s.name = %q{quickbase}
3
- s.version = "0.0.12"
3
+ s.version = "0.1.0"
4
4
 
5
5
  s.required_rubygems_version = Gem::Requirement.new(">= 1.2") if s.respond_to? :required_rubygems_version=
6
6
  s.authors = ["Artem Kalinchuk"]
@@ -13,6 +13,8 @@ Gem::Specification.new do |s|
13
13
  s.rubyforge_project = %q{quickbase}
14
14
  s.rubygems_version = %q{1.8.5}
15
15
  s.summary = %q{Quickbase Ruby Gem}
16
+ s.homepage = 'https://github.com/kalinchuk/quickbase'
17
+ s.license = 'MIT'
16
18
  s.add_dependency(%q<nokogiri>, [">= 0"])
17
19
  s.add_dependency(%q<httparty>, [">= 0"])
18
20
  s.add_dependency(%q<activesupport>, [">= 0"])
@@ -4,80 +4,91 @@ require 'pp'
4
4
  require 'spec_helper'
5
5
 
6
6
  #fill in your own quickbase account / database
7
- Quickbase::Connection.username = ""
8
- Quickbase::Connection.password = ""
9
- Quickbase::Connection.org = ""
10
- apptoken = ""
11
- dbid = ""
7
+ Quickbase::Connection.username = "username"
8
+ Quickbase::Connection.password = "password"
9
+ Quickbase::Connection.org = "intuitcorp"
10
+ apptoken = "apptoken"
11
+ dbid = "dbid"
12
12
 
13
13
  describe Quickbase::Connection do
14
+ let(:connection) { described_class.new(:apptoken => apptoken, :dbid => dbid) }
15
+ let(:connection_hash) do
16
+ {
17
+ apptoken: connection.apptoken,
18
+ dbid: connection.dbid,
19
+ hours: connection.hours,
20
+ org: connection.org,
21
+ password: connection.password,
22
+ username: connection.username
23
+ }
24
+ end
25
+
26
+ let(:default_values_hash) do
27
+ {
28
+ apptoken: apptoken,
29
+ dbid: dbid,
30
+ hours: nil,
31
+ org: described_class.org,
32
+ password: described_class.password,
33
+ username: described_class.username
34
+ }
35
+ end
36
+
14
37
  describe "initialize" do
15
38
  it "initializes successfully" do
16
- quickbase = Quickbase::Connection.new(:apptoken => apptoken, :dbid => dbid)
17
-
18
- connection_hash = {
19
- :apptoken => quickbase.apptoken,
20
- :dbid => quickbase.dbid,
21
- :hours => quickbase.hours,
22
- :org => quickbase.org,
23
- :password => quickbase.password,
24
- :username => quickbase.username
25
- }
26
-
27
- default_values_hash = {
28
- :apptoken => apptoken,
29
- :dbid => dbid,
30
- :hours => nil,
31
- :org => Quickbase::Connection.org,
32
- :password => Quickbase::Connection.password,
33
- :username => Quickbase::Connection.username
34
- }
35
-
36
- connection_hash.should == default_values_hash
39
+ expect(connection_hash).to eq default_values_hash
37
40
  end
38
41
  end
39
42
  end
40
43
 
41
44
  describe Quickbase::Helper do
42
45
  describe "self.hash_to_xml" do
43
- it "creates XML out of a hash" do
44
- hash = {:test => "this is the content of the test tag", :test2 => "contents of test2"}
45
-
46
- Quickbase::Helper.hash_to_xml(hash).join.should == "<test>this is the content of the test tag</test><test2>contents of test2</test2>"
47
- end
46
+ let(:params) { {test: "this is the content of the test tag", test2: "contents of test2"} }
47
+ let(:result) { ["<test>this is the content of the test tag</test>", "<test2>contents of test2</test2>"] }
48
+
49
+ subject { described_class.hash_to_xml(params) }
50
+
51
+ it { is_expected.to eq result }
48
52
  end
49
-
53
+
50
54
  describe "self.generate_xml" do
51
- it "returns a formatted Quickbase XML" do
52
- hash = {:test => "this is the content of the test tag", :test2 => "contents of test2"}
53
- Quickbase::Helper.generate_xml(Quickbase::Helper.hash_to_xml(hash)).to_s.should == Nokogiri::XML("<qdbapi><test>this is the content of the test tag</test><test2>contents of test2</test2></qdbapi>").to_s
55
+ let(:input) { ["<test>this is the content of the test tag</test>", "<test2>contents of test2</test2>"] }
56
+ let(:expect_xml) { Nokogiri::XML("<qdbapi><test>this is the content of the test tag</test><test2>contents of test2</test2></qdbapi>") }
57
+
58
+ subject { described_class.generate_xml(input).to_s }
59
+
60
+ it 'returns a formatted Quickbase XML' do
61
+ expect(subject).to eq expect_xml.to_s
54
62
  end
55
63
  end
56
-
64
+
57
65
  describe "self.generate_fields" do
58
- it "creates an array of tags with all the fields" do
59
- fields = {:first_name => "John", :last_name => "Smith"}
60
- Quickbase::Helper.generate_fields(fields).should == ["<field name=\"first_name\">John</field>", "<field name=\"last_name\">Smith</field>"]
61
- end
66
+ let(:fields) { {first_name: "John", last_name: "Smith"} }
67
+ let(:result) { ["<field name=\"first_name\">John</field>", "<field name=\"last_name\">Smith</field>"] }
68
+
69
+ subject { described_class.generate_fields(fields) }
70
+
71
+ it { is_expected.to eq result }
62
72
  end
63
73
  end
64
74
 
65
75
  describe Quickbase::API do
66
- describe "do_query" do
67
- it "queries for data" do
68
- quickbase = Quickbase::Connection.new(:apptoken => apptoken, :dbid => dbid)
69
-
70
- results = quickbase.api.do_query(:query => "{'1'.XEX.'1'}", :clist => "1.2", :slist => "1")
71
- results.length.should_not == 0
72
- end
76
+ let(:connection) { Quickbase::Connection.new(apptoken: apptoken, dbid: dbid) }
77
+ let(:api) { connection.api }
78
+
79
+ describe "do_query", vcr: {cassette_name: 'do_query'} do
80
+ subject { api.do_query(query: "{'1'.XEX.'1'}", clist: "1.2", slist: "1") }
81
+
82
+ it { is_expected.to eq [{"1"=>"1280355979800", "2"=>"1280355979800"}, {"1"=>"1280355979800", "2"=>"1280355979800"}] }
73
83
  end
74
-
75
- describe "do_query_return_xml" do
76
- it "return xml" do
77
- quickbase = Quickbase::Connection.new(:apptoken => apptoken, :dbid => dbid)
78
-
79
- xml = quickbase.api.do_query_return_nokogiri_obj(:query => "{'1'.XEX.'1'}", :clist => "1.2", :slist => "1")
80
- xml.class.to_s.should == "Nokogiri::XML::Document"
84
+
85
+ describe "do_query_return_xml", vcr: {cassette_name: 'do_query'} do
86
+ let(:xml_response) { IO.read('./spec/fixtures/xml_response.xml') }
87
+ subject { api.do_query_return_nokogiri_obj(query: "{'1'.XEX.'1'}", clist: "1.2", slist: "1") }
88
+
89
+ it "returns xml" do
90
+ expect(subject).to be_a_kind_of Nokogiri::XML::Document
91
+ expect(subject.to_s).to eq xml_response
81
92
  end
82
93
  end
83
- end
94
+ end
metadata CHANGED
@@ -1,8 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: quickbase
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.12
5
- prerelease:
4
+ version: 0.1.0
6
5
  platform: ruby
7
6
  authors:
8
7
  - Artem Kalinchuk
@@ -14,49 +13,43 @@ dependencies:
14
13
  - !ruby/object:Gem::Dependency
15
14
  name: nokogiri
16
15
  requirement: !ruby/object:Gem::Requirement
17
- none: false
18
16
  requirements:
19
- - - ! '>='
17
+ - - ">="
20
18
  - !ruby/object:Gem::Version
21
19
  version: '0'
22
20
  type: :runtime
23
21
  prerelease: false
24
22
  version_requirements: !ruby/object:Gem::Requirement
25
- none: false
26
23
  requirements:
27
- - - ! '>='
24
+ - - ">="
28
25
  - !ruby/object:Gem::Version
29
26
  version: '0'
30
27
  - !ruby/object:Gem::Dependency
31
28
  name: httparty
32
29
  requirement: !ruby/object:Gem::Requirement
33
- none: false
34
30
  requirements:
35
- - - ! '>='
31
+ - - ">="
36
32
  - !ruby/object:Gem::Version
37
33
  version: '0'
38
34
  type: :runtime
39
35
  prerelease: false
40
36
  version_requirements: !ruby/object:Gem::Requirement
41
- none: false
42
37
  requirements:
43
- - - ! '>='
38
+ - - ">="
44
39
  - !ruby/object:Gem::Version
45
40
  version: '0'
46
41
  - !ruby/object:Gem::Dependency
47
42
  name: activesupport
48
43
  requirement: !ruby/object:Gem::Requirement
49
- none: false
50
44
  requirements:
51
- - - ! '>='
45
+ - - ">="
52
46
  - !ruby/object:Gem::Version
53
47
  version: '0'
54
48
  type: :runtime
55
49
  prerelease: false
56
50
  version_requirements: !ruby/object:Gem::Requirement
57
- none: false
58
51
  requirements:
59
- - - ! '>='
52
+ - - ">="
60
53
  - !ruby/object:Gem::Version
61
54
  version: '0'
62
55
  description: The Quickbase Gem provides integration access to the Intuit Quickbase
@@ -66,40 +59,40 @@ executables: []
66
59
  extensions: []
67
60
  extra_rdoc_files: []
68
61
  files:
69
- - lib/quickbase.rb
70
- - quickbase.gemspec
71
62
  - README.rdoc
72
63
  - lib/classes/api.rb
73
64
  - lib/classes/connection.rb
74
65
  - lib/classes/helper.rb
75
66
  - lib/classes/http.rb
67
+ - lib/quickbase.rb
68
+ - quickbase.gemspec
76
69
  - spec/quickbase_spec.rb
77
- homepage:
78
- licenses: []
70
+ homepage: https://github.com/kalinchuk/quickbase
71
+ licenses:
72
+ - MIT
73
+ metadata: {}
79
74
  post_install_message:
80
75
  rdoc_options:
81
- - --line-numbers
82
- - --inline-source
83
- - --title
76
+ - "--line-numbers"
77
+ - "--inline-source"
78
+ - "--title"
84
79
  - Quickbase
85
80
  require_paths:
86
81
  - lib
87
82
  required_ruby_version: !ruby/object:Gem::Requirement
88
- none: false
89
83
  requirements:
90
- - - ! '>='
84
+ - - ">="
91
85
  - !ruby/object:Gem::Version
92
86
  version: '0'
93
87
  required_rubygems_version: !ruby/object:Gem::Requirement
94
- none: false
95
88
  requirements:
96
- - - ! '>='
89
+ - - ">="
97
90
  - !ruby/object:Gem::Version
98
91
  version: '1.2'
99
92
  requirements: []
100
93
  rubyforge_project: quickbase
101
- rubygems_version: 1.8.23.2
94
+ rubygems_version: 2.4.6
102
95
  signing_key:
103
- specification_version: 3
96
+ specification_version: 4
104
97
  summary: Quickbase Ruby Gem
105
98
  test_files: []