diff --git a/Gemfile b/Gemfile index 2bf9d93776..60a86bac84 100644 --- a/Gemfile +++ b/Gemfile @@ -202,6 +202,9 @@ gem "sentry-delayed_job", '~> 5.3.0' gem "sentry-rails", '~> 5.3.0' gem "sentry-ruby", '~> 5.3.0' +# Appsignal integration +gem "appsignal", "~> 3.0", require: false + group :test do gem 'launchy', '~> 2.5.0' gem 'rack-test', '~> 1.1.0' diff --git a/Gemfile.lock b/Gemfile.lock index d27c2f9db0..bc2258c0e6 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -282,6 +282,8 @@ GEM airbrake-ruby (~> 6.0) airbrake-ruby (6.1.0) rbtree3 (~> 0.5) + appsignal (3.0.27) + rack ast (2.4.2) attr_required (1.0.1) auto_strip_attributes (2.6.0) @@ -1015,6 +1017,7 @@ DEPENDENCIES acts_as_tree (~> 2.9.0) addressable (~> 2.8.0) airbrake (~> 13.0.0) + appsignal (~> 3.0) auto_strip_attributes (~> 2.5) awesome_nested_set (~> 3.5.0) aws-sdk-core (~> 3.107) diff --git a/config/initializers/appsignal.rb b/config/initializers/appsignal.rb new file mode 100644 index 0000000000..cc86c93fdc --- /dev/null +++ b/config/initializers/appsignal.rb @@ -0,0 +1,33 @@ +require 'open_project/version' + +if ENV['APPSIGNAL_ENABLED'] == 'true' + require 'appsignal' + OpenProject::Application.configure do |app| + config = { + active: true, + name: ENV.fetch('APPSIGNAL_NAME'), + push_api_key: ENV.fetch('APPSIGNAL_KEY'), + revision: OpenProject::VERSION.to_s, + ignore_actions: %w[OkComputerController#index OkComputerController#show] + } + + if Rails.env.development? + config[:log] = 'stdout' + config[:debug] = true + config[:log_level] = 'debug' + end + + Appsignal.config = Appsignal::Config.new( + Rails.root, + Rails.env, + config + ) + + app.middleware.insert_after( + ActionDispatch::DebugExceptions, + Appsignal::Rack::RailsInstrumentation + ) + + Appsignal.start + end +end diff --git a/config/puma.rb b/config/puma.rb index 54fd04f2e6..d375917d8f 100644 --- a/config/puma.rb +++ b/config/puma.rb @@ -33,6 +33,8 @@ preload_app! if ENV["RAILS_ENV"] == 'production' # Allow puma to be restarted by `rails restart` command. plugin :tmp_restart unless ENV["RAILS_ENV"] == 'production' +plugin :appsignal if ENV['APPSIGNAL_ENABLED'] == 'true' + # activate statsd plugin only if a host is configured explicitly if OpenProject::Configuration.statsd_host.present? module ConfigurationViaOpenProject diff --git a/lib/api/appsignal_api.rb b/lib/api/appsignal_api.rb new file mode 100644 index 0000000000..898b0704a6 --- /dev/null +++ b/lib/api/appsignal_api.rb @@ -0,0 +1,41 @@ +#-- copyright +# OpenProject is an open source project management software. +# Copyright (C) 2012-2022 the OpenProject GmbH +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License version 3. +# +# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows: +# Copyright (C) 2006-2013 Jean-Philippe Lang +# Copyright (C) 2010-2013 the ChiliProject Team +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +# +# See COPYRIGHT and LICENSE files for more details. +#++ +require "appsignal" +require "appsignal/integrations/grape" + +module API + module AppsignalAPI + def self.included(base) + base.class_eval do + if Appsignal.active? + insert_before Grape::Middleware::Error, Appsignal::Grape::Middleware + end + end + end + end +end diff --git a/lib/api/open_project_api.rb b/lib/api/open_project_api.rb index dab7c66315..53ea3b5114 100644 --- a/lib/api/open_project_api.rb +++ b/lib/api/open_project_api.rb @@ -28,6 +28,8 @@ module API class OpenProjectAPI < ::Grape::API + include ::API::AppsignalAPI + class << self def inherited(api, *) super diff --git a/lib/api/root.rb b/lib/api/root.rb index f0bbc5129d..9d843b36a8 100644 --- a/lib/api/root.rb +++ b/lib/api/root.rb @@ -25,9 +25,9 @@ # # See COPYRIGHT and LICENSE files for more details. #++ - module API class Root < ::API::RootAPI + include ::API::AppsignalAPI content_type 'hal+json', 'application/hal+json; charset=utf-8' format 'hal+json' formatter 'hal+json', API::Formatter.new diff --git a/lib/api/root_api.rb b/lib/api/root_api.rb index 44f93af2f9..f6b8eb72b5 100644 --- a/lib/api/root_api.rb +++ b/lib/api/root_api.rb @@ -35,6 +35,7 @@ require 'open_project/authentication' module API class RootAPI < Grape::API include OpenProject::Authentication::Scope + include ::API::AppsignalAPI extend API::Utilities::GrapeHelper insert_before Grape::Middleware::Error,