Updated from tootsuite

pull/84/merge
Ondřej Hruška 2017-07-17 20:03:57 +02:00
commit c727eae441
34 changed files with 221 additions and 29 deletions

View File

@ -15,6 +15,7 @@ RUN echo "@edge https://nl.alpinelinux.org/alpine/edge/main" >> /etc/apk/reposit
&& apk -U upgrade \
&& apk add -t build-dependencies \
build-base \
libidn-dev \
libxml2-dev \
libxslt-dev \
postgresql-dev \
@ -27,6 +28,7 @@ RUN echo "@edge https://nl.alpinelinux.org/alpine/edge/main" >> /etc/apk/reposit
git \
icu-dev \
imagemagick@edge \
libidn \
libpq \
libxml2 \
libxslt \

View File

@ -20,7 +20,6 @@ class ActivityPub::OutboxesController < Api::BaseController
ActivityPub::CollectionPresenter.new(
id: account_outbox_url(@account),
type: :ordered,
current: account_outbox_url(@account),
size: @account.statuses_count,
items: @statuses
)

View File

@ -21,7 +21,6 @@ class FollowerAccountsController < ApplicationController
ActivityPub::CollectionPresenter.new(
id: account_followers_url(@account),
type: :ordered,
current: account_followers_url(@account),
size: @account.followers_count,
items: @follows.map { |f| ActivityPub::TagManager.instance.uri_for(f.account) }
)

View File

@ -21,7 +21,6 @@ class FollowingAccountsController < ApplicationController
ActivityPub::CollectionPresenter.new(
id: account_following_index_url(@account),
type: :ordered,
current: account_following_index_url(@account),
size: @account.following_count,
items: @follows.map { |f| ActivityPub::TagManager.instance.uri_for(f.target_account) }
)

View File

@ -23,7 +23,6 @@ class TagsController < ApplicationController
ActivityPub::CollectionPresenter.new(
id: tag_url(@tag),
type: :ordered,
current: tag_url(@tag),
size: @tag.statuses.count,
items: @statuses.map { |s| ActivityPub::TagManager.instance.uri_for(s) }
)

View File

@ -32,7 +32,7 @@ export default class ExtendedVideoPlayer extends React.PureComponent {
render () {
return (
<div className='extended-video-player' style={{ width: this.props.width, height: this.props.height }}>
<div className='extended-video-player'>
<video
ref={this.setRef}
src={this.props.src}

View File

@ -140,7 +140,7 @@ export default class ComposeForm extends ImmutablePureComponent {
handleEmojiPick = (data) => {
const position = this.autosuggestTextarea.textarea.selectionStart;
const emojiChar = String.fromCodePoint(parseInt(data.unicode, 16));
const emojiChar = data.unicode.split('-').map(code => String.fromCodePoint(parseInt(code, 16))).join('');
this._restoreCaret = position + emojiChar.length + 1;
this.props.onPickEmoji(position, data);
}

View File

@ -8,8 +8,6 @@ function main() {
const React = require('react');
const ReactDOM = require('react-dom');
require.context('../images/', true);
if (window.history && history.replaceState) {
const { pathname, search, hash } = window.location;
const path = pathname + search + hash;

View File

@ -126,7 +126,7 @@ const insertSuggestion = (state, position, token, completion) => {
};
const insertEmoji = (state, position, emojiData) => {
const emoji = String.fromCodePoint(parseInt(emojiData.unicode, 16));
const emoji = emojiData.unicode.split('-').map(code => String.fromCodePoint(parseInt(code, 16))).join('');
return state.withMutations(map => {
map.update('text', oldText => `${oldText.slice(0, position)}${emoji} ${oldText.slice(position)}`);

View File

@ -4,4 +4,6 @@ import { start } from 'rails-ujs';
require('font-awesome/css/font-awesome.css');
require('mastodon-application-style');
require.context('../images/', true);
start();

View File

@ -7,8 +7,6 @@ import loadPolyfills from '../mastodon/load_polyfills';
import { processBio } from '../glitch/util/bio_metadata';
import ready from '../mastodon/ready';
require.context('../images/', true);
const { localeData } = getLocale();
localeData.forEach(IntlRelativeFormat.__addLocaleData);

View File

@ -1384,8 +1384,8 @@
top: 0;
left: 0;
right: 0;
width: 100%;
height: 100%;
max-width: 100%;
max-height: 100%;
background-image: none;
}
@ -3313,8 +3313,9 @@ button.icon-button.active i.fa-retweet {
video {
max-width: 80vw;
max-height: 80vh;
width: 100%;
width: auto;
height: auto;
margin: auto;
}
.extended-video-player,
@ -3330,6 +3331,10 @@ button.icon-button.active i.fa-retweet {
background: url('../images/void.png') repeat;
object-fit: contain;
}
.react-swipeable-view-container {
max-width: 80vw;
}
}
.media-modal__close {

View File

@ -1,5 +1,5 @@
# frozen_string_literal: true
class ActivityPub::CollectionPresenter < ActiveModelSerializers::Model
attributes :id, :type, :current, :size, :items
attributes :id, :type, :size, :items
end

View File

@ -0,0 +1,15 @@
# frozen_string_literal: true
class ActivityPub::AcceptFollowSerializer < ActiveModel::Serializer
attributes :type, :actor
has_one :object, serializer: ActivityPub::FollowSerializer
def type
'Accept'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.target_account)
end
end

View File

@ -7,6 +7,8 @@ class ActivityPub::ActorSerializer < ActiveModel::Serializer
:inbox, :outbox, :preferred_username,
:name, :summary, :icon, :image
has_one :public_key, serializer: ActivityPub::PublicKeySerializer
def id
account_url(object)
end
@ -50,4 +52,8 @@ class ActivityPub::ActorSerializer < ActiveModel::Serializer
def image
full_asset_url(object.header.url(:original))
end
def public_key
object
end
end

View File

@ -0,0 +1,18 @@
# frozen_string_literal: true
class ActivityPub::BlockSerializer < ActiveModel::Serializer
attributes :type, :actor
attribute :virtual_object, key: :object
def type
'Block'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.account)
end
def virtual_object
ActivityPub::TagManager.instance.uri_for(object.target_account)
end
end

View File

@ -6,8 +6,7 @@ class ActivityPub::CollectionSerializer < ActiveModel::Serializer
super
end
attributes :id, :type, :total_items,
:current
attributes :id, :type, :total_items
has_many :items, key: :ordered_items

View File

@ -0,0 +1,18 @@
# frozen_string_literal: true
class ActivityPub::DeleteSerializer < ActiveModel::Serializer
attributes :type, :actor
attribute :virtual_object, key: :object
def type
'Delete'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.account)
end
def virtual_object
ActivityPub::TagManager.instance.uri_for(object)
end
end

View File

@ -0,0 +1,18 @@
# frozen_string_literal: true
class ActivityPub::FollowSerializer < ActiveModel::Serializer
attributes :type, :actor
attribute :virtual_object, key: :object
def type
'Follow'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.account)
end
def virtual_object
ActivityPub::TagManager.instance.uri_for(object.target_account)
end
end

View File

@ -0,0 +1,18 @@
# frozen_string_literal: true
class ActivityPub::LikeSerializer < ActiveModel::Serializer
attributes :type, :actor
attribute :virtual_object, key: :object
def type
'Like'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.account)
end
def virtual_object
ActivityPub::TagManager.instance.uri_for(object.status)
end
end

View File

@ -3,7 +3,7 @@
class ActivityPub::NoteSerializer < ActiveModel::Serializer
attributes :id, :type, :summary, :content,
:in_reply_to, :published, :url,
:actor, :to, :cc, :sensitive
:attributed_to, :to, :cc, :sensitive
has_many :media_attachments, key: :attachment
has_many :virtual_tags, key: :tag
@ -36,7 +36,7 @@ class ActivityPub::NoteSerializer < ActiveModel::Serializer
ActivityPub::TagManager.instance.url_for(object)
end
def actor
def attributed_to
ActivityPub::TagManager.instance.uri_for(object.account)
end

View File

@ -0,0 +1,17 @@
# frozen_string_literal: true
class ActivityPub::PublicKeySerializer < ActiveModel::Serializer
attributes :id, :owner, :public_key_pem
def id
[ActivityPub::TagManager.instance.uri_for(object), '#main-key'].join
end
def owner
ActivityPub::TagManager.instance.uri_for(object)
end
def public_key_pem
object.public_key
end
end

View File

@ -0,0 +1,15 @@
# frozen_string_literal: true
class ActivityPub::RejectFollowSerializer < ActiveModel::Serializer
attributes :type, :actor
has_one :object, serializer: ActivityPub::FollowSerializer
def type
'Reject'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.target_account)
end
end

View File

@ -0,0 +1,15 @@
# frozen_string_literal: true
class ActivityPub::UndoBlockSerializer < ActiveModel::Serializer
attributes :type, :actor
has_one :object, serializer: ActivityPub::BlockSerializer
def type
'Undo'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.account)
end
end

View File

@ -0,0 +1,15 @@
# frozen_string_literal: true
class ActivityPub::UndoFollowSerializer < ActiveModel::Serializer
attributes :type, :actor
has_one :object, serializer: ActivityPub::FollowSerializer
def type
'Undo'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.account)
end
end

View File

@ -0,0 +1,15 @@
# frozen_string_literal: true
class ActivityPub::UndoLikeSerializer < ActiveModel::Serializer
attributes :type, :actor
has_one :object, serializer: ActivityPub::LikeSerializer
def type
'Undo'
end
def actor
ActivityPub::TagManager.instance.uri_for(object.account)
end
end

View File

@ -0,0 +1,15 @@
# frozen_string_literal: true
class ActivityPub::UpdateSerializer < ActiveModel::Serializer
attributes :type, :actor
has_one :object, serializer: ActivityPub::ActorSerializer
def type
'Update'
end
def actor
ActivityPub::TagManager.instance.uri_for(object)
end
end

View File

@ -9,7 +9,7 @@ class WebPushNotificationWorker
recipient = Account.find(recipient_id)
notification = Notification.find(notification_id)
sessions_with_subscriptions = recipient.user.session_activations.reject { |session| session.web_push_subscription.nil? }
sessions_with_subscriptions = recipient.user.session_activations.where.not(web_push_subscription: nil)
sessions_with_subscriptions.each do |session|
begin
@ -17,8 +17,7 @@ class WebPushNotificationWorker
rescue Webpush::InvalidSubscription, Webpush::ExpiredSubscription
# Subscription expiration is not currently implemented in any browser
session.web_push_subscription.destroy!
session.web_push_subscription = nil
session.save!
session.update!(web_push_subscription: nil)
rescue Webpush::PayloadTooLarge => e
Rails.logger.error(e)
end

View File

@ -85,6 +85,7 @@ Rails.application.configure do
:ca_file => ENV['SMTP_CA_FILE'].presence,
:openssl_verify_mode => ENV['SMTP_OPENSSL_VERIFY_MODE'],
:enable_starttls_auto => ENV['SMTP_ENABLE_STARTTLS_AUTO'] || true,
:tls => ENV['SMTP_TLS'].presence,
}
config.action_mailer.delivery_method = ENV.fetch('SMTP_DELIVERY_METHOD', 'smtp').to_sym

View File

@ -10,7 +10,7 @@ pl:
domain_count_after: instancji
domain_count_before: Serwer połączony z
features:
humane_approach_body: Nauczeni na błędach innych sieci społecznościowych, Mastodon został zaprojektowany tak, aby uniknąć częstych nadużyć.
humane_approach_body: Nauczeni na błędach innych sieci społecznościowych, zaprojektowaliśmy Mastodona tak, aby uniknąć częstych nadużyć.
humane_approach_title: Bardziej ludzkie podejście
not_a_product_body: Mastodon nie jest komercyjną siecią. Nie doświadczysz tu reklam, zbierania danych, ani centralnego ośrodka, tak jak w przypadku wielu rozwiązań.
not_a_product_title: Jesteś człowiekiem, nie produktem

View File

@ -8,7 +8,7 @@ en:
one: <span class="name-counter">1</span> character left
other: <span class="name-counter">%{count}</span> characters left
header: PNG, GIF or JPG. At most 2MB. Will be downscaled to 700x335px
locked: Requires you to manually approve followers and defaults post privacy to followers-only
locked: Requires you to manually approve followers
note:
one: <span class="note-counter">1</span> character left
other: <span class="note-counter">%{count}</span> characters left

View File

@ -6,7 +6,7 @@ ja:
avatar: 2MBまでのPNGやGIF、JPGが利用可能です。120x120pxまで縮小されます。
display_name: あと<span class="name-counter">%{count}</span>文字入力できます。
header: 2MBまでのPNGやGIF、JPGが利用可能です。 700x335pxまで縮小されます。
locked: フォロワーを手動で承認する必要があります。デフォルトではトゥートの公開範囲はフォロワーのみです。
locked: フォロワーを手動で承認する必要があります。
note: あと<span class="note-counter">%{count}</span>文字入力できます。
imports:
data: 他の Mastodon インスタンスからエクスポートしたCSVファイルを選択して下さい

View File

@ -10,7 +10,7 @@ pl:
one: Pozostał <span class="name-counter">1</span> znak.
other: Pozostało <span class="name-counter">%{count}</span> znaków
header: PNG, GIF lub JPG. Maksymalnie 2MB. Zostanie zmniejszony do 700x335px
locked: Musisz akceptować obserwacje; Twoje wpisy są domyślnie widoczne tylko dla Twoich obserwujących
locked: Musisz akceptować prośby o śledzenie
note:
few: Pozostały <span class="name-counter">%{count}</span> znaki.
many: Pozostało <span class="name-counter">%{count}</span> znaków

View File

@ -232,9 +232,16 @@ namespace :mastodon do
task prepare_for_foreign_keys: :environment do
# All the deletes:
ActiveRecord::Base.connection.execute('DELETE FROM statuses USING statuses s LEFT JOIN accounts a ON a.id = s.account_id WHERE statuses.id = s.id AND a.id IS NULL')
ActiveRecord::Base.connection.execute('DELETE FROM account_domain_blocks USING account_domain_blocks adb LEFT JOIN accounts a ON a.id = adb.account_id WHERE account_domain_blocks.id = adb.id AND a.id IS NULL')
ActiveRecord::Base.connection.execute('DELETE FROM conversation_mutes USING conversation_mutes cm LEFT JOIN accounts a ON a.id = cm.account_id WHERE conversation_mutes.id = cm.id AND a.id IS NULL')
ActiveRecord::Base.connection.execute('DELETE FROM conversation_mutes USING conversation_mutes cm LEFT JOIN conversations c ON c.id = cm.conversation_id WHERE conversation_mutes.id = cm.id AND c.id IS NULL')
if ActiveRecord::Base.connection.table_exists? :account_domain_blocks
ActiveRecord::Base.connection.execute('DELETE FROM account_domain_blocks USING account_domain_blocks adb LEFT JOIN accounts a ON a.id = adb.account_id WHERE account_domain_blocks.id = adb.id AND a.id IS NULL')
end
if ActiveRecord::Base.connection.table_exists? :conversation_mutes
ActiveRecord::Base.connection.execute('DELETE FROM conversation_mutes USING conversation_mutes cm LEFT JOIN accounts a ON a.id = cm.account_id WHERE conversation_mutes.id = cm.id AND a.id IS NULL')
ActiveRecord::Base.connection.execute('DELETE FROM conversation_mutes USING conversation_mutes cm LEFT JOIN conversations c ON c.id = cm.conversation_id WHERE conversation_mutes.id = cm.id AND c.id IS NULL')
end
ActiveRecord::Base.connection.execute('DELETE FROM favourites USING favourites f LEFT JOIN accounts a ON a.id = f.account_id WHERE favourites.id = f.id AND a.id IS NULL')
ActiveRecord::Base.connection.execute('DELETE FROM favourites USING favourites f LEFT JOIN statuses s ON s.id = f.status_id WHERE favourites.id = f.id AND s.id IS NULL')
ActiveRecord::Base.connection.execute('DELETE FROM blocks USING blocks b LEFT JOIN accounts a ON a.id = b.account_id WHERE blocks.id = b.id AND a.id IS NULL')