Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

236 simple api #241

Open
wants to merge 34 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 11 commits
Commits
Show all changes
34 commits
Select commit Hold shift + click to select a range
1ad6247
Update minitest to version 5.8.2
sferik Oct 29, 2015
900eae4
Update webmock to version 1.22.2
sferik Oct 29, 2015
43f7697
Create Adopted controller for API, and wrote initial auth/authorizati…
May 1, 2017
3b65084
Add API route, and setting to allow for basic_auth
May 1, 2017
69d6af7
Forgot to add the helper file
May 1, 2017
b1b4305
Edited authentication controller so that a session isn't created on t…
May 2, 2017
91b0e3b
Adopted Drains API controller test
May 2, 2017
7371587
Trying to fix Travis CI errors
May 2, 2017
15fae71
Added formatting for different content types, and edited fields to be…
May 2, 2017
7287643
(Finally realized I can run Rubocop on my local machine)
May 2, 2017
160a045
More controller tests
May 2, 2017
0b4dab3
Add Faker gem in order to make sample users
Jun 20, 2017
ceca853
Adding some user seeds
Jun 20, 2017
b8fff22
Added a rake task for DEV so mock users can automatically adopt drain…
Jul 24, 2017
88a33a7
Passing rubocop
Jul 24, 2017
b893346
Changing !nil to nil... !nil evaluates to true
Jul 25, 2017
973efac
Initial comments for cursor funcionality
Jul 26, 2017
5f868d1
Adding Kaminari gem for pagination
Aug 14, 2017
5772058
added pagination functionality to API
Aug 14, 2017
da2f4b1
Made is so that a CSV template is rendered with all results rather th…
Aug 14, 2017
01c0719
auto_adopt task comment for further clarification
Aug 14, 2017
343a600
Updated dev-envt config file
Dec 15, 2017
78c0c75
temporarily changed asset host
Dec 15, 2017
cfeba19
Added a total_pages variable, changed default page to 1, and a adopte…
Dec 15, 2017
417c95f
Updating versions
Dec 16, 2017
2953cf3
Removed format options - JSON is the only format available now
Dec 16, 2017
e24cea2
Updated gem versions
Dec 16, 2017
dcc6277
Change local_time to local-time... (I saw it was already changed, but…
Dec 16, 2017
e66a624
Updated pagination defaults
Dec 16, 2017
4032d8d
Uncommenting so I could add drains
Dec 16, 2017
c375680
Making this clearer, and printing out info
Dec 16, 2017
ea959a8
Response data tests for pagination counts and drain data
Dec 16, 2017
57f6f42
Fixed a lot of merge conflicts from prod... And made changes to pass …
Dec 16, 2017
739d86c
Merge remote-tracking branch 'origin/master' into 236-simple-api
jszwedko Jan 6, 2018
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ ruby '2.2.3'

gem 'dotenv-rails', groups: [:development, :test]
gem 'rails', '~> 4.2.4'
gem 'faker', '1.7.3'
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we need an exact version here?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Changed that to have the version ~> 1.7.0... These are the sure compatible versions, not sure if they will change support in the future.

gem 'airbrake', '~> 5.2'
gem 'devise'
gem 'geokit'
Expand Down
3 changes: 3 additions & 0 deletions Gemfile.lock
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,8 @@ GEM
railties (>= 4.0, < 5.1)
erubis (2.7.0)
execjs (2.6.0)
faker (1.7.3)
i18n (~> 0.5)
font-awesome-rails (4.5.0.1)
railties (>= 3.2, < 5.1)
geokit (1.10.0)
Expand Down Expand Up @@ -233,6 +235,7 @@ DEPENDENCIES
coveralls
devise
dotenv-rails
faker (= 1.7.3)
geokit
haml
http_accept_language
Expand Down
2 changes: 2 additions & 0 deletions app/assets/javascripts/adopted.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
// Place all the behaviors and hooks related to the matching controller here.
// All this logic will automatically be available in application.js.
3 changes: 3 additions & 0 deletions app/assets/stylesheets/adopted.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
// Place all the styles related to the Adopted controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/
35 changes: 35 additions & 0 deletions app/controllers/adopted_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
class AdoptedController < ApplicationController
before_action :authenticate

def index
@things = Thing.where.not(user_id: !nil)
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think you want !nil, but just nil

Interestingly -- not that anyone cares -- !nil evaluates to true and true gets converted to 1 in the sql, so you end up with WHERE user_id != 1. (I only know this because I checked the console)

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is true, good catch

render_types
end

private

def render_types
respond_to do |format|
format.csv do
headers['Content-Type'] ||= 'text/csv'
headers['Content-Disposition'] = 'attachment; filename=\'adopted_drains.csv\''
end
format.xml { render xml: format_fields(@things) }
format.all { render json: format_fields(@things) }
end
end

def format_fields(obj)
obj.map { |thing| {latitude: thing.lat, longitude: thing.lng, city_id: 'N-' + thing.city_id.to_s} }
end

def authenticate
authenticate_or_request_with_http_basic('Administration') do |username, password|
user = User.find_by(email: username)
if user && user.valid_password?(password)
return true if user.admin?
render html: '<div> You must be an admin to access this page </div>'.html_safe
end
end
end
end
2 changes: 2 additions & 0 deletions app/controllers/application_controller.rb
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
require 'csv'

class ApplicationController < ActionController::Base
# Prevent CSRF attacks by raising an exception.
# For APIs, you may want to use :null_session instead.
Expand Down
2 changes: 2 additions & 0 deletions app/helpers/adopted_helper.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
module AdoptedHelper
end
5 changes: 5 additions & 0 deletions app/views/adopted/index.csv.erb
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<%- headers = ['Lat', 'Lng', 'City ID'] -%>
<%= CSV.generate_line headers %>
<%- @things.each do |thing| -%>
<%= CSV.generate_line([thing.lat, thing.lng, "N-" + thing.city_id.to_s]) -%>
<%- end -%>
2 changes: 1 addition & 1 deletion config/initializers/devise.rb
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@
# given strategies, for example, `config.http_authenticatable = [:database]` will
# enable it only for database authentication. The supported strategies are:
# :database = Support basic authentication with authentication key + password
# config.http_authenticatable = false
config.http_authenticatable = false
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why was this uncommented?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Never mind, I see that the API is locked to authenticated users.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cool


# If http headers should be returned for AJAX requests. True by default.
# config.http_authenticatable_on_xhr = true
Expand Down
9 changes: 9 additions & 0 deletions config/routes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -19,4 +19,13 @@
resource :things
mount RailsAdmin::Engine => '/admin', :as => 'rails_admin'
root to: 'main#index'

# API
scope '/api' do
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍 to the URL pathing here

scope '/v1' do
scope '/drains' do
get '/adopted' => 'adopted#index'
end
end
end
end
16 changes: 16 additions & 0 deletions db/seeds.rb
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

r = Random.new

=begin
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did you mean to leave this commented?

500.times do |i|
Thing.where(city_id: i).first_or_initialize.tap do |thing|
thing.name = "Some Drain #{i}"
Expand All @@ -15,3 +16,18 @@
thing.save!
end
end

=end


1000.times do |i|
first_name = Faker::Name.first_name
last_name = Faker::Name.last_name
email = "user-#{i+1}@usertest.org"
password = "pass1234"
User.create!(first_name: first_name,
last_name: last_name,
email: email,
password: password)
end

44 changes: 44 additions & 0 deletions test/controllers/adopted_controller_test.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
require 'test_helper'

class AdoptedControllerTest < ActionController::TestCase
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like checking the content-type, but could we make a few assertions on the response content to make sure the right records are returned? It'd also be nice to exercise the paging logic a little here.

setup do
request.env['devise.mapping'] = Devise.mappings[:user]
@user = users(:erik)
@admin = users(:admin)
end

test 'should get index' do
@request.env['HTTP_AUTHORIZATION'] = ActionController::HttpAuthentication::Basic.encode_credentials(@user.email, 'correct')

get :index
assert_response :success
end

test 'should get json' do
@request.env['HTTP_AUTHORIZATION'] = ActionController::HttpAuthentication::Basic.encode_credentials(@admin.email, 'correct')

get :index, format: :json
assert_equal 'application/json', @response.content_type
end

test 'should get xml' do
@request.env['HTTP_AUTHORIZATION'] = ActionController::HttpAuthentication::Basic.encode_credentials(@admin.email, 'correct')

get :index, format: :xml
assert_equal 'application/xml', @response.content_type
end

test 'should get csv' do
@request.env['HTTP_AUTHORIZATION'] = ActionController::HttpAuthentication::Basic.encode_credentials(@admin.email, 'correct')

get :index, format: :csv
assert_equal 'text/csv', @response.content_type
end

test 'only admins get access' do
@request.env['HTTP_AUTHORIZATION'] = ActionController::HttpAuthentication::Basic.encode_credentials(@user.email, 'correct')

get :index
assert_equal 'text/html', @response.content_type # If user were an admin, content_type would be JSON, since that is default
end
end