From e2fbf8bc7479967baa84ef26eb03e19f0fd868e8 Mon Sep 17 00:00:00 2001 From: Evan Minto Date: Sat, 4 Feb 2017 14:46:23 -0800 Subject: [PATCH 1/7] Add an account endpoint for ActivityPub and link to it on HTML profile pages --- .../api/activitypub/accounts_controller.rb | 20 +++++++++++++++++++ app/views/accounts/show.html.haml | 1 + app/views/api/activitypub/accounts/show.rabl | 10 ++++++++++ config/routes.rb | 6 ++++++ 4 files changed, 37 insertions(+) create mode 100644 app/controllers/api/activitypub/accounts_controller.rb create mode 100644 app/views/api/activitypub/accounts/show.rabl diff --git a/app/controllers/api/activitypub/accounts_controller.rb b/app/controllers/api/activitypub/accounts_controller.rb new file mode 100644 index 00000000000..efb6413a0dc --- /dev/null +++ b/app/controllers/api/activitypub/accounts_controller.rb @@ -0,0 +1,20 @@ +# frozen_string_literal: true + +class Api::Activitypub::AccountsController < ApiController + before_action -> { doorkeeper_authorize! :read }, except: [:show] + before_action :require_user!, except: [:show] + before_action :set_account, except: [:verify_credentials, :suggestions, :search] + + respond_to :'application/activity+json' + respond_to :'application/ld+json; profile="https://www.w3.org/ns/activitystreams#"' + + def show + render content_type: :'application/ld+json; profile="https://www.w3.org/ns/activitystreams#"' + end + + private + + def set_account + @account = Account.find(params[:id]) + end +end diff --git a/app/views/accounts/show.html.haml b/app/views/accounts/show.html.haml index c194ce33dd3..cd539890827 100644 --- a/app/views/accounts/show.html.haml +++ b/app/views/accounts/show.html.haml @@ -4,6 +4,7 @@ - content_for :header_tags do %link{ rel: 'salmon', href: api_salmon_url(@account.id) }/ %link{ rel: 'alternate', type: 'application/atom+xml', href: account_url(@account, format: 'atom') }/ + %link{ rel: 'alternate', type: 'application/ld+json; profile="https://www.w3.org/ns/activitystreams#"', href: "http://mastodon.dev/api/v1/activitypub/accounts/#{@account.username}" }/ %meta{ property: 'og:site_name', content: 'Mastodon' }/ %meta{ property: 'og:type', content: 'profile' }/ diff --git a/app/views/api/activitypub/accounts/show.rabl b/app/views/api/activitypub/accounts/show.rabl new file mode 100644 index 00000000000..806789d0037 --- /dev/null +++ b/app/views/api/activitypub/accounts/show.rabl @@ -0,0 +1,10 @@ +object @account + +node(:'@context') { 'https://www.w3.org/ns/activitystreams' } +node(:type) { 'Person' } +node(:id) { request.original_url } +node(:url) { |account| TagManager.instance.url_for(account) } +node(:name) { |account| account.display_name } +node(:preferredUsername) { |account| account.username } +node(:summary) { |account| account.note } +node(:icon) { |account| full_asset_url(account.avatar.url(:original)) } diff --git a/config/routes.rb b/config/routes.rb index 699f56833de..f831c423984 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -153,6 +153,12 @@ Rails.application.routes.draw do end end + namespace :activitypub do + resources :accounts do + get '/:id', to: 'accounts#show' + end + end + namespace :web do resource :settings, only: [:update] end From 8bd8ea7c0406a8eeb145471475b105366e195e6a Mon Sep 17 00:00:00 2001 From: Evan Minto Date: Sat, 4 Feb 2017 14:49:24 -0800 Subject: [PATCH 2/7] Remove unnecessary leftover code --- app/controllers/api/activitypub/accounts_controller.rb | 4 +--- config/routes.rb | 4 +--- 2 files changed, 2 insertions(+), 6 deletions(-) diff --git a/app/controllers/api/activitypub/accounts_controller.rb b/app/controllers/api/activitypub/accounts_controller.rb index efb6413a0dc..82936f0621b 100644 --- a/app/controllers/api/activitypub/accounts_controller.rb +++ b/app/controllers/api/activitypub/accounts_controller.rb @@ -1,9 +1,7 @@ # frozen_string_literal: true class Api::Activitypub::AccountsController < ApiController - before_action -> { doorkeeper_authorize! :read }, except: [:show] - before_action :require_user!, except: [:show] - before_action :set_account, except: [:verify_credentials, :suggestions, :search] + before_action :set_account respond_to :'application/activity+json' respond_to :'application/ld+json; profile="https://www.w3.org/ns/activitystreams#"' diff --git a/config/routes.rb b/config/routes.rb index f831c423984..4d0138b825d 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -154,9 +154,7 @@ Rails.application.routes.draw do end namespace :activitypub do - resources :accounts do - get '/:id', to: 'accounts#show' - end + resources :accounts, only: [:show] end namespace :web do From 94e213c6c11fb3476a6c151425052775427574e1 Mon Sep 17 00:00:00 2001 From: Evan Minto Date: Mon, 6 Feb 2017 01:19:05 -0800 Subject: [PATCH 3/7] Reuse existing controller and route --- app/controllers/accounts_controller.rb | 2 ++ .../api/activitypub/accounts_controller.rb | 18 ------------------ app/views/accounts/show.html.haml | 1 - .../{api/activitypub => }/accounts/show.rabl | 5 ++--- app/views/activitypub/base.rabl | 1 + app/views/activitypub/intransient.rabl | 3 +++ app/views/activitypub/types/person.rabl | 3 +++ config/initializers/mime_types.rb | 5 +++-- config/routes.rb | 4 ---- 9 files changed, 14 insertions(+), 28 deletions(-) delete mode 100644 app/controllers/api/activitypub/accounts_controller.rb rename app/views/{api/activitypub => }/accounts/show.rabl (68%) create mode 100644 app/views/activitypub/base.rabl create mode 100644 app/views/activitypub/intransient.rabl create mode 100644 app/views/activitypub/types/person.rabl diff --git a/app/controllers/accounts_controller.rb b/app/controllers/accounts_controller.rb index 411a41ccc29..b837f006e62 100644 --- a/app/controllers/accounts_controller.rb +++ b/app/controllers/accounts_controller.rb @@ -18,6 +18,8 @@ class AccountsController < ApplicationController format.atom do @entries = @account.stream_entries.order('id desc').where(hidden: false).with_includes.paginate_by_max_id(20, params[:max_id], params[:since_id]) end + + format.activitystreams2 end end diff --git a/app/controllers/api/activitypub/accounts_controller.rb b/app/controllers/api/activitypub/accounts_controller.rb deleted file mode 100644 index 82936f0621b..00000000000 --- a/app/controllers/api/activitypub/accounts_controller.rb +++ /dev/null @@ -1,18 +0,0 @@ -# frozen_string_literal: true - -class Api::Activitypub::AccountsController < ApiController - before_action :set_account - - respond_to :'application/activity+json' - respond_to :'application/ld+json; profile="https://www.w3.org/ns/activitystreams#"' - - def show - render content_type: :'application/ld+json; profile="https://www.w3.org/ns/activitystreams#"' - end - - private - - def set_account - @account = Account.find(params[:id]) - end -end diff --git a/app/views/accounts/show.html.haml b/app/views/accounts/show.html.haml index cd539890827..c194ce33dd3 100644 --- a/app/views/accounts/show.html.haml +++ b/app/views/accounts/show.html.haml @@ -4,7 +4,6 @@ - content_for :header_tags do %link{ rel: 'salmon', href: api_salmon_url(@account.id) }/ %link{ rel: 'alternate', type: 'application/atom+xml', href: account_url(@account, format: 'atom') }/ - %link{ rel: 'alternate', type: 'application/ld+json; profile="https://www.w3.org/ns/activitystreams#"', href: "http://mastodon.dev/api/v1/activitypub/accounts/#{@account.username}" }/ %meta{ property: 'og:site_name', content: 'Mastodon' }/ %meta{ property: 'og:type', content: 'profile' }/ diff --git a/app/views/api/activitypub/accounts/show.rabl b/app/views/accounts/show.rabl similarity index 68% rename from app/views/api/activitypub/accounts/show.rabl rename to app/views/accounts/show.rabl index 806789d0037..76aa4a80927 100644 --- a/app/views/api/activitypub/accounts/show.rabl +++ b/app/views/accounts/show.rabl @@ -1,8 +1,7 @@ +extends 'activitypub/types/person.rabl' + object @account -node(:'@context') { 'https://www.w3.org/ns/activitystreams' } -node(:type) { 'Person' } -node(:id) { request.original_url } node(:url) { |account| TagManager.instance.url_for(account) } node(:name) { |account| account.display_name } node(:preferredUsername) { |account| account.username } diff --git a/app/views/activitypub/base.rabl b/app/views/activitypub/base.rabl new file mode 100644 index 00000000000..c5e94997a1b --- /dev/null +++ b/app/views/activitypub/base.rabl @@ -0,0 +1 @@ +node(:'@context') { 'https://www.w3.org/ns/activitystreams' } diff --git a/app/views/activitypub/intransient.rabl b/app/views/activitypub/intransient.rabl new file mode 100644 index 00000000000..21261f56d52 --- /dev/null +++ b/app/views/activitypub/intransient.rabl @@ -0,0 +1,3 @@ +extends 'activitypub/base.rabl' + +node(:id) { request.original_url } diff --git a/app/views/activitypub/types/person.rabl b/app/views/activitypub/types/person.rabl new file mode 100644 index 00000000000..17c53bb7b25 --- /dev/null +++ b/app/views/activitypub/types/person.rabl @@ -0,0 +1,3 @@ +extends 'activitypub/intransient.rabl' + +node(:type) { 'Person' } \ No newline at end of file diff --git a/config/initializers/mime_types.rb b/config/initializers/mime_types.rb index 5a16a14e8e4..b1b73c84655 100644 --- a/config/initializers/mime_types.rb +++ b/config/initializers/mime_types.rb @@ -1,4 +1,5 @@ # Be sure to restart your server when you modify this file. -Mime::Type.register "application/json", :json, %w( text/x-json application/jsonrequest application/jrd+json ) -Mime::Type.register "text/xml", :xml, %w( application/xml application/atom+xml application/xrd+xml ) +Mime::Type.register "application/json", :json, %w( text/x-json application/jsonrequest application/jrd+json ) +Mime::Type.register "text/xml", :xml, %w( application/xml application/atom+xml application/xrd+xml ) +Mime::Type.register "application/activity+json", :activitystreams2 diff --git a/config/routes.rb b/config/routes.rb index 4d0138b825d..699f56833de 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -153,10 +153,6 @@ Rails.application.routes.draw do end end - namespace :activitypub do - resources :accounts, only: [:show] - end - namespace :web do resource :settings, only: [:update] end From 3fa5d059977388066d71e475e484728f6019d04e Mon Sep 17 00:00:00 2001 From: Evan Minto Date: Mon, 6 Feb 2017 11:39:08 -0800 Subject: [PATCH 4/7] Simplify RABL --- app/views/accounts/show.rabl | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/app/views/accounts/show.rabl b/app/views/accounts/show.rabl index 76aa4a80927..def91b42501 100644 --- a/app/views/accounts/show.rabl +++ b/app/views/accounts/show.rabl @@ -2,8 +2,7 @@ extends 'activitypub/types/person.rabl' object @account -node(:url) { |account| TagManager.instance.url_for(account) } -node(:name) { |account| account.display_name } -node(:preferredUsername) { |account| account.username } -node(:summary) { |account| account.note } -node(:icon) { |account| full_asset_url(account.avatar.url(:original)) } +attributes display_name: :name, username: :preferredUsername, note: :summary + +node(:icon) { |account| full_asset_url(account.avatar.url(:original)) } +node(:image) { |account| full_asset_url(account.header.url(:original)) } From da7f24c23827d9d4e8808367735f9ea6b050e6d8 Mon Sep 17 00:00:00 2001 From: Evan Minto Date: Mon, 6 Feb 2017 12:14:02 -0800 Subject: [PATCH 5/7] Add test --- spec/controllers/accounts_controller_spec.rb | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/spec/controllers/accounts_controller_spec.rb b/spec/controllers/accounts_controller_spec.rb index 34f17a94337..d2c93c7079f 100644 --- a/spec/controllers/accounts_controller_spec.rb +++ b/spec/controllers/accounts_controller_spec.rb @@ -24,6 +24,16 @@ RSpec.describe AccountsController, type: :controller do end end + context 'activitystreams2' do + before do + get :show, params: { username: alice.username }, format: 'activitystreams2' + end + + it 'returns http success with Activity Streams 2.0' do + expect(response).to have_http_status(:success) + end + end + context 'html' do before do get :show, params: { username: alice.username } From 53234e59479095968155bf7769e51614ef91c12d Mon Sep 17 00:00:00 2001 From: Evan Minto Date: Mon, 6 Feb 2017 12:15:47 -0800 Subject: [PATCH 6/7] Add trailing newline --- app/views/activitypub/types/person.rabl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/views/activitypub/types/person.rabl b/app/views/activitypub/types/person.rabl index 17c53bb7b25..c284fc53b69 100644 --- a/app/views/activitypub/types/person.rabl +++ b/app/views/activitypub/types/person.rabl @@ -1,3 +1,3 @@ extends 'activitypub/intransient.rabl' -node(:type) { 'Person' } \ No newline at end of file +node(:type) { 'Person' } From 28cbb6dc2176cb9ba57841c6dc52b9dbfaf074c8 Mon Sep 17 00:00:00 2001 From: Evan Minto Date: Mon, 6 Feb 2017 17:00:55 -0800 Subject: [PATCH 7/7] Add AS2 format to RABL files --- app/views/accounts/{show.rabl => show.activitystreams2.rabl} | 2 +- .../activitypub/{base.rabl => base.activitystreams2.rabl} | 0 app/views/activitypub/intransient.activitystreams2.rabl | 3 +++ app/views/activitypub/intransient.rabl | 3 --- app/views/activitypub/types/person.activitystreams2.rabl | 3 +++ app/views/activitypub/types/person.rabl | 3 --- 6 files changed, 7 insertions(+), 7 deletions(-) rename app/views/accounts/{show.rabl => show.activitystreams2.rabl} (81%) rename app/views/activitypub/{base.rabl => base.activitystreams2.rabl} (100%) create mode 100644 app/views/activitypub/intransient.activitystreams2.rabl delete mode 100644 app/views/activitypub/intransient.rabl create mode 100644 app/views/activitypub/types/person.activitystreams2.rabl delete mode 100644 app/views/activitypub/types/person.rabl diff --git a/app/views/accounts/show.rabl b/app/views/accounts/show.activitystreams2.rabl similarity index 81% rename from app/views/accounts/show.rabl rename to app/views/accounts/show.activitystreams2.rabl index def91b42501..dabae3f297f 100644 --- a/app/views/accounts/show.rabl +++ b/app/views/accounts/show.activitystreams2.rabl @@ -1,4 +1,4 @@ -extends 'activitypub/types/person.rabl' +extends 'activitypub/types/person.activitystreams2.rabl' object @account diff --git a/app/views/activitypub/base.rabl b/app/views/activitypub/base.activitystreams2.rabl similarity index 100% rename from app/views/activitypub/base.rabl rename to app/views/activitypub/base.activitystreams2.rabl diff --git a/app/views/activitypub/intransient.activitystreams2.rabl b/app/views/activitypub/intransient.activitystreams2.rabl new file mode 100644 index 00000000000..968e451c266 --- /dev/null +++ b/app/views/activitypub/intransient.activitystreams2.rabl @@ -0,0 +1,3 @@ +extends 'activitypub/base.activitystreams2.rabl' + +node(:id) { request.original_url } diff --git a/app/views/activitypub/intransient.rabl b/app/views/activitypub/intransient.rabl deleted file mode 100644 index 21261f56d52..00000000000 --- a/app/views/activitypub/intransient.rabl +++ /dev/null @@ -1,3 +0,0 @@ -extends 'activitypub/base.rabl' - -node(:id) { request.original_url } diff --git a/app/views/activitypub/types/person.activitystreams2.rabl b/app/views/activitypub/types/person.activitystreams2.rabl new file mode 100644 index 00000000000..487a60791f3 --- /dev/null +++ b/app/views/activitypub/types/person.activitystreams2.rabl @@ -0,0 +1,3 @@ +extends 'activitypub/intransient.activitystreams2.rabl' + +node(:type) { 'Person' } diff --git a/app/views/activitypub/types/person.rabl b/app/views/activitypub/types/person.rabl deleted file mode 100644 index c284fc53b69..00000000000 --- a/app/views/activitypub/types/person.rabl +++ /dev/null @@ -1,3 +0,0 @@ -extends 'activitypub/intransient.rabl' - -node(:type) { 'Person' }