diff --git a/app/controllers/about_controller.rb b/app/controllers/about_controller.rb index 7fd43489f..04e7ddacf 100644 --- a/app/controllers/about_controller.rb +++ b/app/controllers/about_controller.rb @@ -2,30 +2,25 @@ class AboutController < ApplicationController before_action :set_body_classes + before_action :set_instance_presenter, only: [:show, :more] - def index - @description = Setting.site_description - @open_registrations = Setting.open_registrations - @closed_registrations_message = Setting.closed_registrations_message + def show; end - @user = User.new - @user.build_account - end - - def more - @description = Setting.site_description - @extended_description = Setting.site_extended_description - @contact_account = Account.find_local(Setting.site_contact_username) - @contact_email = Setting.site_contact_email - @user_count = Rails.cache.fetch('user_count') { User.count } - @status_count = Rails.cache.fetch('local_status_count') { Status.local.count } - @domain_count = Rails.cache.fetch('distinct_domain_count') { Account.distinct.count(:domain) } - end + def more; end def terms; end private + def new_user + User.new.tap(&:build_account) + end + helper_method :new_user + + def set_instance_presenter + @instance_presenter = InstancePresenter.new + end + def set_body_classes @body_classes = 'about-body' end diff --git a/app/presenters/instance_presenter.rb b/app/presenters/instance_presenter.rb new file mode 100644 index 000000000..cd809566f --- /dev/null +++ b/app/presenters/instance_presenter.rb @@ -0,0 +1,28 @@ +# frozen_string_literal: true + +class InstancePresenter + delegate( + :closed_registrations_message, + :contact_email, + :open_registrations, + :site_description, + :site_extended_description, + to: Setting + ) + + def contact_account + Account.find_local(Setting.site_contact_username) + end + + def user_count + Rails.cache.fetch('user_count') { User.count } + end + + def status_count + Rails.cache.fetch('local_status_count') { Status.local.count } + end + + def domain_count + Rails.cache.fetch('distinct_domain_count') { Account.distinct.count(:domain) } + end +end diff --git a/app/views/about/_registration.html.haml b/app/views/about/_registration.html.haml new file mode 100644 index 000000000..c7a9a488b --- /dev/null +++ b/app/views/about/_registration.html.haml @@ -0,0 +1,30 @@ += simple_form_for(new_user, url: user_registration_path) do |f| + = f.simple_fields_for :account do |account_fields| + = account_fields.input :username, + autofocus: true, + placeholder: t('simple_form.labels.defaults.username'), + required: true, + input_html: { 'aria-label' => t('simple_form.labels.defaults.username') } + + = f.input :email, + placeholder: t('simple_form.labels.defaults.email'), + required: true, + input_html: { 'aria-label' => t('simple_form.labels.defaults.email') } + = f.input :password, + autocomplete: "off", + placeholder: t('simple_form.labels.defaults.password'), + required: true, + input_html: { 'aria-label' => t('simple_form.labels.defaults.password') } + = f.input :password_confirmation, + autocomplete: "off", + placeholder: t('simple_form.labels.defaults.confirm_password'), + required: true, + input_html: { 'aria-label' => t('simple_form.labels.defaults.confirm_password') } + + .actions + = f.button :button, t('about.get_started'), type: :submit + + .info + = link_to t('auth.login'), new_user_session_path, class: 'webapp-btn' + · + = link_to t('about.about_this'), about_more_path diff --git a/app/views/about/more.html.haml b/app/views/about/more.html.haml index 2de3bf986..8c12f57c1 100644 --- a/app/views/about/more.html.haml +++ b/app/views/about/more.html.haml @@ -7,42 +7,42 @@ .panel %h2= Rails.configuration.x.local_domain - - unless @description.blank? - %p= @description.html_safe + - unless @instance_presenter.site_description.blank? + %p= @instance_presenter.site_description.html_safe .information-board .section %span= t 'about.user_count_before' - %strong= number_with_delimiter @user_count + %strong= number_with_delimiter @instance_presenter.user_count %span= t 'about.user_count_after' .section %span= t 'about.status_count_before' - %strong= number_with_delimiter @status_count + %strong= number_with_delimiter @instance_presenter.status_count %span= t 'about.status_count_after' .section %span= t 'about.domain_count_before' - %strong= number_with_delimiter @domain_count + %strong= number_with_delimiter @instance_presenter.domain_count %span= t 'about.domain_count_after' - - unless @extended_description.blank? - .panel= @extended_description.html_safe + - unless @instance_presenter.site_extended_description.blank? + .panel= @instance_presenter.site_extended_description.html_safe .sidebar .panel .panel-header= t 'about.contact' .panel-body - - if @contact_account + - if @instance_presenter.contact_account .owner - .avatar= image_tag @contact_account.avatar.url + .avatar= image_tag @instance_presenter.contact_account.avatar.url .name - = link_to TagManager.instance.url_for(@contact_account) do - %span.display_name.emojify= display_name(@contact_account) - %span.username= "@#{@contact_account.acct}" + = link_to TagManager.instance.url_for(@instance_presenter.contact_account) do + %span.display_name.emojify= display_name(@instance_presenter.contact_account) + %span.username= "@#{@instance_presenter.contact_account.acct}" - - unless @contact_email.blank? + - unless @instance_presenter.contact_email.blank? .contact-email = t 'about.business_email' - %strong= @contact_email + %strong= @instance_presenter.contact_email .panel .panel-header= t 'about.links' .panel-list diff --git a/app/views/about/index.html.haml b/app/views/about/show.html.haml similarity index 60% rename from app/views/about/index.html.haml rename to app/views/about/show.html.haml index f6b0c1668..8a0d00daa 100644 --- a/app/views/about/index.html.haml +++ b/app/views/about/show.html.haml @@ -8,7 +8,7 @@ %meta{ property: 'og:site_name', content: site_title }/ %meta{ property: 'og:type', content: 'website' }/ %meta{ property: 'og:title', content: Rails.configuration.x.local_domain }/ - %meta{ property: 'og:description', content: @description.blank? ? "Mastodon is a free, open-source social network server. A decentralized alternative to commercial platforms, it avoids the risks of a single company monopolizing your communication. Anyone can run Mastodon and participate in the social network seamlessly" : strip_tags(@description) }/ + %meta{ property: 'og:description', content: strip_tags(@instance_presenter.site_description.blank? ? t('about.about_mastodon') : @instance_presenter.site_description) }/ %meta{ property: 'og:image', content: asset_url('mastodon_small.jpg') }/ %meta{ property: 'og:image:width', content: '400' }/ %meta{ property: 'og:image:height', content: '400' }/ @@ -24,28 +24,14 @@ .screenshot-with-signup .mascot= image_tag 'fluffy-elephant-friend.png' - - if @open_registrations - = simple_form_for(@user, url: user_registration_path) do |f| - = f.simple_fields_for :account do |ff| - = ff.input :username, autofocus: true, placeholder: t('simple_form.labels.defaults.username'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.username') } - - = f.input :email, placeholder: t('simple_form.labels.defaults.email'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.email') } - = f.input :password, autocomplete: "off", placeholder: t('simple_form.labels.defaults.password'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.password') } - = f.input :password_confirmation, autocomplete: "off", placeholder: t('simple_form.labels.defaults.confirm_password'), required: true, input_html: { 'aria-label' => t('simple_form.labels.defaults.confirm_password') } - - .actions - = f.button :button, t('about.get_started'), type: :submit - - .info - = link_to t('auth.login'), new_user_session_path, class: 'webapp-btn' - · - = link_to t('about.about_this'), about_more_path + - if @instance_presenter.open_registrations + = render 'registration' - else .closed-registrations-message - - if @closed_registrations_message.blank? + - if @instance_presenter.closed_registrations_message.blank? %p= t('about.closed_registrations') - else - = @closed_registrations_message.html_safe + = @instance_presenter.closed_registrations_message.html_safe .info = link_to t('auth.login'), new_user_session_path, class: 'webapp-btn' · @@ -85,9 +71,9 @@ = fa_icon('li check-square') = t 'about.features.api' - - unless @description.blank? + - unless @instance_presenter.site_description.blank? %h3= t('about.description_headline', domain: Rails.configuration.x.local_domain) - %p= @description.html_safe + %p= @instance_presenter.site_description.html_safe .actions .info diff --git a/config/routes.rb b/config/routes.rb index 66b0ed830..b0a13aa78 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -188,7 +188,7 @@ Rails.application.routes.draw do get '/web/(*any)', to: 'home#index', as: :web - get '/about', to: 'about#index' + get '/about', to: 'about#show' get '/about/more', to: 'about#more' get '/terms', to: 'about#terms' diff --git a/spec/controllers/about_controller_spec.rb b/spec/controllers/about_controller_spec.rb index 4282649e1..f49de9622 100644 --- a/spec/controllers/about_controller_spec.rb +++ b/spec/controllers/about_controller_spec.rb @@ -3,9 +3,16 @@ require 'rails_helper' RSpec.describe AboutController, type: :controller do render_views - describe 'GET #index' do + describe 'GET #show' do it 'returns http success' do - get :index + get :show + expect(response).to have_http_status(:success) + end + end + + describe 'GET #more' do + it 'returns http success' do + get :more expect(response).to have_http_status(:success) end end diff --git a/spec/presenters/instance_presenter_spec.rb b/spec/presenters/instance_presenter_spec.rb new file mode 100644 index 000000000..0f318d9c3 --- /dev/null +++ b/spec/presenters/instance_presenter_spec.rb @@ -0,0 +1,74 @@ +require 'rails_helper' + +describe InstancePresenter do + let(:instance_presenter) { InstancePresenter.new } + + it "delegates site_description to Setting" do + Setting.site_description = "Site desc" + + expect(instance_presenter.site_description).to eq "Site desc" + end + + it "delegates site_extended_description to Setting" do + Setting.site_extended_description = "Extended desc" + + expect(instance_presenter.site_extended_description).to eq "Extended desc" + end + + it "delegates open_registrations to Setting" do + Setting.open_registrations = false + + expect(instance_presenter.open_registrations).to eq false + end + + it "delegates closed_registrations_message to Setting" do + Setting.closed_registrations_message = "Closed message" + + expect(instance_presenter.closed_registrations_message).to eq "Closed message" + end + + it "delegates contact_email to Setting" do + Setting.contact_email = "admin@example.com" + + expect(instance_presenter.contact_email).to eq "admin@example.com" + end + + describe "contact_account" do + it "returns the account for the site contact username" do + Setting.site_contact_username = "aaa" + account = Fabricate(:account, username: "aaa") + + expect(instance_presenter.contact_account).to eq(account) + end + end + + describe "user_count" do + it "returns the number of site users" do + cache = double + allow(Rails).to receive(:cache).and_return(cache) + allow(cache).to receive(:fetch).with("user_count").and_return(123) + + expect(instance_presenter.user_count).to eq(123) + end + end + + describe "status_count" do + it "returns the number of local statuses" do + cache = double + allow(Rails).to receive(:cache).and_return(cache) + allow(cache).to receive(:fetch).with("local_status_count").and_return(234) + + expect(instance_presenter.status_count).to eq(234) + end + end + + describe "domain_count" do + it "returns the number of known domains" do + cache = double + allow(Rails).to receive(:cache).and_return(cache) + allow(cache).to receive(:fetch).with("distinct_domain_count").and_return(345) + + expect(instance_presenter.domain_count).to eq(345) + end + end +end