* Add dual booting logic to Gemfile This might be helpful for the Rails 6.0 upgrade project. * Add more than one gemfile to Travis' configuration We want to see how the application behaves with more than one Rails versions: - Gemfile -> Rails 5.2 - Gemfile.next -> Rails 6.0 This will help us figure out what needs to be addressed before migrating to Rails 6.0. If you want to read more about this technique (dual booting) you can check out this page: https://www.fastruby.io/blog/upgrade-rails/dual-boot/dual-boot-with-rails-6-0-beta.html * Fix joins * Upgrade Gemfile.next.lock * Make sure we're installing the correct versions of gems * Add Rails 6 notes * Update rubocop in Gemfile.next.lock * Fix organization spec * Fix page_views_spec * Add Rails 6 and run rails app:update * Remove some tricks * Remove Gemfile.next for now * Fix .content_type deprecation * Fix deprecation of .where.not NAND/NOR behavior * Fix deprecation of parameterized emails * Fix specs * Remove next flag for now * Fix spec (hopefully) * Add wait_for_javascript * Fix spec, thanks @maestromac! * Try without wait for javascript hack * Remove unnecessary bin/update * Remove file that snuck in the rebase * Update the vendored gems * Replace migrate+db:setup with db:prepare * Update vendored gems * Fix Gemfile.lock and update vendored stuff * Fix Gemfile.lock to be the same as master's minus the changes Co-authored-by: rhymes <rhymesete@gmail.com>
239 lines
8.4 KiB
Ruby
239 lines
8.4 KiB
Ruby
require "rails_helper"
|
|
|
|
RSpec.describe "Api::V0::Webhooks", type: :request do
|
|
let_it_be_changeable(:user) { create(:user) }
|
|
let_it_be_changeable(:webhook) do
|
|
create(:webhook_endpoint, user: user, target_url: "https://api.example.com/go")
|
|
end
|
|
|
|
describe "GET /api/v0/webhooks" do
|
|
let_it_be_readonly(:webhook2) do
|
|
create(:webhook_endpoint, user: user, target_url: "https://api.example.com/webhook")
|
|
end
|
|
|
|
context "when accessing with oauth" do
|
|
it "returns a 401 if unauthorized" do
|
|
get api_webhooks_path
|
|
expect(response).to have_http_status(:unauthorized)
|
|
end
|
|
|
|
it "returns a 403 if public scope is missing (oauth)" do
|
|
access_token = create(:doorkeeper_access_token, resource_owner_id: user.id)
|
|
headers = { "authorization" => "Bearer #{access_token.token}", "content-type" => "application/json" }
|
|
|
|
get api_webhooks_path, headers: headers
|
|
expect(response).to have_http_status(:forbidden)
|
|
end
|
|
|
|
it "returns a 200 if authorized" do
|
|
access_token = create(:doorkeeper_access_token, resource_owner_id: user.id, scopes: "public")
|
|
webhook = create(:webhook_endpoint, user: user, target_url: "https://api.example.com/go2", oauth_application_id: access_token.application_id)
|
|
headers = { "authorization" => "Bearer #{access_token.token}", "content-type" => "application/json" }
|
|
get api_webhooks_path, headers: headers
|
|
expect(response).to have_http_status(:ok)
|
|
expect(response.parsed_body.first).to eq(
|
|
"created_at" => webhook.created_at.rfc3339,
|
|
"events" => webhook.events,
|
|
"id" => webhook.id,
|
|
"source" => webhook.source,
|
|
"target_url" => webhook.target_url,
|
|
"type_of" => "webhook_endpoint",
|
|
)
|
|
end
|
|
end
|
|
|
|
context "when accessing via cookie" do
|
|
before do
|
|
sign_in user
|
|
create(:webhook_endpoint)
|
|
end
|
|
|
|
it "returns 200 on success" do
|
|
get api_webhooks_path
|
|
expect(response).to have_http_status(:ok)
|
|
end
|
|
|
|
it "returns json on success" do
|
|
get api_webhooks_path
|
|
|
|
expect(response.parsed_body).to include(
|
|
hash_including("id" => webhook.id, "target_url" => webhook.target_url),
|
|
hash_including("id" => webhook2.id, "target_url" => webhook2.target_url),
|
|
)
|
|
end
|
|
|
|
it "returns the correct json representation" do
|
|
get api_webhooks_path
|
|
|
|
expect(response.parsed_body.first).to eq(
|
|
"created_at" => webhook.created_at.rfc3339,
|
|
"events" => webhook.events,
|
|
"id" => webhook.id,
|
|
"source" => webhook.source,
|
|
"target_url" => webhook.target_url,
|
|
"type_of" => "webhook_endpoint",
|
|
)
|
|
end
|
|
end
|
|
end
|
|
|
|
describe "GET /api/v0/webhooks/:id" do
|
|
before do
|
|
sign_in user
|
|
end
|
|
|
|
it "returns 200 on success" do
|
|
get api_webhook_path(webhook.id)
|
|
|
|
expect(response).to have_http_status(:ok)
|
|
end
|
|
|
|
it "returns 404 if the webhook does not exist" do
|
|
get api_webhook_path(9999)
|
|
|
|
expect(response).to have_http_status(:not_found)
|
|
end
|
|
|
|
it "returns 404 if another user webhook is accessed" do
|
|
other_webhook = create(:webhook_endpoint, user: create(:user))
|
|
|
|
get api_webhook_path(other_webhook.id)
|
|
|
|
expect(response).to have_http_status(:not_found)
|
|
end
|
|
|
|
it "returns the correct json representation" do
|
|
get api_webhook_path(webhook.id)
|
|
|
|
expect(response.parsed_body).to include(
|
|
"created_at" => webhook.created_at.rfc3339,
|
|
"events" => webhook.events,
|
|
"id" => webhook.id,
|
|
"source" => webhook.source,
|
|
"target_url" => webhook.target_url,
|
|
"type_of" => "webhook_endpoint",
|
|
)
|
|
end
|
|
|
|
it "returns the correct json representation for the webhook user" do
|
|
get api_webhook_path(webhook.id)
|
|
|
|
response_webhook_user = response.parsed_body["user"]
|
|
user_profile_image = ProfileImage.new(webhook.user)
|
|
|
|
expect(response_webhook_user["name"]).to eq(webhook.user.name)
|
|
expect(response_webhook_user["username"]).to eq(webhook.user.username)
|
|
expect(response_webhook_user["twitter_username"]).to eq(webhook.user.twitter_username)
|
|
expect(response_webhook_user["github_username"]).to eq(webhook.user.github_username)
|
|
expect(response_webhook_user["website_url"]).to eq(webhook.user.processed_website_url)
|
|
expect(response_webhook_user["profile_image"]).to eq(user_profile_image.get(width: 640))
|
|
expect(response_webhook_user["profile_image_90"]).to eq(user_profile_image.get(width: 90))
|
|
end
|
|
end
|
|
|
|
describe "POST /api/v0/webhooks" do
|
|
let(:webhook_params) do
|
|
{
|
|
source: "stackbit",
|
|
target_url: Faker::Internet.url(scheme: "https"),
|
|
events: %w[article_created article_updated article_destroyed]
|
|
}
|
|
end
|
|
|
|
before do
|
|
sign_in user
|
|
end
|
|
|
|
it "creates a webhook" do
|
|
expect do
|
|
post api_webhooks_path, params: { webhook_endpoint: webhook_params }
|
|
end.to change(Webhook::Endpoint, :count).by(1)
|
|
end
|
|
|
|
it "creates a webhook with events and data" do
|
|
post api_webhooks_path, params: { webhook_endpoint: webhook_params }
|
|
created_webhook = user.webhook_endpoints.last
|
|
expect(created_webhook.events).to eq(%w[article_created article_updated article_destroyed])
|
|
expect(created_webhook.target_url).to eq(webhook_params[:target_url])
|
|
expect(created_webhook.source).to eq(webhook_params[:source])
|
|
expect(created_webhook.oauth_application_id).to eq(nil)
|
|
end
|
|
|
|
it "returns :created and json response on success" do
|
|
post api_webhooks_path, params: { webhook_endpoint: webhook_params }
|
|
expect(response).to have_http_status(:created)
|
|
expect(response.media_type).to eq("application/json")
|
|
json = JSON.parse(response.body)
|
|
expect(json["target_url"]).to eq(webhook_params[:target_url])
|
|
end
|
|
end
|
|
|
|
describe "DELETE /api/v0/webhooks/:id" do
|
|
before do
|
|
sign_in user
|
|
end
|
|
|
|
it "deletes the webhook" do
|
|
expect do
|
|
delete api_webhook_path(webhook.id)
|
|
end.to change(Webhook::Endpoint, :count).by(-1)
|
|
end
|
|
|
|
it "returns 204 on success" do
|
|
delete api_webhook_path(webhook.id)
|
|
expect(response).to have_http_status(:no_content)
|
|
end
|
|
|
|
it "doesn't allow to destroy other user webhook" do
|
|
other_webhook = create(:webhook_endpoint, user: create(:user))
|
|
expect do
|
|
delete api_webhook_path(other_webhook.id)
|
|
end.not_to change(Webhook::Endpoint, :count)
|
|
end
|
|
|
|
it "returns 404 if another user webhook is accessed" do
|
|
other_webhook = create(:webhook_endpoint, user: create(:user))
|
|
delete api_webhook_path(other_webhook.id)
|
|
expect(response).to have_http_status(:not_found)
|
|
end
|
|
end
|
|
|
|
describe "authorized with doorkeeper" do
|
|
let!(:oauth_app) { create(:application) }
|
|
let!(:oauth_app2) { create(:application) }
|
|
let(:access_token) { create :doorkeeper_access_token, resource_owner: user, application: oauth_app2, scopes: "public" }
|
|
|
|
it "renders index successfully" do
|
|
get api_webhooks_path, params: { access_token: access_token.token }
|
|
expect(response.media_type).to eq("application/json")
|
|
expect(response).to have_http_status(:ok)
|
|
end
|
|
|
|
it "renders only corresponding webhooks" do
|
|
create(:webhook_endpoint, oauth_application_id: oauth_app.id, user: user)
|
|
webhook2 = create(:webhook_endpoint, oauth_application_id: oauth_app2.id, user: user)
|
|
get api_webhooks_path, params: { access_token: access_token.token }
|
|
|
|
json = JSON.parse(response.body)
|
|
ids = json.map { |item| item["id"] }
|
|
expect(ids).to eq([webhook2.id])
|
|
end
|
|
|
|
it "sets correct oauth app id for the webhook if needed" do
|
|
webhook_params = {
|
|
source: "stackbit",
|
|
target_url: Faker::Internet.url(scheme: "https"),
|
|
events: %w[article_created article_updated article_destroyed]
|
|
}
|
|
post api_webhooks_path, params: { access_token: access_token.token, webhook_endpoint: webhook_params }
|
|
webhook = user.webhook_endpoints.find_by(target_url: webhook_params[:target_url])
|
|
expect(webhook.oauth_application_id).to eq(oauth_app2.id)
|
|
end
|
|
|
|
it "doesn't allow destroying another app webhook" do
|
|
other_webhook = create(:webhook_endpoint, user: user)
|
|
delete api_webhook_path(other_webhook.id), params: { access_token: access_token.token }
|
|
expect(response).to have_http_status(:not_found)
|
|
end
|
|
end
|
|
end
|