Skip to content

Commit

Permalink
Initial commit
Browse files Browse the repository at this point in the history
  • Loading branch information
taylorbrooks committed Feb 4, 2024
0 parents commit 3d11f60
Show file tree
Hide file tree
Showing 24 changed files with 706 additions and 0 deletions.
22 changes: 22 additions & 0 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
name: Run specs

on:
push:
branches: [ master ]
pull_request:
branches: [ master ]

jobs:
test:
runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v2
- name: Set up Ruby
uses: ruby/setup-ruby@v1
with:
bundler-cache: true
- name: Install dependencies
run: bundle install
- name: Run tests
run: bundle exec rspec
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
shelby_arena-*.gem
.env
Gemfile.lock
.DS_Store
1 change: 1 addition & 0 deletions .ruby-version
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
2.7.4
1 change: 1 addition & 0 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
language: ruby
3 changes: 3 additions & 0 deletions Gemfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
source 'https://rubygems.org'

gemspec
22 changes: 22 additions & 0 deletions LICENSE
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
Copyright (c) 2013 Taylor Brooks

MIT License

Permission is hereby granted, free of charge, to any person obtaining
a copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sublicense, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:

The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
50 changes: 50 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
# Shelby Arena Ruby Client ![example workflow](https://github.com/taylorbrooks/shelby_arena/actions/workflows/test.yml/badge.svg)

A Ruby wrapper for the Shelby Arena API

### Installation
Add this line to your application's Gemfile:
````ruby
# in your Gemfile
gem 'shelby_arena', '~> 0.0.1'

# then...
bundle install
````

### Usage
````ruby
# Authenticating with username and password
client = ShelbyArena::Client.new(
url: ...,
username: ...,
password: ...,
)

# Authenticating with authorization token
client = ShelbyArena::Client.new(
url: ...,
authorization_token: ...,
)

# Find a specific person
client.find_person_by_email('gob@bluthco.com')
client.find_person_by_name('Tobias Funke')
````

### History

View the [changelog](https://github.com/taylorbrooks/shelby_arena/blob/master/CHANGELOG.md)
This gem follows [Semantic Versioning](http://semver.org/)

### Contributing

Everyone is encouraged to help improve this project. Here are a few ways you can help:

- [Report bugs](https://github.com/taylorbrooks/shelby_arena/issues)
- Fix bugs and [submit pull requests](https://github.com/taylorbrooks/shelby_arena/pulls)
- Write, clarify, or fix documentation
- Suggest or add new features

### Copyright
Copyright (c) 2023 Taylor Brooks. See LICENSE for details.
14 changes: 14 additions & 0 deletions Rakefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
require 'bundler/gem_tasks'
require 'rspec/core/rake_task'

RSpec::Core::RakeTask.new(:spec)

task default: :spec

task :environment do
require 'dotenv'
Dotenv.load

$LOAD_PATH.unshift File.expand_path('../lib', __FILE__)
require 'shelby_arena'
end
19 changes: 19 additions & 0 deletions bin/rspec
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
#!/usr/bin/env ruby
# frozen_string_literal: true

# This file was generated by Bundler.
#
# The application 'rspec' is installed as part of a gem, and
# this file is here to facilitate running it.
#

require 'pathname'
ENV['BUNDLE_GEMFILE'] ||= File.expand_path(
'../../Gemfile',
Pathname.new(__FILE__).realpath
)

require 'rubygems'
require 'bundler/setup'

load Gem.bin_path('rspec-core', 'rspec')
6 changes: 6 additions & 0 deletions lib/shelby_arena.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
require_relative 'shelby_arena/client'
require_relative 'shelby_arena/error'
require_relative 'shelby_arena/version'

module ShelbyArena
end
101 changes: 101 additions & 0 deletions lib/shelby_arena/client.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,101 @@
require 'faraday'

Dir[File.expand_path('../resources/*.rb', __FILE__)].each { |f| require f }
require File.expand_path('../response/base.rb', __FILE__)
Dir[File.expand_path('../response/*.rb', __FILE__)].each { |f| require f }

module ShelbyArena
class Client
include ShelbyArena::Client::Batch
include ShelbyArena::Client::Fund
include ShelbyArena::Client::Person
include ShelbyArena::Client::Contribution

attr_reader :url, :username, :password, :logger, :connection, :adapter, :ssl, :api_key, :api_secret, :api_session

def initialize(url:, username:, password:, api_key:, api_secret:, logger: true, adapter: Faraday.default_adapter, ssl: nil)
if username.nil? && password.nil?
raise ArgumentError, 'either username and password'
end

@url = "#{url}/api.svc/"
@username = username
@password = password
@api_key = api_key
@api_secret = api_secret
@logger = logger
@adapter = adapter
@ssl = ssl
@api_session = fetch_api_session
end

def delete(path, options = {})
connection.delete(path, options).body
end

def get(path, options = {})
connection.get(path, options).body
end

def patch(path, options = {})
connection.patch(path, options).body
end

def post(path, options = {})
connection.post(path, options).body
end

def json_post(path, options = {})
connection(true).post(path, options).body
end

def put(path, options = {})
connection.put(path, options).body
end

private

def fetch_api_session
params = {
username: username,
password: password,
api_key: api_key
}

res = post('login', **params)

res.dig('ApiSession', 'SessionID')
end

def generate_api_sig(path, options = {})
options[:api_session] = api_session
params = Faraday::FlatParamsEncoder.encode(options)
thing_to_hash = "#{api_secret}_#{path}?#{params}".downcase
Digest::MD5.hexdigest(thing_to_hash)
end

def connection(json = false)
headers = {
accept: 'application/json',
'User-Agent' => "shelby-arena-ruby-gem/v#{ShelbyArena::VERSION}"
}

headers['Content-Type'] = 'application/json' if json

client_opts = {
url: url,
headers: headers
}

client_opts[:ssl] = ssl if ssl

Faraday.new(client_opts) do |conn|
conn.request :url_encoded
conn.response :logger if logger
conn.response :xml
conn.use FaradayMiddleware::ShelbyArenaErrorHandler
conn.adapter adapter
end
end
end
end
50 changes: 50 additions & 0 deletions lib/shelby_arena/error.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
module ShelbyArena
class Error < StandardError; end
class BadGateway < Error; end
class BadRequest < Error; end
class CloudflareError < Error; end
class Forbidden < Error; end
class GatewayTimeout < Error; end
class InternalServerError < Error; end
class NotFound < Error; end
class ServiceUnavailable < Error; end
class Unauthorized < Error; end
end

require 'faraday'
module FaradayMiddleware
class ShelbyArenaErrorHandler < Faraday::Middleware
ERROR_STATUSES = 400..600

def on_complete(env)
case env[:status]
when 400
raise ShelbyArena::BadRequest, error_message(env)
when 401
raise ShelbyArena::Unauthorized, error_message(env)
when 403
raise ShelbyArena::Forbidden, error_message(env)
when 404
raise ShelbyArena::NotFound, error_message(env)
when 500
raise ShelbyArena::InternalServerError, error_message(env)
when 502
raise ShelbyArena::BadGateway, error_message(env)
when 503
raise ShelbyArena::ServiceUnavailable, error_message(env)
when 504
raise ShelbyArena::GatewayTimeout, error_message(env)
when 520
raise ShelbyArena::CloudflareError, error_message(env)
when ERROR_STATUSES
raise ShelbyArena::Error, error_message(env)
end
end

private

def error_message(env)
"#{env[:status]}: #{env[:url]} #{env[:body]}"
end
end
end
43 changes: 43 additions & 0 deletions lib/shelby_arena/resources/batch.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
module ShelbyArena
class Client
module Batch
def list_batches(options = {})
path = 'batch/list'
options[:api_sig] = generate_api_sig(path, options)

res = get(path, options.sort)
Response::Batch.format(res.dig('BatchListResult', 'Batches', 'Batch'))
end

def find_batch(id, options = {})
path = "batch/#{id}"
options[:api_sig] = generate_api_sig(path, options)

res = get(path, options.sort)
Response::Batch.format(res.dig('Batch'))
end

def create_batch(name:, start_date:, end_date:)
path = 'batch/add'
body = {
BatchName: name,
BatchDate: start_date,
BatchDateEnd: end_date
}

options = {}
options[:api_sig] = generate_api_sig(path, options)
json_body = body.to_json

json_post("#{path}?api_session=#{options[:api_session]}&api_sig=#{options[:api_sig]}", json_body)
end

def delete_batch(id, options = {})
path = "batch/#{id}"
options[:api_sig] = generate_api_sig(path, options)
require 'pry'; binding.pry
delete(path, options.sort)
end
end
end
end
Loading

0 comments on commit 3d11f60

Please sign in to comment.