Compare commits

...

12 Commits

Author SHA1 Message Date
Christopher Harrington 5134e363f7
Merge 641b07167a into 574cdad7a8 2023-12-26 10:09:25 +00:00
Mathilde 574cdad7a8
Fixing wrongly formatted readme
Contributing to Hometown section would show up as title instead of simple body text.
2023-12-26 11:09:13 +01:00
Christopher Harrington 641b07167a Review fix: Restructure for early return
Per IanWhitney's review, the complex logic with the unless clause is pretty clumsy. We can check this condition first and return false immediately, and leave the remaining logic as a simpler statement on its own.
2023-05-06 21:58:01 -05:00
Christopher Harrington 3897eaa15e Review fix: Avoid ternary expressions
It seems I let my inner C programmer get the better of me. Per IanWhitney's review, Ruby's if structures are expressions and return values, which make them more suitable than a ternary expression in terms of readability.
2023-05-06 21:49:45 -05:00
Christopher Harrington e6f8a67f9f Review fix: Use only directive for all auth skips
IanWhitney's review pointed out that it is more consistent and a safer default to include the "only:" directive for all cases where we skip the user authentication requirement. In particular: if a future public method is added to this controller, it should not be implicitly available pre-auth.
2023-05-06 21:40:57 -05:00
Christopher Harrington 7d7e61da4a Return empty statuses and tags for users visible through restricted API 2023-04-09 22:41:10 -05:00
Christopher Harrington 744f500a89 Fix front-end to avoid tight request loop on 401 response 2023-04-09 22:41:10 -05:00
Christopher Harrington 86ba6925b8 Allow restricted API account details if user does not opt-out 2023-04-09 22:41:10 -05:00
Christopher Harrington 135b9f5fb3 Allow restricted API lookup if user does not opt-out 2023-04-09 22:41:10 -05:00
Christopher Harrington 0c9c7b88e1 Add user-oriented helper methods
This centralizes the core check for the user's preferences into a single helper method, and gives us one place to change the user preference flag if it turns out user_prefers_noindex isn't appropriate. Also adds a convenience error response specific to the user visibility situation.
2023-04-09 22:41:10 -05:00
Christopher Harrington 9fbcfe7d51 Move unless criteria into boolean method
It's helpful to be able to ask the parent class whether we would disallow API access based on the current request (and hence whether we know the requesting user) rather than simply based on configuration. This doesn't appear to regress any existing functionality.
2023-04-09 22:41:10 -05:00
Christopher Harrington 1c4948da08 Exempt Emoji API endpoint from auth
When viewing a profile anonymously, the request for custom emoji will show a 401 Unauthorized error to the user. Exempt this endpoint from the authentication requirement.
2023-04-09 22:41:10 -05:00
8 changed files with 40 additions and 4 deletions

View File

@ -81,7 +81,7 @@ Hometown uses [semantic versioning](https://semver.org) and follows a versioning
## Contributing to Hometown
Setting up your Hometown development environment is [exactly like setting up your Mastodon development environment](https://docs.joinmastodon.org/dev/overview/). Pull requests should be made to the `hometown-dev` branch, which is our default branch in Github.
=======
You can open issues for bugs you've found or features you think are missing. You can also submit pull requests to this repository or submit translations using Crowdin. To get started, take a look at [CONTRIBUTING.md](CONTRIBUTING.md). If your contributions are accepted into Mastodon, you can request to be paid through [our OpenCollective](https://opencollective.com/mastodon).
**IRC channel**: #mastodon on irc.libera.chat

View File

@ -153,9 +153,19 @@ class Api::BaseController < ApplicationController
end
def disallow_unauthenticated_api_access?
return false if current_user
ENV['DISALLOW_UNAUTHENTICATED_API_ACCESS'] == 'true' || Rails.configuration.x.whitelist_mode
end
def user_would_block_unauthenticated_api_access?(account)
# alternately account.locked? would also be a good candidate for this
disallow_unauthenticated_api_access? && account.user_prefers_noindex?
end
def user_blocks_unauthenticated_api_access
render json: { error: 'This user is only visible to authenticated users' }, status: 401
end
private
def respond_with_error(code)

View File

@ -3,10 +3,14 @@
class Api::V1::Accounts::FeaturedTagsController < Api::BaseController
before_action :set_account
before_action :set_featured_tags
skip_before_action :require_authenticated_user!, only: [:index]
respond_to :json
def index
if user_would_block_unauthenticated_api_access?(@account)
user_blocks_unauthenticated_api_access and return
end
render json: @featured_tags, each_serializer: REST::FeaturedTagSerializer
end
@ -17,6 +21,9 @@ class Api::V1::Accounts::FeaturedTagsController < Api::BaseController
end
def set_featured_tags
@featured_tags = @account.suspended? ? [] : @account.featured_tags
@featured_tags = if @account.suspended? || disallow_unauthenticated_api_access?
[]
else
@account.featured_tags
end
end

View File

@ -1,10 +1,14 @@
# frozen_string_literal: true
class Api::V1::Accounts::LookupController < Api::BaseController
skip_before_action :require_authenticated_user!, only: :show
before_action -> { authorize_if_got_token! :read, :'read:accounts' }
before_action :set_account
def show
if user_would_block_unauthenticated_api_access?(@account)
user_blocks_unauthenticated_api_access and return
end
render json: @account, serializer: REST::AccountSerializer
end

View File

@ -3,11 +3,15 @@
class Api::V1::Accounts::StatusesController < Api::BaseController
before_action -> { authorize_if_got_token! :read, :'read:statuses' }
before_action :set_account
skip_before_action :require_authenticated_user!, only: [:index]
after_action :insert_pagination_headers, unless: -> { truthy_param?(:pinned) }
def index
@statuses = load_statuses
if user_would_block_unauthenticated_api_access?(@account)
user_blocks_unauthenticated_api_access and return
end
render json: @statuses, each_serializer: REST::StatusSerializer, relationships: StatusRelationshipsPresenter.new(@statuses, current_user&.account_id)
end
@ -18,7 +22,10 @@ class Api::V1::Accounts::StatusesController < Api::BaseController
end
def load_statuses
@account.suspended? ? [] : cached_account_statuses
if @account.suspended? || disallow_unauthenticated_api_access?
[]
else
cached_account_statuses
end
def cached_account_statuses

View File

@ -13,11 +13,14 @@ class Api::V1::AccountsController < Api::BaseController
before_action :check_account_confirmation, except: [:create]
before_action :check_enabled_registrations, only: [:create]
skip_before_action :require_authenticated_user!, only: :create
skip_before_action :require_authenticated_user!, only: [:create, :show]
override_rate_limit_headers :follow, family: :follows
def show
if user_would_block_unauthenticated_api_access?(@account)
user_blocks_unauthenticated_api_access and return
end
render json: @account, serializer: REST::AccountSerializer
end

View File

@ -2,6 +2,7 @@
class Api::V1::CustomEmojisController < Api::BaseController
skip_before_action :set_cache_headers
skip_before_action :require_authenticated_user!, only: :index
def index
expires_in 3.minutes, public: true

View File

@ -190,6 +190,10 @@ export default function timelines(state = initialState, action) {
case TIMELINE_EXPAND_REQUEST:
return state.update(action.timeline, initialTimeline, map => map.set('isLoading', true));
case TIMELINE_EXPAND_FAIL:
if (action.error?.response?.status === 401) {
// don't loop continuously on 401 unauthenticated response
return state.update(action.timeline, initialTimeline, map => map.set('hasMore', false));
}
return state.update(action.timeline, initialTimeline, map => map.set('isLoading', false));
case TIMELINE_EXPAND_SUCCESS:
return expandNormalizedTimeline(state, action.timeline, fromJS(action.statuses), action.next, action.partial, action.isLoadingRecent, action.usePendingItems);