about summary refs log tree commit diff
diff options
context:
space:
mode:
authorJenkins <jenkins@jenkins.ninjawedding.org>2018-01-03 04:17:11 +0000
committerJenkins <jenkins@jenkins.ninjawedding.org>2018-01-03 04:17:11 +0000
commit933840bebf4ce8f5282c88e8c3e8c1b3675fbf2d (patch)
treee1d156a830d9446218ad1f250111dfc32df76961
parentfa768abf5c10eb3469a26347a9fa5ff677b3d394 (diff)
parent99f962ba731f67050a914bb5b9a245869531ebd1 (diff)
Merge remote-tracking branch 'tootsuite/master' into glitchsoc/master
-rw-r--r--Gemfile2
-rw-r--r--Gemfile.lock2
-rw-r--r--app/controllers/auth/registrations_controller.rb4
-rw-r--r--app/controllers/statuses_controller.rb7
-rw-r--r--app/helpers/settings_helper.rb1
-rw-r--r--app/javascript/mastodon/actions/notifications.js2
-rw-r--r--app/javascript/mastodon/actions/push_notifications/index.js4
-rw-r--r--app/javascript/mastodon/actions/push_notifications/setter.js4
-rw-r--r--app/javascript/mastodon/actions/settings.js6
-rw-r--r--app/javascript/mastodon/features/compose/containers/warning_container.js9
-rw-r--r--app/javascript/mastodon/features/notifications/components/column_settings.js4
-rw-r--r--app/javascript/mastodon/features/notifications/containers/column_settings_container.js8
-rw-r--r--app/javascript/mastodon/locales/sr-Latn.json259
-rw-r--r--app/javascript/mastodon/locales/sr.json18
-rw-r--r--app/javascript/mastodon/reducers/push_notifications.js2
-rw-r--r--app/javascript/mastodon/reducers/settings.js2
-rw-r--r--app/javascript/styles/mastodon/components.scss5
-rw-r--r--app/lib/activity_tracker.rb2
-rw-r--r--app/lib/activitypub/activity/delete.rb1
-rw-r--r--app/lib/sanitize_config.rb8
-rw-r--r--app/mailers/user_mailer.rb15
-rw-r--r--app/models/user.rb11
-rw-r--r--app/services/activitypub/process_account_service.rb2
-rwxr-xr-xapp/views/layouts/application.html.haml3
-rw-r--r--app/views/user_mailer/confirmation_instructions.sr-Latn.html.erb15
-rw-r--r--app/views/user_mailer/confirmation_instructions.sr-Latn.text.erb12
-rw-r--r--app/views/user_mailer/email_changed.en.html.erb15
-rw-r--r--app/views/user_mailer/email_changed.en.text.erb13
-rw-r--r--app/views/user_mailer/password_change.sr-Latn.html.erb3
-rw-r--r--app/views/user_mailer/password_change.sr-Latn.text.erb3
-rw-r--r--app/views/user_mailer/reconfirmation_instructions.en.html.erb15
-rw-r--r--app/views/user_mailer/reconfirmation_instructions.en.text.erb12
-rw-r--r--app/views/user_mailer/reset_password_instructions.sr-Latn.html.erb8
-rw-r--r--app/views/user_mailer/reset_password_instructions.sr-Latn.text.erb8
-rw-r--r--config/application.rb1
-rw-r--r--config/initializers/devise.rb5
-rw-r--r--config/locales/activerecord.sr-Latn.yml13
-rw-r--r--config/locales/devise.en.yml4
-rw-r--r--config/locales/devise.sr-Latn.yml63
-rw-r--r--config/locales/doorkeeper.sr-Latn.yml119
-rw-r--r--config/locales/simple_form.sr-Latn.yml75
-rw-r--r--config/locales/simple_form.sr.yml4
-rw-r--r--config/locales/sr-Latn.yml723
-rw-r--r--config/locales/sr.yml14
-rw-r--r--spec/lib/formatter_spec.rb2
-rw-r--r--spec/mailers/user_mailer_spec.rb26
46 files changed, 1482 insertions, 52 deletions
diff --git a/Gemfile b/Gemfile
index bea840041..b9bcf6a43 100644
--- a/Gemfile
+++ b/Gemfile
@@ -29,7 +29,7 @@ gem 'browser'
 gem 'charlock_holmes', '~> 0.7.5'
 gem 'iso-639'
 gem 'cld3', '~> 3.2.0'
-gem 'devise', '~> 4.2'
+gem 'devise', '~> 4.3'
 gem 'devise-two-factor', '~> 3.0'
 gem 'doorkeeper', '~> 4.2'
 gem 'fast_blank', '~> 1.0'
diff --git a/Gemfile.lock b/Gemfile.lock
index 8af7872af..58c59ad35 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -562,7 +562,7 @@ DEPENDENCIES
   charlock_holmes (~> 0.7.5)
   cld3 (~> 3.2.0)
   climate_control (~> 0.2)
-  devise (~> 4.2)
+  devise (~> 4.3)
   devise-two-factor (~> 3.0)
   doorkeeper (~> 4.2)
   dotenv-rails (~> 2.2)
diff --git a/app/controllers/auth/registrations_controller.rb b/app/controllers/auth/registrations_controller.rb
index f4247fd95..2b6a1bdbc 100644
--- a/app/controllers/auth/registrations_controller.rb
+++ b/app/controllers/auth/registrations_controller.rb
@@ -38,6 +38,10 @@ class Auth::RegistrationsController < Devise::RegistrationsController
     new_user_session_path
   end
 
+  def after_update_path_for(_resource)
+    edit_user_registration_path
+  end
+
   def check_enabled_registrations
     redirect_to root_path if single_user_mode? || !allowed_registrations?
   end
diff --git a/app/controllers/statuses_controller.rb b/app/controllers/statuses_controller.rb
index 84c9e7685..6a635fba2 100644
--- a/app/controllers/statuses_controller.rb
+++ b/app/controllers/statuses_controller.rb
@@ -10,6 +10,7 @@ class StatusesController < ApplicationController
   before_action :set_link_headers
   before_action :check_account_suspension
   before_action :redirect_to_original, only: [:show]
+  before_action { response.headers['Vary'] = 'Accept' }
 
   def show
     respond_to do |format|
@@ -26,6 +27,12 @@ class StatusesController < ApplicationController
                serializer: ActivityPub::NoteSerializer,
                adapter: ActivityPub::Adapter,
                content_type: 'application/activity+json'
+
+        # Allow HTTP caching for 3 minutes if the status is public
+        unless @stream_entry.hidden?
+          request.session_options[:skip] = true
+          expires_in(3.minutes, public: true)
+        end
       end
     end
   end
diff --git a/app/helpers/settings_helper.rb b/app/helpers/settings_helper.rb
index ce8aadcc6..a63eb5e43 100644
--- a/app/helpers/settings_helper.rb
+++ b/app/helpers/settings_helper.rb
@@ -30,6 +30,7 @@ module SettingsHelper
     ru: 'Русский',
     sk: 'Slovensky',
     sr: 'Српски',
+    'sr-Latn': 'Srpski (latinica)',
     sv: 'Svenska',
     th: 'ภาษาไทย',
     tr: 'Türkçe',
diff --git a/app/javascript/mastodon/actions/notifications.js b/app/javascript/mastodon/actions/notifications.js
index b24ac8b73..502690045 100644
--- a/app/javascript/mastodon/actions/notifications.js
+++ b/app/javascript/mastodon/actions/notifications.js
@@ -31,7 +31,7 @@ const fetchRelatedRelationships = (dispatch, notifications) => {
 
 const unescapeHTML = (html) => {
   const wrapper = document.createElement('div');
-  html = html.replace(/<br \/>|<br>|\n/, ' ');
+  html = html.replace(/<br \/>|<br>|\n/g, ' ');
   wrapper.innerHTML = html;
   return wrapper.textContent;
 };
diff --git a/app/javascript/mastodon/actions/push_notifications/index.js b/app/javascript/mastodon/actions/push_notifications/index.js
index 376b55b62..2ffec500a 100644
--- a/app/javascript/mastodon/actions/push_notifications/index.js
+++ b/app/javascript/mastodon/actions/push_notifications/index.js
@@ -15,9 +15,9 @@ export {
   register,
 };
 
-export function changeAlerts(key, value) {
+export function changeAlerts(path, value) {
   return dispatch => {
-    dispatch(setAlerts(key, value));
+    dispatch(setAlerts(path, value));
     dispatch(saveSettings());
   };
 }
diff --git a/app/javascript/mastodon/actions/push_notifications/setter.js b/app/javascript/mastodon/actions/push_notifications/setter.js
index a2cc41c5a..5561766bf 100644
--- a/app/javascript/mastodon/actions/push_notifications/setter.js
+++ b/app/javascript/mastodon/actions/push_notifications/setter.js
@@ -23,11 +23,11 @@ export function clearSubscription () {
   };
 }
 
-export function setAlerts (key, value) {
+export function setAlerts (path, value) {
   return dispatch => {
     dispatch({
       type: SET_ALERTS,
-      key,
+      path,
       value,
     });
   };
diff --git a/app/javascript/mastodon/actions/settings.js b/app/javascript/mastodon/actions/settings.js
index 79adca18c..aeef43527 100644
--- a/app/javascript/mastodon/actions/settings.js
+++ b/app/javascript/mastodon/actions/settings.js
@@ -4,11 +4,11 @@ import { debounce } from 'lodash';
 export const SETTING_CHANGE = 'SETTING_CHANGE';
 export const SETTING_SAVE   = 'SETTING_SAVE';
 
-export function changeSetting(key, value) {
+export function changeSetting(path, value) {
   return dispatch => {
     dispatch({
       type: SETTING_CHANGE,
-      key,
+      path,
       value,
     });
 
@@ -21,7 +21,7 @@ const debouncedSave = debounce((dispatch, getState) => {
     return;
   }
 
-  const data = getState().get('settings').filter((_, key) => key !== 'saved').toJS();
+  const data = getState().get('settings').filter((_, path) => path !== 'saved').toJS();
 
   axios.put('/api/web/settings', { data }).then(() => dispatch({ type: SETTING_SAVE }));
 }, 5000, { trailing: true });
diff --git a/app/javascript/mastodon/features/compose/containers/warning_container.js b/app/javascript/mastodon/features/compose/containers/warning_container.js
index d34471a3e..b9f280958 100644
--- a/app/javascript/mastodon/features/compose/containers/warning_container.js
+++ b/app/javascript/mastodon/features/compose/containers/warning_container.js
@@ -5,20 +5,27 @@ import PropTypes from 'prop-types';
 import { FormattedMessage } from 'react-intl';
 import { me } from '../../../initial_state';
 
+const APPROX_HASHTAG_RE = /(?:^|[^\/\)\w])#(\S+)/i;
+
 const mapStateToProps = state => ({
   needsLockWarning: state.getIn(['compose', 'privacy']) === 'private' && !state.getIn(['accounts', me, 'locked']),
+  hashtagWarning: state.getIn(['compose', 'privacy']) !== 'public' && APPROX_HASHTAG_RE.test(state.getIn(['compose', 'text'])),
 });
 
-const WarningWrapper = ({ needsLockWarning }) => {
+const WarningWrapper = ({ needsLockWarning, hashtagWarning }) => {
   if (needsLockWarning) {
     return <Warning message={<FormattedMessage id='compose_form.lock_disclaimer' defaultMessage='Your account is not {locked}. Anyone can follow you to view your follower-only posts.' values={{ locked: <a href='/settings/profile'><FormattedMessage id='compose_form.lock_disclaimer.lock' defaultMessage='locked' /></a> }} />} />;
   }
+  if (hashtagWarning) {
+    return <Warning message={<FormattedMessage id='compose_form.hashtag_warning' defaultMessage="This toot won't be listed under any hashtag as it is unlisted. Only public toots can be searched by hashtag." />} />;
+  }
 
   return null;
 };
 
 WarningWrapper.propTypes = {
   needsLockWarning: PropTypes.bool,
+  hashtagWarning: PropTypes.bool,
 };
 
 export default connect(mapStateToProps)(WarningWrapper);
diff --git a/app/javascript/mastodon/features/notifications/components/column_settings.js b/app/javascript/mastodon/features/notifications/components/column_settings.js
index 23545185c..d9638aaf3 100644
--- a/app/javascript/mastodon/features/notifications/components/column_settings.js
+++ b/app/javascript/mastodon/features/notifications/components/column_settings.js
@@ -14,8 +14,8 @@ export default class ColumnSettings extends React.PureComponent {
     onClear: PropTypes.func.isRequired,
   };
 
-  onPushChange = (key, checked) => {
-    this.props.onChange(['push', ...key], checked);
+  onPushChange = (path, checked) => {
+    this.props.onChange(['push', ...path], checked);
   }
 
   render () {
diff --git a/app/javascript/mastodon/features/notifications/containers/column_settings_container.js b/app/javascript/mastodon/features/notifications/containers/column_settings_container.js
index f4c63fee6..e9cef0a7b 100644
--- a/app/javascript/mastodon/features/notifications/containers/column_settings_container.js
+++ b/app/javascript/mastodon/features/notifications/containers/column_settings_container.js
@@ -18,11 +18,11 @@ const mapStateToProps = state => ({
 
 const mapDispatchToProps = (dispatch, { intl }) => ({
 
-  onChange (key, checked) {
-    if (key[0] === 'push') {
-      dispatch(changePushNotifications(key.slice(1), checked));
+  onChange (path, checked) {
+    if (path[0] === 'push') {
+      dispatch(changePushNotifications(path.slice(1), checked));
     } else {
-      dispatch(changeSetting(['notifications', ...key], checked));
+      dispatch(changeSetting(['notifications', ...path], checked));
     }
   },
 
diff --git a/app/javascript/mastodon/locales/sr-Latn.json b/app/javascript/mastodon/locales/sr-Latn.json
new file mode 100644
index 000000000..971ffb5c5
--- /dev/null
+++ b/app/javascript/mastodon/locales/sr-Latn.json
@@ -0,0 +1,259 @@
+{
+  "account.block": "Blokiraj korisnika @{name}",
+  "account.block_domain": "Sakrij sve sa domena {domain}",
+  "account.disclaimer_full": "Navedene informacije možda ne odslikavaju korisnički profil u potpunosti.",
+  "account.edit_profile": "Izmeni profil",
+  "account.follow": "Zaprati",
+  "account.followers": "Pratioca",
+  "account.follows": "Prati",
+  "account.follows_you": "Prati Vas",
+  "account.hide_reblogs": "Sakrij podrške koje daje korisnika @{name}",
+  "account.media": "Mediji",
+  "account.mention": "Pomeni korisnika @{name}",
+  "account.moved_to": "{name} se pomerio na:",
+  "account.mute": "Mutiraj @{name}",
+  "account.mute_notifications": "Isključi obaveštenja od korisnika @{name}",
+  "account.posts": "Statusa",
+  "account.report": "Prijavi @{name}",
+  "account.requested": "Čekam odobrenje. Kliknite da poništite zahtev za praćenje",
+  "account.share": "Podeli profil korisnika @{name}",
+  "account.show_reblogs": "Prikaži podrške od korisnika @{name}",
+  "account.unblock": "Odblokiraj korisnika @{name}",
+  "account.unblock_domain": "Odblokiraj domen {domain}",
+  "account.unfollow": "Otprati",
+  "account.unmute": "Odmutiraj @{name}",
+  "account.unmute_notifications": "Uključi nazad obaveštenja od korisnika @{name}",
+  "account.view_full_profile": "Vidi ceo profil",
+  "boost_modal.combo": "Možete pritisnuti {combo} da preskočite ovo sledeći put",
+  "bundle_column_error.body": "Nešto je pošlo po zlu prilikom učitavanja ove komponente.",
+  "bundle_column_error.retry": "Pokušajte ponovo",
+  "bundle_column_error.title": "Mrežna greška",
+  "bundle_modal_error.close": "Zatvori",
+  "bundle_modal_error.message": "Nešto nije bilo u redu pri učitavanju ove komponente.",
+  "bundle_modal_error.retry": "Pokušajte ponovo",
+  "column.blocks": "Blokirani korisnici",
+  "column.community": "Lokalna lajna",
+  "column.favourites": "Omiljeni",
+  "column.follow_requests": "Zahtevi za praćenje",
+  "column.home": "Početna",
+  "column.lists": "Liste",
+  "column.mutes": "Mutirani korisnici",
+  "column.notifications": "Obaveštenja",
+  "column.pins": "Prikačeni tutovi",
+  "column.public": "Združena lajna",
+  "column_back_button.label": "Nazad",
+  "column_header.hide_settings": "Sakrij postavke",
+  "column_header.moveLeft_settings": "Pomeri kolonu ulevo",
+  "column_header.moveRight_settings": "Pomeri kolonu udesno",
+  "column_header.pin": "Prikači",
+  "column_header.show_settings": "Prikaži postavke",
+  "column_header.unpin": "Otkači",
+  "column_subheading.navigation": "Navigacija",
+  "column_subheading.settings": "Postavke",
+  "compose_form.lock_disclaimer": "Vaš nalog nije {locked}. Svako može da Vas zaprati i da vidi objave namenjene samo Vašim pratiocima.",
+  "compose_form.lock_disclaimer.lock": "zaključan",
+  "compose_form.placeholder": "Šta Vam je na umu?",
+  "compose_form.publish": "Tutni",
+  "compose_form.publish_loud": "{publish}!",
+  "compose_form.sensitive": "Obeleži multimediju kao osetljivu",
+  "compose_form.spoiler": "Sakrij tekst ispod upozorenja",
+  "compose_form.spoiler_placeholder": "Ovde upišite upozorenje",
+  "confirmation_modal.cancel": "Poništi",
+  "confirmations.block.confirm": "Blokiraj",
+  "confirmations.block.message": "Da li ste sigurni da želite da blokirate korisnika {name}?",
+  "confirmations.delete.confirm": "Obriši",
+  "confirmations.delete.message": "Da li ste sigurni da želite obrišete ovaj status?",
+  "confirmations.delete_list.confirm": "Obriši",
+  "confirmations.delete_list.message": "Da li ste sigurni da želite da bespovratno obrišete ovu listu?",
+  "confirmations.domain_block.confirm": "Sakrij ceo domen",
+  "confirmations.domain_block.message": "Da li ste stvarno, stvarno sigurno da želite da blokirate ceo domen {domain}? U većini slučajeva, par dobrih blokiranja ili mutiranja su dovoljna i preporučljiva.",
+  "confirmations.mute.confirm": "Mutiraj",
+  "confirmations.mute.message": "Da li stvarno želite da mutirate korisnika {name}?",
+  "confirmations.unfollow.confirm": "Otprati",
+  "confirmations.unfollow.message": "Da li ste sigurni da želite da otpratite korisnika {name}?",
+  "embed.instructions": "Ugradi ovaj status na Vaš veb sajt kopiranjem koda ispod.",
+  "embed.preview": "Ovako će da izgleda:",
+  "emoji_button.activity": "Aktivnost",
+  "emoji_button.custom": "Proizvoljno",
+  "emoji_button.flags": "Zastave",
+  "emoji_button.food": "Hrana & piće",
+  "emoji_button.label": "Ubaci smajli",
+  "emoji_button.nature": "Priroda",
+  "emoji_button.not_found": "Nema smajlija!! (╯°□°)╯︵ ┻━┻",
+  "emoji_button.objects": "Objekti",
+  "emoji_button.people": "Ljudi",
+  "emoji_button.recent": "Najčešće korišćeni",
+  "emoji_button.search": "Pretraga...",
+  "emoji_button.search_results": "Rezultati pretrage",
+  "emoji_button.symbols": "Simboli",
+  "emoji_button.travel": "Putovanja & mesta",
+  "empty_column.community": "Lokalna lajna je prazna. Napišite nešto javno da lajna produva!",
+  "empty_column.hashtag": "Trenutno nema ništa na ovom heštegu.",
+  "empty_column.home": "Vaša lajna je prazna! Posetite {public} ili koristite pretragu da počnete i upoznajete nove ljude.",
+  "empty_column.home.public_timeline": "javna lajna",
+  "empty_column.list": "U ovoj listi još nema ničega. Kada članovi liste objave nove statuse, oni će se pojavljivati ovde.",
+  "empty_column.notifications": "Trenutno nemate obaveštenja. Družite se malo da započnete razgovore.",
+  "empty_column.public": "Ovde nema ničega! Napišite nešto javno, ili nađite korisnike sa drugih instanci koje ćete zapratiti da popunite ovu prazninu",
+  "follow_request.authorize": "Odobri",
+  "follow_request.reject": "Odbij",
+  "getting_started.appsshort": "Aplikacije",
+  "getting_started.faq": "ČPP",
+  "getting_started.heading": "Da počnete",
+  "getting_started.open_source_notice": "Mastodont je softver otvorenog koda. Možete mu doprineti ili prijaviti probleme preko GitHub-a na {github}.",
+  "getting_started.userguide": "Korisničko uputstvo",
+  "home.column_settings.advanced": "Napredno",
+  "home.column_settings.basic": "Osnovno",
+  "home.column_settings.filter_regex": "Filtriraj regularnim izrazima",
+  "home.column_settings.show_reblogs": "Prikaži i podržavanja",
+  "home.column_settings.show_replies": "Prikaži odgovore",
+  "home.settings": "Postavke kolone",
+  "keyboard_shortcuts.back": "da odete nazad",
+  "keyboard_shortcuts.boost": "da podržite",
+  "keyboard_shortcuts.column": "da se prebacite na status u jednoj od kolona",
+  "keyboard_shortcuts.compose": "da se prebacite na pisanje novog tuta",
+  "keyboard_shortcuts.description": "Opis",
+  "keyboard_shortcuts.down": "da se pomerite na dole u listi",
+  "keyboard_shortcuts.enter": "da otvorite status",
+  "keyboard_shortcuts.favourite": "da označite kao omiljeno",
+  "keyboard_shortcuts.heading": "Prečice na tastaturi",
+  "keyboard_shortcuts.hotkey": "Prečica",
+  "keyboard_shortcuts.legend": "da prikažete ovaj podsetnik",
+  "keyboard_shortcuts.mention": "da pomenete autora",
+  "keyboard_shortcuts.reply": "da odgovorite",
+  "keyboard_shortcuts.search": "da se prebacite na pretragu",
+  "keyboard_shortcuts.toot": "da započnete skroz novi tut",
+  "keyboard_shortcuts.unfocus": "da ne budete više na pretrazi/pravljenju novog tuta",
+  "keyboard_shortcuts.up": "da se pomerite na gore u listi",
+  "lightbox.close": "Zatvori",
+  "lightbox.next": "Sledeći",
+  "lightbox.previous": "Prethodni",
+  "lists.account.add": "Dodaj na listu",
+  "lists.account.remove": "Ukloni sa liste",
+  "lists.delete": "Obriši listu",
+  "lists.edit": "Izmeni listu",
+  "lists.new.create": "Dodaj listu",
+  "lists.new.title_placeholder": "Naslov nove liste",
+  "lists.search": "Pretraži među ljudima koje pratite",
+  "lists.subheading": "Vaše liste",
+  "loading_indicator.label": "Učitavam...",
+  "media_gallery.toggle_visible": "Uključi/isključi vidljivost",
+  "missing_indicator.label": "Nije pronađeno",
+  "mute_modal.hide_notifications": "Sakrij obaveštenja od ovog korisnika?",
+  "navigation_bar.blocks": "Blokirani korisnici",
+  "navigation_bar.community_timeline": "Lokalna lajna",
+  "navigation_bar.edit_profile": "Izmeni profil",
+  "navigation_bar.favourites": "Omiljeni",
+  "navigation_bar.follow_requests": "Zahtevi za praćenje",
+  "navigation_bar.info": "O ovoj instanci",
+  "navigation_bar.keyboard_shortcuts": "Prečice na tastaturi",
+  "navigation_bar.lists": "Liste",
+  "navigation_bar.logout": "Odjava",
+  "navigation_bar.mutes": "Mutirani korisnici",
+  "navigation_bar.pins": "Prikačeni tutovi",
+  "navigation_bar.preferences": "Podešavanja",
+  "navigation_bar.public_timeline": "Združena lajna",
+  "notification.favourite": "{name} je stavio Vaš status kao omiljeni",
+  "notification.follow": "{name} Vas je zapratio",
+  "notification.mention": "{name} Vas je pomenuo",
+  "notification.reblog": "{name} je podržao(la) Vaš status",
+  "notifications.clear": "Očisti obaveštenja",
+  "notifications.clear_confirmation": "Da li ste sigurno da trajno želite da očistite Vaša obaveštenja?",
+  "notifications.column_settings.alert": "Obaveštenja na radnoj površini",
+  "notifications.column_settings.favourite": "Omiljeni:",
+  "notifications.column_settings.follow": "Novi pratioci:",
+  "notifications.column_settings.mention": "Pominjanja:",
+  "notifications.column_settings.push": "Guraj obaveštenja",
+  "notifications.column_settings.push_meta": "Ovaj uređaj",
+  "notifications.column_settings.reblog": "Podrški:",
+  "notifications.column_settings.show": "Prikaži u koloni",
+  "notifications.column_settings.sound": "Puštaj zvuk",
+  "onboarding.done": "Gotovo",
+  "onboarding.next": "Sledeće",
+  "onboarding.page_five.public_timelines": "Lokalna lajna prikazuje sve javne statuse od svih na domenu {domain}. Združena lajna prikazuje javne statuse od svih ljudi koje prate korisnici sa domena {domain}. Ovo su javne lajne, sjajan način da otkrijete nove ljude.",
+  "onboarding.page_four.home": "Početna lajna prikazuje statuse ljudi koje Vi pratite.",
+  "onboarding.page_four.notifications": "Kolona sa obaveštenjima Vam prikazuje kada neko priča sa Vama.",
+  "onboarding.page_one.federation": "Mastodont je mreža nezavisnih servera koji se uvezuju da naprave jednu veću društvenu mrežu. Ove servere zovemo instancama.",
+  "onboarding.page_one.handle": "Vi ste na domenu {domain}, pa je Vaša puna identifikacija {handle}",
+  "onboarding.page_one.welcome": "Dobrodošli na Mastodont!",
+  "onboarding.page_six.admin": "Administrator Vaše instance je {admin}.",
+  "onboarding.page_six.almost_done": "Još malo, pa gotovo...",
+  "onboarding.page_six.appetoot": "Prijatutno!",
+  "onboarding.page_six.apps_available": "Postoje {apps} dostupne za iOS, Android i druge platforme.",
+  "onboarding.page_six.github": "Mastodont je slobodan softver otvorenog koda. Možete prijavljivati greške, potraživati nove funckionalnosti, ili učestvujući u programiranju. Naš izvorni kod je ovde: {github}.",
+  "onboarding.page_six.guidelines": "smernice zajednice",
+  "onboarding.page_six.read_guidelines": "Pročitejte {guidelines} domena {domain}!",
+  "onboarding.page_six.various_app": "mobilne aplikacije",
+  "onboarding.page_three.profile": "Izmenite profil da promenite avatar, biografiju i ime za prikaz. Tamo ćete naći i ostala podešavanja.",
+  "onboarding.page_three.search": "Korisite pretragu da nađete ljude i gledate heštegove, kao što su {illustration} i {introductions}. Da nađete osobu koja nije na ovoj instanci, koristite njenu punu identifikaciju.",
+  "onboarding.page_two.compose": "Pišite statuse iz prve kolone. Možete otpremati slike, menjati podešavanja privatnosti, i dodavati upozorenja za osetljiv sadržaj preko ikonica ispod.",
+  "onboarding.skip": "Preskoči",
+  "privacy.change": "Podesi status privatnosti",
+  "privacy.direct.long": "Objavi samo korisnicima koji su pomenuti",
+  "privacy.direct.short": "Direktno",
+  "privacy.private.long": "Objavi samo pratiocima",
+  "privacy.private.short": "Samo za pratioce",
+  "privacy.public.long": "Objavi na javnoj lajni",
+  "privacy.public.short": "Javno",
+  "privacy.unlisted.long": "Ne objavljuj na javnim lajnama",
+  "privacy.unlisted.short": "Neizlistano",
+  "relative_time.days": "{number}d",
+  "relative_time.hours": "{number}h",
+  "relative_time.just_now": "sada",
+  "relative_time.minutes": "{number}m",
+  "relative_time.seconds": "{number}s",
+  "reply_indicator.cancel": "Poništi",
+  "report.placeholder": "Dodatni komentari",
+  "report.submit": "Pošalji",
+  "report.target": "Prijavljujem {target}",
+  "search.placeholder": "Pretraga",
+  "search_popout.search_format": "Napredni format pretrage",
+  "search_popout.tips.hashtag": "hešteg",
+  "search_popout.tips.status": "status",
+  "search_popout.tips.text": "Traženjem običnog teksta ćete dobiti sva pronađena imena, sva korisnička imena i sve nađene heštegove",
+  "search_popout.tips.user": "korisnik",
+  "search_results.total": "{count, number} {count, plural, one {rezultat} few {rezultata} other {rezultata}}",
+  "standalone.public_title": "Pogled iznutra...",
+  "status.cannot_reblog": "Ovaj status ne može da se podrži",
+  "status.delete": "Obriši",
+  "status.embed": "Ugradi na sajt",
+  "status.favourite": "Omiljeno",
+  "status.load_more": "Učitaj još",
+  "status.media_hidden": "Multimedija sakrivena",
+  "status.mention": "Pomeni korisnika @{name}",
+  "status.more": "Još",
+  "status.mute_conversation": "Mutiraj prepisku",
+  "status.open": "Proširi ovaj status",
+  "status.pin": "Prikači na profil",
+  "status.reblog": "Podrži",
+  "status.reblogged_by": "{name} podržao(la)",
+  "status.reply": "Odgovori",
+  "status.replyAll": "Odgovori na diskusiju",
+  "status.report": "Prijavi korisnika @{name}",
+  "status.sensitive_toggle": "Kliknite da vidite",
+  "status.sensitive_warning": "Osetljiv sadržaj",
+  "status.share": "Podeli",
+  "status.show_less": "Prikaži manje",
+  "status.show_more": "Prikaži više",
+  "status.unmute_conversation": "Uključi prepisku",
+  "status.unpin": "Otkači sa profila",
+  "tabs_bar.compose": "Napiši",
+  "tabs_bar.federated_timeline": "Združeno",
+  "tabs_bar.home": "Početna",
+  "tabs_bar.local_timeline": "Lokalno",
+  "tabs_bar.notifications": "Obaveštenja",
+  "ui.beforeunload": "Ako napustite Mastodont, izgubićete napisani nacrt.",
+  "upload_area.title": "Prevucite ovde da otpremite",
+  "upload_button.label": "Dodaj multimediju",
+  "upload_form.description": "Opiši za slabovide osobe",
+  "upload_form.undo": "Opozovi",
+  "upload_progress.label": "Otpremam...",
+  "video.close": "Zatvori video",
+  "video.exit_fullscreen": "Napusti ceo ekran",
+  "video.expand": "Proširi video",
+  "video.fullscreen": "Ceo ekran",
+  "video.hide": "Sakrij video",
+  "video.mute": "Ugasi zvuk",
+  "video.pause": "Pauziraj",
+  "video.play": "Pusti",
+  "video.unmute": "Vrati zvuk"
+}
diff --git a/app/javascript/mastodon/locales/sr.json b/app/javascript/mastodon/locales/sr.json
index f56d553b9..c8e4573e6 100644
--- a/app/javascript/mastodon/locales/sr.json
+++ b/app/javascript/mastodon/locales/sr.json
@@ -7,7 +7,7 @@
   "account.followers": "Пратиоца",
   "account.follows": "Прати",
   "account.follows_you": "Прати Вас",
-  "account.hide_reblogs": "Сакриј погуравања од корисника @{name}",
+  "account.hide_reblogs": "Сакриј подршке које даје корисника @{name}",
   "account.media": "Медији",
   "account.mention": "Помени корисника @{name}",
   "account.moved_to": "{name} се померио на:",
@@ -17,7 +17,7 @@
   "account.report": "Пријави @{name}",
   "account.requested": "Чекам одобрење. Кликните да поништите захтев за праћење",
   "account.share": "Подели профил корисника @{name}",
-  "account.show_reblogs": "Прикажи погуравања од корисника @{name}",
+  "account.show_reblogs": "Прикажи подршке од корисника @{name}",
   "account.unblock": "Одблокирај корисника @{name}",
   "account.unblock_domain": "Одблокирај домен {domain}",
   "account.unfollow": "Отпрати",
@@ -104,11 +104,11 @@
   "home.column_settings.advanced": "Напредно",
   "home.column_settings.basic": "Основно",
   "home.column_settings.filter_regex": "Филтрирај регуларним изразима",
-  "home.column_settings.show_reblogs": "Прикажи и погуравања",
+  "home.column_settings.show_reblogs": "Прикажи и подржавања",
   "home.column_settings.show_replies": "Прикажи одговоре",
   "home.settings": "Поставке колоне",
   "keyboard_shortcuts.back": "да одете назад",
-  "keyboard_shortcuts.boost": "да погурате",
+  "keyboard_shortcuts.boost": "да подржите",
   "keyboard_shortcuts.column": "да се пребаците на статус у једној од колона",
   "keyboard_shortcuts.compose": "да се пребаците на писање новог тута",
   "keyboard_shortcuts.description": "Опис",
@@ -155,7 +155,7 @@
   "notification.favourite": "{name} је ставио Ваш статус као омиљени",
   "notification.follow": "{name} Вас је запратио",
   "notification.mention": "{name} Вас је поменуо",
-  "notification.reblog": "{name} је погурао Ваш статус",
+  "notification.reblog": "{name} је подржао(ла) Ваш статус",
   "notifications.clear": "Очисти обавештења",
   "notifications.clear_confirmation": "Да ли сте сигурно да трајно желите да очистите Ваша обавештења?",
   "notifications.column_settings.alert": "Обавештења на радној површини",
@@ -164,7 +164,7 @@
   "notifications.column_settings.mention": "Помињања:",
   "notifications.column_settings.push": "Гурај обавештења",
   "notifications.column_settings.push_meta": "Овај уређај",
-  "notifications.column_settings.reblog": "Погуравања:",
+  "notifications.column_settings.reblog": "Подршки:",
   "notifications.column_settings.show": "Прикажи у колони",
   "notifications.column_settings.sound": "Пуштај звук",
   "onboarding.done": "Готово",
@@ -213,7 +213,7 @@
   "search_popout.tips.user": "корисник",
   "search_results.total": "{count, number} {count, plural, one {резултат} few {резултата} other {резултата}}",
   "standalone.public_title": "Поглед изнутра...",
-  "status.cannot_reblog": "Овај статус не може да се погура",
+  "status.cannot_reblog": "Овај статус не може да се подржи",
   "status.delete": "Обриши",
   "status.embed": "Угради на сајт",
   "status.favourite": "Омиљено",
@@ -224,8 +224,8 @@
   "status.mute_conversation": "Мутирај преписку",
   "status.open": "Прошири овај статус",
   "status.pin": "Прикачи на профил",
-  "status.reblog": "Погурај",
-  "status.reblogged_by": "{name} погурао(ла)",
+  "status.reblog": "Подржи",
+  "status.reblogged_by": "{name} подржао(ла)",
   "status.reply": "Одговори",
   "status.replyAll": "Одговори на дискусију",
   "status.report": "Пријави корисника @{name}",
diff --git a/app/javascript/mastodon/reducers/push_notifications.js b/app/javascript/mastodon/reducers/push_notifications.js
index c15b38fe4..85628c6b1 100644
--- a/app/javascript/mastodon/reducers/push_notifications.js
+++ b/app/javascript/mastodon/reducers/push_notifications.js
@@ -44,7 +44,7 @@ export default function push_subscriptions(state = initialState, action) {
   case CLEAR_SUBSCRIPTION:
     return initialState;
   case SET_ALERTS:
-    return state.setIn(action.key, action.value);
+    return state.setIn(action.path, action.value);
   default:
     return state;
   }
diff --git a/app/javascript/mastodon/reducers/settings.js b/app/javascript/mastodon/reducers/settings.js
index 5817cf49b..390b2a13a 100644
--- a/app/javascript/mastodon/reducers/settings.js
+++ b/app/javascript/mastodon/reducers/settings.js
@@ -93,7 +93,7 @@ export default function settings(state = initialState, action) {
     return hydrate(state, action.state.get('settings'));
   case SETTING_CHANGE:
     return state
-      .setIn(action.key, action.value)
+      .setIn(action.path, action.value)
       .set('saved', false);
   case COLUMN_ADD:
     return state
diff --git a/app/javascript/styles/mastodon/components.scss b/app/javascript/styles/mastodon/components.scss
index a03165690..a09a766d0 100644
--- a/app/javascript/styles/mastodon/components.scss
+++ b/app/javascript/styles/mastodon/components.scss
@@ -2072,6 +2072,11 @@
   cursor: default;
 }
 
+.getting-started__wrapper,
+.getting_started {
+  background: $ui-base-color;
+}
+
 .getting-started__wrapper {
   position: relative;
   overflow-y: auto;
diff --git a/app/lib/activity_tracker.rb b/app/lib/activity_tracker.rb
index 50e927b0c..5b4972674 100644
--- a/app/lib/activity_tracker.rb
+++ b/app/lib/activity_tracker.rb
@@ -15,7 +15,7 @@ class ActivityTracker
       key = [prefix, current_week].join(':')
 
       redis.pfadd(key, value)
-      redis.expire(key, value)
+      redis.expire(key, EXPIRE_AFTER)
     end
 
     private
diff --git a/app/lib/activitypub/activity/delete.rb b/app/lib/activitypub/activity/delete.rb
index d0fb49342..5fa60a81c 100644
--- a/app/lib/activitypub/activity/delete.rb
+++ b/app/lib/activitypub/activity/delete.rb
@@ -13,6 +13,7 @@ class ActivityPub::Activity::Delete < ActivityPub::Activity
 
   def delete_person
     SuspendAccountService.new.call(@account)
+    @account.destroy!
   end
 
   def delete_note
diff --git a/app/lib/sanitize_config.rb b/app/lib/sanitize_config.rb
index f09288fcd..c2b466924 100644
--- a/app/lib/sanitize_config.rb
+++ b/app/lib/sanitize_config.rb
@@ -6,14 +6,14 @@ class Sanitize
 
     CLASS_WHITELIST_TRANSFORMER = lambda do |env|
       node = env[:node]
-      class_list = node['class']&.split(' ')
+      class_list = node['class']&.split(/[\t\n\f\r ]/)
 
       return unless class_list
 
       class_list.keep_if do |e|
-        return true if e =~ /^(h|p|u|dt|e)-/ # microformats classes
-        return true if e =~ /^(mention|hashtag)$/ # semantic classes
-        return true if e =~ /^(ellipsis|invisible)$/ # link formatting classes
+        next true if e =~ /^(h|p|u|dt|e)-/ # microformats classes
+        next true if e =~ /^(mention|hashtag)$/ # semantic classes
+        next true if e =~ /^(ellipsis|invisible)$/ # link formatting classes
       end
 
       node['class'] = class_list.join(' ')
diff --git a/app/mailers/user_mailer.rb b/app/mailers/user_mailer.rb
index 5a062dc25..7821be32b 100644
--- a/app/mailers/user_mailer.rb
+++ b/app/mailers/user_mailer.rb
@@ -13,7 +13,9 @@ class UserMailer < Devise::Mailer
     return if @resource.disabled?
 
     I18n.with_locale(@resource.locale || I18n.default_locale) do
-      mail to: @resource.unconfirmed_email.blank? ? @resource.email : @resource.unconfirmed_email, subject: I18n.t('devise.mailer.confirmation_instructions.subject', instance: @instance)
+      mail to: @resource.unconfirmed_email.blank? ? @resource.email : @resource.unconfirmed_email,
+           subject: I18n.t(@resource.pending_reconfirmation? ? 'devise.mailer.reconfirmation_instructions.subject' : 'devise.mailer.confirmation_instructions.subject', instance: @instance),
+           template_name: @resource.pending_reconfirmation? ? 'reconfirmation_instructions' : 'confirmation_instructions'
     end
   end
 
@@ -39,4 +41,15 @@ class UserMailer < Devise::Mailer
       mail to: @resource.email, subject: I18n.t('devise.mailer.password_change.subject')
     end
   end
+
+  def email_changed(user, **)
+    @resource = user
+    @instance = Rails.configuration.x.local_domain
+
+    return if @resource.disabled?
+
+    I18n.with_locale(@resource.locale || I18n.default_locale) do
+      mail to: @resource.email, subject: I18n.t('devise.mailer.email_changed.subject')
+    end
+  end
 end
diff --git a/app/models/user.rb b/app/models/user.rb
index fed9c4977..231271f73 100644
--- a/app/models/user.rb
+++ b/app/models/user.rb
@@ -41,12 +41,15 @@ class User < ApplicationRecord
 
   ACTIVE_DURATION = 14.days
 
-  devise :registerable, :recoverable,
-         :rememberable, :trackable, :validatable, :confirmable,
-         :two_factor_authenticatable, :two_factor_backupable,
-         otp_secret_encryption_key: ENV['OTP_SECRET'],
+  devise :two_factor_authenticatable,
+         otp_secret_encryption_key: ENV['OTP_SECRET']
+
+  devise :two_factor_backupable,
          otp_number_of_backup_codes: 10
 
+  devise :registerable, :recoverable, :rememberable, :trackable, :validatable,
+         :confirmable
+
   belongs_to :account, inverse_of: :user, required: true
   belongs_to :invite, counter_cache: :uses
   accepts_nested_attributes_for :account
diff --git a/app/services/activitypub/process_account_service.rb b/app/services/activitypub/process_account_service.rb
index 06ca75563..0fbf18c00 100644
--- a/app/services/activitypub/process_account_service.rb
+++ b/app/services/activitypub/process_account_service.rb
@@ -74,7 +74,7 @@ class ActivityPub::ProcessAccountService < BaseService
     @account.statuses_count    = outbox_total_items    if outbox_total_items.present?
     @account.following_count   = following_total_items if following_total_items.present?
     @account.followers_count   = followers_total_items if followers_total_items.present?
-    @account.moved_to_account  = moved_account         if @json['movedTo'].present?
+    @account.moved_to_account  = @json['movedTo'].present? ? moved_account : nil
   end
 
   def after_protocol_change!
diff --git a/app/views/layouts/application.html.haml b/app/views/layouts/application.html.haml
index 5b9e652cb..322d7403e 100755
--- a/app/views/layouts/application.html.haml
+++ b/app/views/layouts/application.html.haml
@@ -2,8 +2,7 @@
 %html{ lang: I18n.locale }
   %head
     %meta{ charset: 'utf-8' }/
-    %meta{ name: 'viewport', content: 'width=device-width, initial-scale=1' }/
-    %meta{ 'http-equiv' => 'X-UA-Compatible', content: 'IE=edge' }/
+    %meta{ name: 'viewport', content: 'width=device-width, initial-scale=1' }/   
     %link{ rel: 'icon', href: favicon_path, type: 'image/x-icon' }/
     %link{ rel: 'apple-touch-icon', sizes: '180x180', href: '/apple-touch-icon.png' }/
     %link{ rel: 'mask-icon', href: '/mask-icon.svg', color: '#2B90D9' }/
diff --git a/app/views/user_mailer/confirmation_instructions.sr-Latn.html.erb b/app/views/user_mailer/confirmation_instructions.sr-Latn.html.erb
new file mode 100644
index 000000000..a16008250
--- /dev/null
+++ b/app/views/user_mailer/confirmation_instructions.sr-Latn.html.erb
@@ -0,0 +1,15 @@
+<p>Dobrodošao <%= @resource.email %> !</p>
+
+<p>Upravo ste napravili nalog na instanci <%= @instance %>.</p>
+
+<p>Da potvrdite Vašu registraciju, molimo Vas kliknite na sledeći link: <br>
+<%= link_to 'Potvrdi moj nalog', confirmation_url(@resource, confirmation_token: @token) %></p>
+
+<p>Ako link iznad ne radi, kopirajte i nalepite ovu adresu u adresnu traku: <br>
+<span><%= confirmation_url(@resource, confirmation_token: @token) %></span>
+
+<p>Takođe pogledajte i <%= link_to 'pravila i uslove korišćenja', terms_url %>.</p>
+
+<p>S poštovanjem,<p>
+
+<p><%= @instance %> tim</p>
diff --git a/app/views/user_mailer/confirmation_instructions.sr-Latn.text.erb b/app/views/user_mailer/confirmation_instructions.sr-Latn.text.erb
new file mode 100644
index 000000000..60fe9db0d
--- /dev/null
+++ b/app/views/user_mailer/confirmation_instructions.sr-Latn.text.erb
@@ -0,0 +1,12 @@
+Dobrodošao <%= @resource.email %> !
+
+Upravo ste napravili nalog na instanci <%= @instance %>.
+
+Da potvrdite Vašu registraciju, molimo Vas kliknite na sledeći link:
+<%= confirmation_url(@resource, confirmation_token: @token) %>
+
+Takođe pogledajte i pravila i uslove korišćenja <%= terms_url %>
+
+S poštovanjem,
+
+<%= @instance %> tim
diff --git a/app/views/user_mailer/email_changed.en.html.erb b/app/views/user_mailer/email_changed.en.html.erb
new file mode 100644
index 000000000..c10680086
--- /dev/null
+++ b/app/views/user_mailer/email_changed.en.html.erb
@@ -0,0 +1,15 @@
+<p>Hello <%= @resource.email %>!</p>
+
+<% if @resource&.unconfirmed_email? %>
+  <p>We're contacting you to notify you that the email you use on <%= @instance %> is being changed to <%= @resource.unconfirmed_email %>.</p>
+<% else %>
+  <p>We're contacting you to notify you that the email you use on <%= @instance %> has been changed to <%= @resource.email %>.</p>
+<% end %>
+
+<p>
+  If you did not change your email, it is likely that someone has gained access to your account. Please change your password immediately or contact the instance admin if you're locked out of your account.
+</p>
+
+<p>Sincerely,<p>
+
+<p>The <%= @instance %> team</p>
diff --git a/app/views/user_mailer/email_changed.en.text.erb b/app/views/user_mailer/email_changed.en.text.erb
new file mode 100644
index 000000000..971972461
--- /dev/null
+++ b/app/views/user_mailer/email_changed.en.text.erb
@@ -0,0 +1,13 @@
+Hello <%= @resource.email %>!
+
+<% if @resource&.unconfirmed_email? %>
+We're contacting you to notify you that the email you use on <%= @instance %> is being changed to <%= @resource.unconfirmed_email %>.
+<% else %>
+We're contacting you to notify you that the email you use on <%= @instance %> has been changed to <%= @resource.email %>.
+<% end %>
+
+If you did not change your email, it is likely that someone has gained access to your account. Please change your password immediately or contact the instance admin if you're locked out of your account.
+
+Sincerely,
+
+The <%= @instance %> team
diff --git a/app/views/user_mailer/password_change.sr-Latn.html.erb b/app/views/user_mailer/password_change.sr-Latn.html.erb
new file mode 100644
index 000000000..ab4e23bdf
--- /dev/null
+++ b/app/views/user_mailer/password_change.sr-Latn.html.erb
@@ -0,0 +1,3 @@
+<p>Zdravo <%= @resource.email %>!</p>
+
+<p>Želimo samo da Vas obavestimo da je Vaša lozinka na Mastodont instanci <%= @instance %> promenjena.</p>
diff --git a/app/views/user_mailer/password_change.sr-Latn.text.erb b/app/views/user_mailer/password_change.sr-Latn.text.erb
new file mode 100644
index 000000000..6e0666d8d
--- /dev/null
+++ b/app/views/user_mailer/password_change.sr-Latn.text.erb
@@ -0,0 +1,3 @@
+Zdravo <%= @resource.email %>!
+
+Želimo samo da Vas obavestimo da je Vaša lozinka na Mastodont instanci <%= @instance %> promenjena.
diff --git a/app/views/user_mailer/reconfirmation_instructions.en.html.erb b/app/views/user_mailer/reconfirmation_instructions.en.html.erb
new file mode 100644
index 000000000..31866a3c8
--- /dev/null
+++ b/app/views/user_mailer/reconfirmation_instructions.en.html.erb
@@ -0,0 +1,15 @@
+<p>Hello <%= @resource.unconfirmed_email %>!</p>
+
+<p>You requested a change to the email address you use on <%= @instance %>.</p>
+
+<p>To confirm your new email, please click on the following link:<br>
+<%= link_to 'Confirm my email address', confirmation_url(@resource, confirmation_token: @token) %></p>
+
+<p>If the above link did not work, copy and paste this URL into your address bar: <br>
+<span><%= confirmation_url(@resource, confirmation_token: @token) %></span>
+
+<p>Please also check out our <%= link_to 'terms and conditions', terms_url %>.</p>
+
+<p>Sincerely,<p>
+
+<p>The <%= @instance %> team</p>
diff --git a/app/views/user_mailer/reconfirmation_instructions.en.text.erb b/app/views/user_mailer/reconfirmation_instructions.en.text.erb
new file mode 100644
index 000000000..c1c735b3a
--- /dev/null
+++ b/app/views/user_mailer/reconfirmation_instructions.en.text.erb
@@ -0,0 +1,12 @@
+Hello <%= @resource.unconfirmed_email %>!
+
+You requested a change to the email address you use on <%= @instance %>.
+
+To confirm your new email, please click on the following link:
+<%= confirmation_url(@resource, confirmation_token: @token) %>
+
+Please also check out our terms and conditions <%= terms_url %>
+
+Sincerely,
+
+The <%= @instance %> team
diff --git a/app/views/user_mailer/reset_password_instructions.sr-Latn.html.erb b/app/views/user_mailer/reset_password_instructions.sr-Latn.html.erb
new file mode 100644
index 000000000..7dede16b2
--- /dev/null
+++ b/app/views/user_mailer/reset_password_instructions.sr-Latn.html.erb
@@ -0,0 +1,8 @@
+<p>Zdravo <%= @resource.email %>!</p>
+
+<p>Neko je zatražio link za promenu lozinke na instanci <%= @instance %>. Ovo možete uraditi klikom na link ispod.</p>
+
+<p><%= link_to 'Promeni moju lozinku', edit_password_url(@resource, reset_password_token: @token) %></p>
+
+<p>Ignorišite ovu poruku, ako niste Vi bili ti koji ste zatražili promenu lozinke.</p>
+<p>Lozinka se neće promeniti sve dok ne kliknete link iznad i ne napravite novu lozinku.</p>
diff --git a/app/views/user_mailer/reset_password_instructions.sr-Latn.text.erb b/app/views/user_mailer/reset_password_instructions.sr-Latn.text.erb
new file mode 100644
index 000000000..31707dee1
--- /dev/null
+++ b/app/views/user_mailer/reset_password_instructions.sr-Latn.text.erb
@@ -0,0 +1,8 @@
+Zdravo <%= @resource.email %>!
+
+Neko je zatražio link za promenu lozinke na instanci <%= @instance %>. Ovo možete uraditi preko linka ispod.
+
+<%= edit_password_url(@resource, reset_password_token: @token) %>
+
+Ignorišite ovu poruku, ako niste Vi bili ti koji ste zatražili promenu lozinke.
+Lozinka se neće promeniti sve dok ne kliknete link iznad i ne napravite novu lozinku.
diff --git a/config/application.rb b/config/application.rb
index 89be2705a..c1bf3cef2 100644
--- a/config/application.rb
+++ b/config/application.rb
@@ -58,6 +58,7 @@ module Mastodon
       :ru,
       :sk,
       :sr,
+      :'sr-Latn',
       :sv,
       :th,
       :tr,
diff --git a/config/initializers/devise.rb b/config/initializers/devise.rb
index 64c4e12ff..07912c28b 100644
--- a/config/initializers/devise.rb
+++ b/config/initializers/devise.rb
@@ -137,6 +137,9 @@ Devise.setup do |config|
   # Setup a pepper to generate the encrypted password.
   # config.pepper = '104d16705f794923e77c5e5167b52452d00646dc952a2d30b541c24086e647012c7b9625f253c51912e455981e503446772973d5f1638631196c819d7137fad4'
 
+  # Send a notification to the original email when the user's email is changed.
+  config.send_email_changed_notification = true
+
   # Send a notification email when the user's password is changed
   config.send_password_change_notification = true
 
@@ -160,7 +163,7 @@ Devise.setup do |config|
   # initial account confirmation) to be applied. Requires additional unconfirmed_email
   # db field (see migrations). Until confirmed, new email is stored in
   # unconfirmed_email column, and copied to email column on successful confirmation.
-  config.reconfirmable = false
+  config.reconfirmable = true
 
   # Defines which key will be used when confirming an account
   # config.confirmation_keys = [:email]
diff --git a/config/locales/activerecord.sr-Latn.yml b/config/locales/activerecord.sr-Latn.yml
new file mode 100644
index 000000000..1527a0d8c
--- /dev/null
+++ b/config/locales/activerecord.sr-Latn.yml
@@ -0,0 +1,13 @@
+---
+sr-Latn:
+  activerecord:
+    errors:
+      models:
+        account:
+          attributes:
+            username:
+              invalid: samo slova, brojevi i donje crte
+        status:
+          attributes:
+            reblog:
+              taken: statusa već postoji
diff --git a/config/locales/devise.en.yml b/config/locales/devise.en.yml
index 586c5349d..c5ae583ff 100644
--- a/config/locales/devise.en.yml
+++ b/config/locales/devise.en.yml
@@ -18,8 +18,12 @@ en:
     mailer:
       confirmation_instructions:
         subject: 'Mastodon: Confirmation instructions for %{instance}'
+      email_changed:
+        subject: 'Mastodon: Email changed'
       password_change:
         subject: 'Mastodon: Password changed'
+      reconfirmation_instructions:
+        subject: 'Mastodon: Confirm email for %{instance}'
       reset_password_instructions:
         subject: 'Mastodon: Reset password instructions'
       unlock_instructions:
diff --git a/config/locales/devise.sr-Latn.yml b/config/locales/devise.sr-Latn.yml
new file mode 100644
index 000000000..21ddbd726
--- /dev/null
+++ b/config/locales/devise.sr-Latn.yml
@@ -0,0 +1,63 @@
+---
+sr-Latn:
+  devise:
+    confirmations:
+      confirmed: Adresa Vaše e-pošte je uspešno potvrđena.
+      send_instructions: U roku od nekoliko minuta primićete e-poštu sa uputstvom za potvrdu Vašeg naloga. Molimo proverite i spam fasciklu ako niste primili poruku.
+      send_paranoid_instructions: Ukoliko se adresa Vaše e-pošte nalazi u našoj bazi, u roku od nekoliko minuta primićete poruku sa uputstvom kako da potvrdite Vaš nalog. Molimo proverite i spam fasciklu ako niste primili poruku.
+    failure:
+      already_authenticated: Već ste prijavljeni.
+      inactive: Vaš nalog još nije aktiviran.
+      invalid: Neispravan %{authentication_keys} ili lozinka.
+      last_attempt: Imate još jedan pokušaj pre nego što Vaš nalog bude zaključan.
+      locked: Vaš nalog je zaključan.
+      not_found_in_database: Neispravan %{authentication_keys} ili lozinka.
+      timeout: Vreme trajanja Vaše sesije je isteklo. Za nastavak prijavite se ponovo.
+      unauthenticated: Za nastavak se morate prijaviti ili registrovati.
+      unconfirmed: Pre nastavka morate potvrditi svoj nalog.
+    mailer:
+      confirmation_instructions:
+        subject: 'Mastodont: Uputstvo za potvrdu korisničkog naloga na instanci %{instance}'
+      password_change:
+        subject: 'Mastodont: Lozinka promenjena'
+      reset_password_instructions:
+        subject: 'Mastodont: Uputstvo za resetovanje lozinke'
+      unlock_instructions:
+        subject: 'Mastodont: Uputstvo za otključavanje korisničkog naloga'
+    omniauth_callbacks:
+      failure: Nismo u mogućnosti autorizovati Vas sa %{kind} nalogom zbog "%{reason}".
+      success: Uspešna autorizacija sa %{kind} naloga.
+    passwords:
+      no_token: Ne možete pristupiti ovoj stranici ako niste pratili vezu u imejlu za resetovanje lozinke. Ukoliko ste pratili vezu za resetovanje lozinke u poruci, molimo Vas da proverite da li ste koristili punu adresu.
+      send_instructions: U roku od nekoliko minuta primitićete poruku sa uputstvom za promenu Vaše lozinke. Molimo proverite i spam fasciklu ako niste primili poruku.
+      send_paranoid_instructions: Ukoliko se adresa Vaše e-pošte nalazi u našoj bazi, u roku od nekoliko minuta primićete poruku sa uputstvom za promenu Vaše lozinke. Molimo proverite i spam fasciklu ako niste primili poruku.
+      updated: Vaša lozinka je uspešno promenjena. Sada ste prijavljeni.
+      updated_not_active: Vaša lozinka nije uspešno promenjena.
+    registrations:
+      destroyed: Ćao! Vaš nalog je uspešno obrisan. Nadamo se da ćete se uskoro vratiti.
+      signed_up: Dobrodošli! Uspešno ste se registrovali.
+      signed_up_but_inactive: Uspešno ste se registrovali. Nažalost ne možete se prijaviti zato što Vaš nalog još nije aktiviran.
+      signed_up_but_locked: Uspešno ste se registrovali. Nažalost ne možete se prijaviti zato što je Vaš nalog zaključan.
+      signed_up_but_unconfirmed: Poruka za potvrdu Vašeg naloga je poslata na Vašu imejl adresu. Kliknite na vezu u imejlu da potvrdite svoj nalog. Molimo proverite i spam fasciklu ako niste primili poruku.
+      update_needs_confirmation: Uspešno ste ažurirali svoj nalog, ali treba da potvrdimo novu adresu Vaše e-pošte. Molimo Vas da proverite e-poštu i pratite link za potvrdu nove adrese Vaše e-pošte.
+      updated: Vaš nalog je uspešno ažuriran.
+    sessions:
+      already_signed_out: Uspešno ste se odjavili.
+      signed_in: Uspešno ste se prijavili.
+      signed_out: Uspešno ste se odjavili.
+    unlocks:
+      send_instructions: U roku od nekoliko minuta primićete imejl sa uputstvom za otključavanje Vašeg naloga. Molimo proverite i spam fasciklu ako niste primili poruku.
+      send_paranoid_instructions: koliko se adresa Vaše e-pošte nalazi u našoj bazi, u roku od nekoliko minuta primićete poruku sa uputstvom kako da otključate Vaš nalog. Molimo proverite i spam fasciklu ako niste primili poruku.
+      unlocked: Vaš nalog je uspešno otključan. Molimo Vas da se prijavite da biste nastavili.
+  errors:
+    messages:
+      already_confirmed: je već potvrđen, molimo Vas da se prijavite
+      confirmation_period_expired: je trebao biti potvrđen tokom perioda %{period}, molimo Vas da zatražite novi
+      expired: je istekao, molimo Vas da zatražite novi
+      not_found: nije pronađeno
+      not_locked: nije zaključan
+      not_saved:
+        few: "%{count} greške sprečavaju %{resource}a:"
+        many: "%{count} grešaka sprečavaju %{resource}a:"
+        one: '1 greška sprečava %{resource}a:'
+        other: "%{count} grešaka sprečavaju %{resource}a:"
diff --git a/config/locales/doorkeeper.sr-Latn.yml b/config/locales/doorkeeper.sr-Latn.yml
new file mode 100644
index 000000000..8e96f8b93
--- /dev/null
+++ b/config/locales/doorkeeper.sr-Latn.yml
@@ -0,0 +1,119 @@
+---
+sr-Latn:
+  activerecord:
+    attributes:
+      doorkeeper/application:
+        name: Ime aplikacije
+        redirect_uri: Adresa za preusmeravanje
+        scopes: Opseg važenja
+        website: Veb sajt aplikacije
+    errors:
+      models:
+        doorkeeper/application:
+          attributes:
+            redirect_uri:
+              fragment_present: ne može da sadrži fragment.
+              invalid_uri: mora biti ispravan URI.
+              relative_uri: mora biti apsolutni URI.
+              secured_uri: mora biti HTTPS/SSL URI.
+  doorkeeper:
+    applications:
+      buttons:
+        authorize: Autorizuj
+        cancel: Poništi
+        destroy: Uništi
+        edit: Izmeni
+        submit: Pošalji
+      confirmations:
+        destroy: Da li ste sigurni?
+      edit:
+        title: Izmeni aplikaciju
+      form:
+        error: Ops! Proverite formular za eventualne greške
+      help:
+        native_redirect_uri: Koristite %{native_redirect_uri} za lokalno testiranje
+        redirect_uri: Koristite jednu liniju po URI-ju
+        scopes: Odvojite opsege važenja sa belinama. Ostavite prazno za podrazumevane opsege važenja.
+      index:
+        application: Aplikacija
+        callback_url: Adresa za povratni poziv
+        delete: Obriši
+        name: Ime
+        new: Nova aplikacija
+        scopes: Opsezi važenja
+        show: Prikaži
+        title: Vaše aplikacije
+      new:
+        title: Nova aplikacija
+      show:
+        actions: Akcije
+        application_id: Klijentski ključ
+        callback_urls: Adrese za povratne pozive
+        scopes: Opseg važenja
+        secret: Klijentska tajna
+        title: 'Aplikacija: %{name}'
+    authorizations:
+      buttons:
+        authorize: Autorizuj se
+        deny: Odbij
+      error:
+        title: Dogodila se greška
+      new:
+        able_to: Biće u mogućnosti da
+        prompt: Aplikacija %{client_name} zahteva pristup Vašem nalogu
+        title: Potrebna autorizacija
+      show:
+        title: Kopirajte ovaj autorizacioni kod i nalepite ga u aplikaciju.
+    authorized_applications:
+      buttons:
+        revoke: Opozovi
+      confirmations:
+        revoke: Da li ste sigurni?
+      index:
+        application: Aplikacija
+        created_at: Autorizovana
+        date_format: "%d.%m.%Y %H:%M:%S"
+        scopes: Opsezi važenja
+        title: Vaše autorizovane aplikacije
+    errors:
+      messages:
+        access_denied: Vlasnik resursa ili autorizacioni server su odbili zahtev.
+        credential_flow_not_configured: Tok Resource Owner Password Credentials nije uspeo pošto je Doorkeeper.configure.resource_owner_from_credentials neiskonfigurisan.
+        invalid_client: Klijentska identifikacija nije uspela zbog nepoznatog klijenta, zato što klijent nije uključio identifikaciju ili zato što je iskorišćen nepodržani identifikacioni metod.
+        invalid_grant: Zadata identifikaciona dozvola je neispravna, istekla, opozvana, ne poklapa se sa adresom preusmeravanja ili je izdata nekog drugom klijentu.
+        invalid_redirect_uri: Uključena adresa preusmeravanja nije ispravna.
+        invalid_request: Obavezni parametar fali u zahtevu, zahtev uključuje nepodržanu vrednost parametra ili je parametar na neki drugi način pogrešan.
+        invalid_resource_owner: Zadati kredencijali vlasnika resursa nisu ispravni ili vlasnik resursa ne može biti nađen
+        invalid_scope: Zahtevani opseg važenja nije ispravan, nepoznat je ili je na neki drugi način pogrešan.
+        invalid_token:
+          expired: Pristupni token je istekao
+          revoked: Pristupni token je opozvan
+          unknown: Pristupni token nije ispravan
+        resource_owner_authenticator_not_configured: Greška u pronalaženju vlasnika resursa pošto Doorkeeper.configure.resource_owner_authenticator nije konfigurisan.
+        server_error: Identifikacioni server je naišao na neočekivanu situaciju zbog koje nije ispunio upućeni zahtev.
+        temporarily_unavailable: Identifikacioni server trenutno ne može da obradi zahtev jer je privremeno preopterećen ili je u režimu održavanja.
+        unauthorized_client: Klijent nije ovlašćen da izvrši ovaj zahtev ovim metodom.
+        unsupported_grant_type: Tip autorizacione dozvole nije podržan od strane autorizacionog servera.
+        unsupported_response_type: Autorizacioni server ne podržava ovaj tip odgovora.
+    flash:
+      applications:
+        create:
+          notice: Aplikacija napravljena.
+        destroy:
+          notice: Aplikacija obrisana.
+        update:
+          notice: Aplikacija ažurirana.
+      authorized_applications:
+        destroy:
+          notice: Aplikacija opozvana.
+    layouts:
+      admin:
+        nav:
+          applications: Aplikacije
+          oauth2_provider: OAuth2 provajder
+      application:
+        title: OAuth autorizacija potrebna
+    scopes:
+      follow: prati, blokira, odblokira i otprati naloge
+      read: čita podatke Vašeg naloga
+      write: objavljuje statuse u Vaše ime
diff --git a/config/locales/simple_form.sr-Latn.yml b/config/locales/simple_form.sr-Latn.yml
new file mode 100644
index 000000000..d811377c3
--- /dev/null
+++ b/config/locales/simple_form.sr-Latn.yml
@@ -0,0 +1,75 @@
+---
+sr-Latn:
+  simple_form:
+    hints:
+      defaults:
+        avatar: PNG, GIF ili JPG. Najviše 2MB. Biće smanjena na 120x120px
+        digest: Poslato posle dužeg perioda neaktivnosti sa pregledom svih bitnih stvari koje ste dobili dok ste bili odsutni
+        display_name:
+          few: <span class="name-counter">%{count}</span> karaktera preostala
+          many: <span class="name-counter">%{count}</span> karaktera preostalo
+          one: <span class="name-counter">1</span> karakter preostao
+          other: <span class="name-counter">%{count}</span> karaktera preostalo
+        header: PNG, GIF ili JPG. Najviše 2MB. Biće smanjena na 700x335px
+        locked: Zahteva da pojedinačno odobrite pratioce
+        note:
+          few: <span class="note-counter">%{count}</span> karaktera preostal
+          many: <span class="note-counter">%{count}</span> karaktera preostalo
+          one: <span class="note-counter">1</span> karakter preostao
+          other: <span class="note-counter">%{count}</span> karaktera preostalo
+        setting_noindex: Utiče na Vaš javni profil i statusne strane
+        setting_theme: Utiče kako će Mastodont izgledati kada ste prijavljeni sa bilo kog uređaja.
+      imports:
+        data: CSV fajl izvezen sa druge Mastodont instance
+      sessions:
+        otp: Unesite dvofaktorski kod sa Vašeg telefona ili koristite jedan od kodova za oporavak.
+      user:
+        filtered_languages: Označeni jezici će za Vas biti isfiltrirani sa javnih lajni
+    labels:
+      defaults:
+        avatar: Avatar
+        confirm_new_password: Potvrdite novu lozinku
+        confirm_password: Potvrdite lozinku
+        current_password: Trenutna lozinka
+        data: Podaci
+        display_name: Ime za prikaz
+        email: Adresa e-pošte
+        expires_in: Ističe nakon
+        filtered_languages: Filtrirani jezici
+        header: Zaglavlje
+        locale: Jezik
+        locked: Zaključaj nalog
+        max_uses: Maksimalni broj korišćenja
+        new_password: Nova lozinka
+        note: Biografija
+        otp_attempt: Dvofaktorski kod
+        password: Lozinka
+        setting_auto_play_gif: Automatski puštaj animirane GIF-ove
+        setting_boost_modal: Prikaži dijalog za potvrdu pre davanja podrške
+        setting_default_privacy: Privatnost objava
+        setting_default_sensitive: Uvek označi multimediju kao osetljivu
+        setting_delete_modal: Prikaži dijalog za potvrdu pre brisanja tuta
+        setting_noindex: Odjavi se od indeksiranja search engine-a
+        setting_reduce_motion: Smanji pokrete u animacijama
+        setting_system_font_ui: Koristi sistemski font
+        setting_theme: Tema sajta
+        setting_unfollow_modal: Prikaži dijalog za potvrdu pre nego što otpratite nekoga
+        severity: Oštrina
+        type: Tip uvoza
+        username: Korisničko ime
+      interactions:
+        must_be_follower: Blokiraj obaveštenja od korisnika koji me ne prate
+        must_be_following: Blokiraj obaveštenja od ljudi koje ne pratim
+        must_be_following_dm: Blokiraj direktne poruke od ljudi koje ne pratim
+      notification_emails:
+        digest: Šalji e-poštu sa sažetkom
+        favourite: Šalji e-poštu kada neko stavi da mu je Vaš status omiljen
+        follow: Šalji e-poštu kada Vas neko zaprati
+        follow_request: Šalji e-poštu kada neko zatraži da Vas zaprati
+        mention: Šalji e-poštu kada Vas neko pomene
+        reblog: Šalji e-poštu kada neko podrži Vaš status
+    'no': Ne
+    required:
+      mark: "*"
+      text: obavezno
+    'yes': Da
diff --git a/config/locales/simple_form.sr.yml b/config/locales/simple_form.sr.yml
index 41dada77b..4e3599e5f 100644
--- a/config/locales/simple_form.sr.yml
+++ b/config/locales/simple_form.sr.yml
@@ -45,7 +45,7 @@ sr:
         otp_attempt: Двофакторски код
         password: Лозинка
         setting_auto_play_gif: Аутоматски пуштај анимиране GIF-ове
-        setting_boost_modal: Прикажи дијалог за потврду пре погуравања
+        setting_boost_modal: Прикажи дијалог за потврду пре давања подршке
         setting_default_privacy: Приватност објава
         setting_default_sensitive: Увек означи мултимедију као осетљиву
         setting_delete_modal: Прикажи дијалог за потврду пре брисања тута
@@ -67,7 +67,7 @@ sr:
         follow: Шаљи е-пошту када Вас неко запрати
         follow_request: Шаљи е-пошту када неко затражи да Вас запрати
         mention: Шаљи е-пошту када Вас неко помене
-        reblog: Шаљи е-пошту када неко погура Ваш статус
+        reblog: Шаљи е-пошту када неко подржи Ваш статус
     'no': Не
     required:
       mark: "*"
diff --git a/config/locales/sr-Latn.yml b/config/locales/sr-Latn.yml
new file mode 100644
index 000000000..45fb1c1ba
--- /dev/null
+++ b/config/locales/sr-Latn.yml
@@ -0,0 +1,723 @@
+---
+sr-Latn:
+  about:
+    about_hashtag_html: Ovo su javni statusi tagovani sa <strong>#%{hashtag}</strong>. Možete odgovarati na njih ako imate nalog bilo gde u fediversu.
+    about_mastodon_html: Mastodont je društvena mreža bazirana na otvorenim protokolima i slobodnom softveru otvorenog koda. Decentralizovana je kao što je decentralizovana e-pošta.
+    about_this: O instanci
+    closed_registrations: Registracije su trenutno zatvorene na ovoj instanci. Ipak! Možete naći drugu instancu na kojoj ćete napraviti nalog i odatle dobiti pristup istoj ovoj mreži.
+    contact: Kontakt
+    contact_missing: Nije postavljeno
+    contact_unavailable: N/A
+    description_headline: Šta je %{domain}?
+    domain_count_after: ostale instance
+    domain_count_before: Povezan na
+    extended_description_html: |
+      <h3>Dobro mesto za pravila</h3>
+      <p>Prošireni opis koji još nije postavljen.</p>
+    features:
+      humane_approach_body: Učeći od grešaka sa ostalih mreža, a da bi se borio protiv zloupotreba na društvenim mrežama, Mastodont pokušava da pravi što etičkije odluke prilikom razvoja.
+      humane_approach_title: Humaniji pristup
+      not_a_product_body: Mastodont nije komercijalna mreža. Nema reklama, nema skupljanja privatnih podataka, nema zaštićenih delova. Nema centralnog autoriteta.
+      not_a_product_title: Vi ste osoba, ne proizvod
+      real_conversation_body: Sa 500 karaktera na raspolaganju i podrškom za granularniji sadržaj i upozorenja na osetljiviji sadržaj, možete se izraziti kako god želite.
+      real_conversation_title: Pravljen za pravi razgovor
+      within_reach_body: Više aplikacija za iOS, Android, kao i druge platforme zahvaljujući ekosistemu dobrih API-ja će Vam omogućiti da ostanete u kontaktu sa prijateljima svuda.
+      within_reach_title: Uvek u kontaktu
+    find_another_instance: Nađite drugu instancu
+    generic_description: "%{domain} je server na mreži"
+    hosted_on: Mastodont hostovan na %{domain}
+    learn_more: Saznajte više
+    other_instances: Lista instanci
+    source_code: Izvorni kod
+    status_count_after: statusa
+    status_count_before: Koji su napisali
+    user_count_after: korisnika
+    user_count_before: Dom za
+    what_is_mastodon: Šta je Mastodont?
+  accounts:
+    follow: Follow
+    followers: Followers
+    following: Following
+    media: Multimedija
+    moved_html: "%{name} je pomeren na %{new_profile_link}:"
+    nothing_here: Ovde nema ništa!
+    people_followed_by: Ljudi koje %{name} prati
+    people_who_follow: Ljudi koji prate %{name}
+    posts: Tutovi
+    posts_with_replies: Tutovi i odgovori
+    remote_follow: Udaljena praćenja
+    reserved_username: Korisničko ime je rezervisano
+    roles:
+      admin: Administrator
+      moderator: Moderator
+    unfollow: Otprati
+  admin:
+    account_moderation_notes:
+      account: Moderator
+      create: Napravi
+      created_at: Datum
+      created_msg: Moderatorska beleška uspešno napravljena!
+      delete: Obriši
+      destroyed_msg: Moderatorska beleška uspešno obrisana!
+    accounts:
+      are_you_sure: Da li ste sigurni?
+      by_domain: Domen
+      confirm: Potvrdi
+      confirmed: Potvrđeno
+      demote: Ražaluj
+      disable: Isključi
+      disable_two_factor_authentication: Isključi 2FA
+      disabled: Isključena
+      display_name: Prikazano ime
+      domain: Domen
+      edit: Izmeni
+      email: E-pošta
+      enable: Uključi
+      enabled: Uključeno
+      feed_url: Adresa dovoda
+      followers: Pratioci
+      followers_url: Adresa pratioca
+      follows: Praćeni
+      inbox_url: Adresa sandučeta
+      ip: IP
+      location:
+        all: Sve
+        local: Lokalne
+        remote: Udaljene
+        title: Lokacija
+      login_status: Status prijave
+      media_attachments: Multimedijalni prilozi
+      memorialize: Prebaci u in memoriam
+      moderation:
+        all: Svi
+        silenced: Ućutkani
+        suspended: Suspendovani
+        title: Moderacija
+      moderation_notes: Moderatorske beleške
+      most_recent_activity: Najskorija aktivnost
+      most_recent_ip: Najskorija IP adresa
+      not_subscribed: Nije pretplaćen
+      order:
+        alphabetic: Abecedni
+        most_recent: Najskoriji
+        title: Redosled
+      outbox_url: Odlazno sanduče
+      perform_full_suspension: Izvrši kompletno isključenje
+      profile_url: Adresa profila
+      promote: Unapredi
+      protocol: Protokol
+      public: Javno
+      push_subscription_expires: PuSH subscription expires
+      redownload: Osveži avatar
+      reset: Resetuj
+      reset_password: Resetuj lozinku
+      resubscribe: Ponovo se pretplati
+      role: Ovlašćenja
+      roles:
+        admin: Administrator
+        moderator: Moderator
+        staff: Osoblje
+        user: Korisnik
+      salmon_url: Salmon adresa
+      search: Pretraga
+      shared_inbox_url: Adresa deljenog sandučeta
+      show:
+        created_reports: Prijave koje je napravio ovaj nalog
+        report: prijava
+        targeted_reports: Prijave napravljene o ovom nalogu
+      silence: Ućutkaj
+      statuses: Statusi
+      subscribe: Pretplati se
+      title: Nalozi
+      undo_silenced: Ukini ćutanje
+      undo_suspension: Ukini suspenziju
+      unsubscribe: Ukini pretplatu
+      username: Korisničko ime
+      web: Veb
+    action_logs:
+      actions:
+        confirm_user: "%{name} je potvrdio adresu e-pošte korisnika %{target}"
+        create_custom_emoji: "%{name} je otpremio novi emotikon %{target}"
+        create_domain_block: "%{name} je blokirao domen %{target}"
+        create_email_domain_block: "%{name} je stavio na crnu listu domen e-pošte %{target}"
+        demote_user: "%{name} je ražalovao korisnika %{target}"
+        destroy_domain_block: "%{name} je odblokirao domen %{target}"
+        destroy_email_domain_block: "%{name} je stavio na belu listu domen e-pošte %{target}"
+        destroy_status: "%{name} je uklonio status korisnika %{target}"
+        disable_2fa_user: "%{name} je isključio obaveznu dvofaktorsku identifikaciju za korisnika %{target}"
+        disable_custom_emoji: "%{name} je onemogućio emotikon %{target}"
+        disable_user: "%{name} je onemogućio prijavljivanje korisniku %{target}"
+        enable_custom_emoji: "%{name} je omogućio emotikon %{target}"
+        enable_user: "%{name} je omogućio prijavljivanje za korisnika %{target}"
+        memorialize_account: "%{name} je pretvorio stranu naloga %{target} kao in memoriam stranu"
+        promote_user: "%{name} je unapredio korisnika %{target}"
+        reset_password_user: "%{name} je resetovao lozinku korisniku %{target}"
+        resolve_report: "%{name} je odbacio prijavu %{target}"
+        silence_account: "%{name} je ućutkao nalog %{target}"
+        suspend_account: "%{name} je suspendovao nalog %{target}"
+        unsilence_account: "%{name} je ukinuo ćutanje nalogu %{target}"
+        unsuspend_account: "%{name} je ukinuo suspenziju nalogu %{target}"
+        update_custom_emoji: "%{name} je izmenio emotikon %{target}"
+        update_status: "%{name} je izmenio status korisnika %{target}"
+      title: Zapisnik
+    custom_emojis:
+      by_domain: Domen
+      copied_msg: Uspešno napravljena lokalna kopija emotikona
+      copy: Kopiraj
+      copy_failed_msg: Ne mogu da napravim lokalnu kopiju tog emotikona
+      created_msg: Emotikon uspešno napravljen!
+      delete: Obriši
+      destroyed_msg: Emotikon uspešno obrisan!
+      disable: Onemogući
+      disabled_msg: Emotikon uspešno onemogućen
+      emoji: Emotikon
+      enable: Omogući
+      enabled_msg: Emotikon uspešno omogućen
+      image_hint: PNG do 50KB
+      listed: Izlistan
+      new:
+        title: Dodaj novi proizvoljni emotikon
+      overwrite: Prepiši
+      shortcode: Prečica
+      shortcode_hint: Najmanje 2 karaktera, dozvoljeni su samo slova, brojevi i donje crte
+      title: Proizvoljni emotikoni
+      unlisted: Neizlistan
+      update_failed_msg: Ne mogu da ažuriram ovaj emotikon
+      updated_msg: emotikon uspešno ažuriran!
+      upload: Otpremi
+    domain_blocks:
+      add_new: Dodaj novi
+      created_msg: Blokiranje domena se obrađuje
+      destroyed_msg: Blokiranje domena je opozvano
+      domain: Domen
+      new:
+        create: Napravi blokadu
+        hint: Blokiranje domena neće sprečiti pravljenje naloga u bazi, ali će retroaktivno i automatski primeniti određene moderatorske metode nad tim nalozima.
+        severity:
+          desc_html: "<strong>Ućutkavanje</strong> će sve statuse ovog naloga učiniti nevidiljivim za sve, osim za one koji nalog već prate. <strong>Suspenzija</strong> će ukloniti sav sadržaj naloga, svu multimediju, i profilne podatke. Koristite <strong>Ništa</strong> ako samo želite da odbacite multimedijalne fajlove."
+          noop: Ništa
+          silence: Ućutkavanje
+          suspend: Suspenzija
+        title: Novo blokiranje domena
+      reject_media: Odbaci multimediju
+      reject_media_hint: Uklanja lokalno uskladištene multimedijske fajlove i odbija da ih skida na dalje. Nebitno je za suspenziju.
+      severities:
+        noop: Ništa
+        silence: Ućutkavanje
+        suspend: Suspenzija
+      severity: Oštrina
+      show:
+        affected_accounts:
+          few: Utiče na %{count} naloga u bazi
+          many: Utiče na %{count} naloga u bazi
+          one: Utiče na jedan nalog u bazi
+          other: Utiče na %{count} naloga u bazi
+        retroactive:
+          silence: Ugasi ućutkivanje za sve postojeće naloge sa ovog domena
+          suspend: Ugasi suspenzije za sve postojeće naloge sa ovog domena
+        title: Poništi blokadu domena za domen %{domain}
+        undo: Poništi
+      title: Blokade domena
+      undo: Poništi
+    email_domain_blocks:
+      add_new: Dodaj novuAdd new
+      created_msg: Uspešno dodao domen e-pošte na crnu listu
+      delete: Ukloni
+      destroyed_msg: Uspešno uklonjen domen e-pošte sa crne liste
+      domain: Domen
+      new:
+        create: Dodaj domen
+        title: Nova stavka u crnoj listi e-pošti
+      title: Crna lista adresa e-pošte
+    instances:
+      account_count: Poznati nalozi
+      domain_name: Domen
+      reset: Resetuj
+      search: Pretraga
+      title: Poznate instance
+    invites:
+      filter:
+        all: Sve
+        available: Aktivne
+        expired: Istekle
+        title: Filter
+      title: Pozivnice
+    reports:
+      action_taken_by: Akciju izveo
+      are_you_sure: Da li ste sigurni?
+      comment:
+        label: Komentar
+        none: Ništa
+      delete: Obriši
+      id: ID
+      mark_as_resolved: Označi kao rešen
+      nsfw:
+        'false': Otkrij medijske priloge
+        'true': Sakrij medijske priloge
+      report: 'Prijava #%{id}'
+      report_contents: Sadržaj
+      reported_account: Prijavljeni nalog
+      reported_by: Prijavio
+      resolved: Rešeni
+      silence_account: Ućutkaj nalog
+      status: Status
+      suspend_account: Suspenduj nalog
+      target: Cilj
+      title: Prijave
+      unresolved: Nerešeni
+      view: Pogledaj
+    settings:
+      bootstrap_timeline_accounts:
+        desc_html: Odvojite više korisničkih imena zarezom. Radi samo za lokalne i otključane naloge. Ako je prazno, onda se odnosi na sve lokalne administratore.
+        title: Nalozi za automatsko zapraćivanje za nove korisnike
+      contact_information:
+        email: Poslovna e-pošta
+        username: Kontakt korisničko ime
+      registrations:
+        closed_message:
+          desc_html: Prikazuje se na glavnoj strani kada je instanca zatvorena za registracije. Možete koristiti HTML tagove
+          title: Poruka o zatvorenoj registraciji
+        deletion:
+          desc_html: Dozvoli svima da mogu da obrišu svoj nalog
+          title: Otvori brisanje naloga
+        min_invite_role:
+          disabled: Niko
+          title: Samo preko pozivnice
+        open:
+          desc_html: Dozvoli svakome da kreira nalog
+          title: Otvorena registracija
+      show_staff_badge:
+        desc_html: Prikaži bedž osoblja na korisničkoj strani
+        title: Prikaži bedž osoblja
+      site_description:
+        desc_html: Uvodni pasus na naslovnoj strani i u meta HTML tagovima. Možete koristiti HTML tagove, konkretno <code>&lt;a&gt;</code> i <code>&lt;em&gt;</code>.
+        title: Opis instance
+      site_description_extended:
+        desc_html: Dobro mesto za vaš kod ponašanja, pravila, smernice i druge stvari po kojima se Vaša instanca razlikuje. Možete koristiti HTML tagove
+        title: Proizvoljne dodatne informacije
+      site_terms:
+        desc_html: Možete pisati Vašu politiku privatnosti, uslove korišćenja i ostale legalne stvari. Možete koristiti HTML tagove
+        title: Proizvoljni uslovi korišćenja
+      site_title: Ime instance
+      thumbnail:
+        desc_html: Koristi se za preglede kroz OpenGraph i API. Preporučuje se 1200x630px
+        title: Sličica instance
+      timeline_preview:
+        desc_html: Prikaži javnu lajnu na početnoj strani
+        title: Pregled lajne
+      title: Postavke sajta
+    statuses:
+      back_to_account: Nazad na stranu naloga
+      batch:
+        delete: Obriši
+        nsfw_off: NSFW isključen
+        nsfw_on: NSFW uključen
+      execute: Izvrši
+      failed_to_execute: Neuspelo izvršavanje
+      media:
+        hide: Sakrij multimediju
+        show: Prikaži multimediju
+        title: Multimedija
+      no_media: Bez multimedije
+      title: Statusi naloga
+      with_media: Sa multimedijom
+    subscriptions:
+      callback_url: Callback URL
+      confirmed: Potvrđeno
+      expires_in: Ističe za
+      last_delivery: Poslednja dostava
+      title: WebSub
+      topic: Topic
+    title: Administracija
+  admin_mailer:
+    new_report:
+      body: "%{reporter} je prijavio %{target}"
+      subject: Nova prijava za %{instance} (#%{id})
+  application_mailer:
+    salutation: "%{name},"
+    settings: 'Promeni podešavanja e-pošte: %{link}'
+    signature: Mastodont obaveštenje sa instance %{instance}
+    view: 'Pogledaj:'
+  applications:
+    created: Aplikacija uspešno napravljena
+    destroyed: Aplikacija uspešno obrisana
+    invalid_url: Data adresa nije ispravna
+    regenerate_token: Rekreiraj pristupni token
+    token_regenerated: Pristupni token uspešno rekreiran
+    warning: Oprezno sa ovim podacima. Nikad je ne delite ni sa kim!
+    your_token: Vaš pristupni token
+  auth:
+    agreement_html: Pristupanjem instanci se slažete sa <a href="%{rules_path}">pravilima instance</a> i <a href="%{terms_path}">uslovima korišćenja</a>.
+    change_password: Bezbednost
+    delete_account: Obriši nalog
+    delete_account_html: Ako želite da obrišete Vaš nalog, možete <a href="%{path}">nastaviti ovde</a>. Bićete upitani da potvrdite.
+    didnt_get_confirmation: Niste dobili poruku sa uputstvima za potvrdu naloga?
+    forgot_password: Zaboravili ste lozinku?
+    invalid_reset_password_token: Token za resetovanje lozinke je neispravan ili je istekao. Zatražite novi.
+    login: Prijavi se
+    logout: Odjava
+    migrate_account: Pomeri u drugi nalog
+    migrate_account_html: Ako želite da preusmerite ovaj nalog na neki drugi, možete to <a href="%{path}">podesiti ovde</a>.
+    register: Registruj se
+    resend_confirmation: Pošalji poruku sa uputstvima o potvrdi naloga ponovo
+    reset_password: Resetuj lozinku
+    set_new_password: Postavi novu lozinku
+  authorize_follow:
+    error: Nažalost, desila se greška pri traženju udaljenog naloga
+    follow: Zaprati
+    follow_request: 'Poslali ste zahtev za praćenjen za:'
+    following: 'Sjajno! Sada pratite:'
+    post_follow:
+      close: Ili možete zatvoriti ovaj prozor.
+      return: Vrati se na profil ovog korisnika
+      web: Idi na veb
+    title: Zaprati %{acct}
+  datetime:
+    distance_in_words:
+      about_x_hours: "%{count}h"
+      about_x_months: "%{count}mesec"
+      about_x_years: "%{count}god"
+      almost_x_years: "%{count}god"
+      half_a_minute: Upravo sad
+      less_than_x_minutes: "%{count}m"
+      less_than_x_seconds: Upravo sad
+      over_x_years: "%{count}god"
+      x_days: "%{count}d"
+      x_minutes: "%{count}m"
+      x_months: "%{count}mesec"
+      x_seconds: "%{count}s"
+  deletes:
+    bad_password_msg: Dobar pokušaj, hakeri! Neispravna lozinka
+    confirm_password: Unesite trenutnu lozinku da bismo proverili Vaš identitet
+    description_html: Ovo će <strong>trajno, bespovratno</strong> ukloniti sadržaj sa Vašef naloga i deaktivirati ga. Vaše korisničko ime će ostati rezervisano da se spreči da se neko ne predstavlja kao Vi sutra.
+    proceed: Obriši nalog
+    success_msg: Vaš nalog je uspešno obrisan
+    warning_html: Garantovano je samo brisanje sadržaja sa ove instance. Sadržaj koji je deljen dalje će verovatno da ostavi neke tragove. Nedostupni i ugašeni serveri, kao i serveri koji su odjavljeni od primanja statusa od Vas, neće ažurirati svoje baze.
+    warning_title: Dostupnost rasejanog sadržaja
+  errors:
+    '403': Nemate dozvola da vidite ovu stranu.
+    '404': Strana koju ste tražili ne postoji.
+    '410': Strana koju ste tražili više ne postoji.
+    '422':
+      content: Security verification failed. Are you blocking cookies?
+      title: Security verification failed
+    '429': Uspored
+    '500':
+      content: Izvinjavamo se, nešto je pošlo po zlu sa ove strane.
+      title: Strana nije ispravna
+    noscript_html: Da biste koristili Mastodont veb aplikaciju, omogućite JavaScript. U suprotnom, probajte neku od <a href="https://github.com/tootsuite/documentation/blob/master/Using-Mastodon/Apps.md">originalnih aplikacija</a> za Mastodont za Vašu platformu.
+  exports:
+    blocks: Blokirali ste
+    csv: CSV
+    follows: PRatite
+    mutes: Mutirali ste
+    storage: Multimedijalno skladište
+  followers:
+    domain: Domen
+    explanation_html: Ako želite da osigurate privatnost Vaših statusa, morate biti svesni ko Vas prati. <strong>Vaši privatni statusi se šalju na sve instance na kojima imate pratioce</strong>. Možda želite da ih pregledate i da uklonite one pratioce na onim instancama za koje nemate poverenja da će poštovati Vašu privatnost.
+    followers_count: Broj pratilaca
+    lock_link: Zaključajte nalog
+    purge: Ukloni iz pratioca
+    success:
+      few: U procesu blokiranja pratioca sa %{count} domena...
+      many: U procesu blokiranja pratioca sa %{count} domena...
+      one: U procesu blokiranja pratioca sa jednog domena...
+      other: U procesu blokiranja pratioca sa %{count} domena...
+    true_privacy_html: Zapamtite da se <strong>prava privatnost može postići samo šifrovanjem sa kraja na kraj</strong>.
+    unlocked_warning_html: Svako može da Vas zaprati da odmah vidi Vaše privatne statuse. %{lock_link} da biste pregledali i odbacili pratioce.
+    unlocked_warning_title: Vaš nalog nije zaključan
+  generic:
+    changes_saved_msg: Izmene uspešno sačuvane!
+    powered_by: omogućio %{link}
+    save_changes: Snimi izmene
+    validation_errors:
+      few: Nešto nije baš kako treba! Pregledajte %{count} greške ispod
+      many: Nešto nije baš kako treba! Pregledajte %{count} grešaka ispod
+      one: Nešto nije baš kako treba! Pregledajte greške ispod
+      other: Nešto nije baš kako treba! Pregledajte %{count} grešaka ispod
+  imports:
+    preface: Možete uvesti podatke koje ste izvezli sa druge instance, kao što su liste ljudi koje ste pratili ili blokirali.
+    success: Vaši podaci su uspešno otpremljeni i biće obrađeni uskoro
+    types:
+      blocking: Lista blokiranja
+      following: Lista pratilaca
+      muting: Lista mutiranih
+    upload: Otpremi
+  in_memoriam_html: In Memoriam.
+  invites:
+    delete: Deaktiviraj
+    expired: Isteklo
+    expires_in:
+      '1800': 30 minuta
+      '21600': 6 sati
+      '3600': 1 sad
+      '43200': 12 sati
+      '86400': 1 dan
+    expires_in_prompt: Nikad
+    generate: Generiši
+    max_uses:
+      few: "%{count} korišćenja"
+      many: "%{count} korišćenja"
+      one: 1 korišćenje
+      other: "%{count} korišćenja"
+    max_uses_prompt: Bez ograničenja
+    prompt: Generiši i podeli linkove sa drugima da im odobrite pristup ovoj instanci
+    table:
+      expires_at: Ističe
+      uses: Korišćenja
+    title: Pozovi ljude
+  landing_strip_html: "<strong>%{name}</strong> je korisnik na %{link_to_root_path}. Možete ga zapratiti ili komunicirati sa njim ako imte nalog bilo gde u fediversu."
+  landing_strip_signup_html: Ako nemate, možete se <a href="%{sign_up_path}">registrovati ovde</a>.
+  lists:
+    errors:
+      limit: Dostigli ste limit broja listi
+  media_attachments:
+    validations:
+      images_and_video: Ne može da se prikači video na status koji već ima slike
+      too_many: Ne može se prikačiti više od 4 fajla
+  migrations:
+    acct: korisnik@domen novog naloga
+    currently_redirecting: 'Profil Vam je podešen da preusmerava na :'
+    proceed: Sačuvaj
+    updated_msg: Prebacivanje postavki Vašeg naloga uspešno izmenjeno!
+  moderation:
+    title: Moderacija
+  notification_mailer:
+    digest:
+      body: 'Evo kratak pregled šta ste propustili na instanci %{instance} od poslednje posete od %{since}:'
+      mention: "%{name} Vas je pomenuo u:"
+      new_followers_summary:
+        few: Dobili ste %{count} nova pratioca! Sjajno!
+        many: Dobili ste %{count} novih pratioca! Sjajno!
+        one: Dobili ste jednog novog pratioca! Jeee!
+        other: Dobili ste %{count} novih pratioca! Sjajno!
+      subject:
+        few: "%{count} nova obaveštenja od poslednje posete \U0001F418"
+        many: "%{count} novih obaveštenja od poslednje posete \U0001F418"
+        one: "1 novo obaveštenje od poslednje posete \U0001F418"
+        other: "%{count} novih obaveštenja od poslednje posete \U0001F418"
+    favourite:
+      body: "%{name} je postavio kao omiljen Vaš status:"
+      subject: "%{name} je postavio kao omiljen Vaš status"
+    follow:
+      body: "%{name} Vas je zapratio!"
+      subject: "%{name} Vas je zapratio"
+    follow_request:
+      body: "%{name} je zatražio da Vas zaprati"
+      subject: 'Pratioci na čekanju: %{name}'
+    mention:
+      body: "%{name} Vas je pomenuo u:"
+      subject: "%{name} Vas je pomenuo"
+    reblog:
+      body: "%{name} Vam je podržao(la) status:"
+      subject: "%{name} je podržao(la) Vaš status"
+  number:
+    human:
+      decimal_units:
+        format: "%n%u"
+        units:
+          billion: B
+          million: M
+          quadrillion: Q
+          thousand: K
+          trillion: T
+          unit: ''
+  pagination:
+    next: Sledeći
+    prev: Prethodni
+    truncate: "&hellip;"
+  preferences:
+    languages: Jezici
+    other: Ostali
+    publishing: Objavljivanje
+    web: Veb
+  push_notifications:
+    favourite:
+      title: "%{name} je stavio Vaš status za omiljeni"
+    follow:
+      title: "%{name} Vas je zapratio"
+    group:
+      title: "%{count} obaveštenja"
+    mention:
+      action_boost: Podrži
+      action_expand: Prikaži još
+      action_favourite: Omiljeni
+      title: "%{name} Vas je pomenuo"
+    reblog:
+      title: "%{name} je podržao(la) Vaš status"
+  remote_follow:
+    acct: Unesite Vaš korisnik@domen sa koga želite da pratite
+    missing_resource: Ne mogu da nađem zahtevanu adresu preusmeravanja za Vaš nalog
+    proceed: Nastavite da zapratite
+    prompt: 'Zapratite će:'
+  sessions:
+    activity: Poslednja aktivnost
+    browser: Veb čitač
+    browsers:
+      alipay: Alipay
+      blackberry: Blekberi
+      chrome: Hrom
+      edge: Microsoft Edge
+      firefox: Firefox
+      generic: Nepoznati veb čitač
+      ie: Internet Explorer
+      micro_messenger: MicroMessenger
+      nokia: Nokia S40 Ovi Browser
+      opera: Opera
+      phantom_js: PhantomJS
+      qq: QQ Browser
+      safari: Safari
+      uc_browser: UCBrowser
+      weibo: Weibo
+    current_session: Trenutna sesija
+    description: "%{browser} sa %{platform}"
+    explanation: Ovo su trenutno prijavljeni veb čitači na Vaš Mastodont nalog.
+    ip: IP
+    platforms:
+      adobe_air: Adobe Air-a
+      android: Androida
+      blackberry: Blekberija
+      chrome_os: Hrom OS-a
+      firefox_os: Fajerfoks OS-a
+      ios: iOS
+      linux: Linuksa
+      mac: Mac-a
+      other: nepoznate platforme
+      windows: Vindouza
+      windows_mobile: Vindouz mobilnog
+      windows_phone: Vindouz telefona
+    revoke: Opozovi
+    revoke_success: Sesija uspešno opozvana
+    title: Sesije
+  settings:
+    authorized_apps: Autorizovane aplikacije
+    back: Nazad na Mastodonta
+    delete: Brisanje naloga
+    development: Razvoj
+    edit_profile: Izmena profila
+    export: Izvoz podataka
+    followers: Autorizovani pratioci
+    import: Uvoz
+    migrate: Prebacivanje naloga
+    notifications: Obaveštenja
+    preferences: Podešavanja
+    settings: Postavke
+    two_factor_authentication: Dvofaktorska identifikacija
+    your_apps: Vaše aplikacije
+  statuses:
+    open_in_web: Otvori u vebu
+    over_character_limit: ograničenje od %{max} karaktera prekoračeno
+    pin_errors:
+      limit: Već imate prikačen najveći broj tutova
+      ownership: Tuđi tutovi ne mogu da se prikače
+      private: Tutovi koji nisu javni ne mogu da se prikače
+      reblog: Podrška ne može da se prikači
+    show_more: Prikaži još
+    title: '%{name}: "%{quote}"'
+    visibilities:
+      private: Samo pratioci
+      private_long: Samo prikaži pratiocima
+      public: Javno
+      public_long: Svako može da vidi
+      unlisted: Neizlistano
+      unlisted_long: Svako može da vidi, ali nije izlistano na javnim lajnama
+  stream_entries:
+    click_to_show: Klikni da vidiš
+    pinned: Prikačeni tut
+    reblogged: podržano
+    sensitive_content: Osetljiv sadržaj
+  terms:
+    body_html: |
+      <h2>Privacy Policy</h2>
+
+      <h3 id="collect">What information do we collect?</h3>
+
+      <p>We collect information from you when you register on our site and gather data when you participate in the forum by reading, writing, and evaluating the content shared here.</p>
+
+      <p>When registering on our site, you may be asked to enter your name and e-mail address. You may, however, visit our site without registering. Your e-mail address will be verified by an email containing a unique link. If that link is visited, we know that you control the e-mail address.</p>
+
+      <p>When registered and posting, we record the IP address that the post originated from. We also may retain server logs which include the IP address of every request to our server.</p>
+
+      <h3 id="use">What do we use your information for?</h3>
+
+      <p>Any of the information we collect from you may be used in one of the following ways:</p>
+
+      <ul>
+        <li>To personalize your experience &mdash; your information helps us to better respond to your individual needs.</li>
+        <li>To improve our site &mdash; we continually strive to improve our site offerings based on the information and feedback we receive from you.</li>
+        <li>To improve customer service &mdash; your information helps us to more effectively respond to your customer service requests and support needs.</li>
+        <li>To send periodic emails &mdash; The email address you provide may be used to send you information, notifications that you request about changes to topics or in response to your user name, respond to inquiries, and/or other requests or questions.</li>
+      </ul>
+
+      <h3 id="protect">How do we protect your information?</h3>
+
+      <p>We implement a variety of security measures to maintain the safety of your personal information when you enter, submit, or access your personal information.</p>
+
+      <h3 id="data-retention">What is your data retention policy?</h3>
+
+      <p>We will make a good faith effort to:</p>
+
+      <ul>
+        <li>Retain server logs containing the IP address of all requests to this server no more than 90 days.</li>
+        <li>Retain the IP addresses associated with registered users and their posts no more than 5 years.</li>
+      </ul>
+
+      <h3 id="cookies">Do we use cookies?</h3>
+
+      <p>Yes. Cookies are small files that a site or its service provider transfers to your computer's hard drive through your Web browser (if you allow). These cookies enable the site to recognize your browser and, if you have a registered account, associate it with your registered account.</p>
+
+      <p>We use cookies to understand and save your preferences for future visits and compile aggregate data about site traffic and site interaction so that we can offer better site experiences and tools in the future. We may contract with third-party service providers to assist us in better understanding our site visitors. These service providers are not permitted to use the information collected on our behalf except to help us conduct and improve our business.</p>
+
+      <h3 id="disclose">Do we disclose any information to outside parties?</h3>
+
+      <p>We do not sell, trade, or otherwise transfer to outside parties your personally identifiable information. This does not include trusted third parties who assist us in operating our site, conducting our business, or servicing you, so long as those parties agree to keep this information confidential. We may also release your information when we believe release is appropriate to comply with the law, enforce our site policies, or protect ours or others rights, property, or safety. However, non-personally identifiable visitor information may be provided to other parties for marketing, advertising, or other uses.</p>
+
+      <h3 id="third-party">Third party links</h3>
+
+      <p>Occasionally, at our discretion, we may include or offer third party products or services on our site. These third party sites have separate and independent privacy policies. We therefore have no responsibility or liability for the content and activities of these linked sites. Nonetheless, we seek to protect the integrity of our site and welcome any feedback about these sites.</p>
+
+      <h3 id="coppa">Children's Online Privacy Protection Act Compliance</h3>
+
+      <p>Our site, products and services are all directed to people who are at least 13 years old. If this server is in the USA, and you are under the age of 13, per the requirements of COPPA (<a href="https://en.wikipedia.org/wiki/Children%27s_Online_Privacy_Protection_Act">Children's Online Privacy Protection Act</a>) do not use this site.</p>
+
+      <h3 id="online">Online Privacy Policy Only</h3>
+
+      <p>This online privacy policy applies only to information collected through our site and not to information collected offline.</p>
+
+      <h3 id="consent">Your Consent</h3>
+
+      <p>By using our site, you consent to our web site privacy policy.</p>
+
+      <h3 id="changes">Changes to our Privacy Policy</h3>
+
+      <p>If we decide to change our privacy policy, we will post those changes on this page.</p>
+
+      <p>This document is CC-BY-SA. It was last updated May 31, 2013.</p>
+
+      <p>Originally adapted from the <a href="https://github.com/discourse/discourse">Discourse privacy policy</a>.</p>
+    title: Uslovi korišćenja i politika privatnosti instance %{instance}
+  themes:
+    default: Mastodont
+  time:
+    formats:
+      default: "%b %d, %Y, %H:%M"
+  two_factor_authentication:
+    code_hint: Unesite kod sa Vaše aplikacije za proveru identiteta da potvrdite
+    description_html: Ako uključite <strong>dvofaktorsku identifikaciju</strong>, moraćete da imate telefon sa sobom da biste mogli da se prijavite. Telefon će onda generisati tokene za Vašu prijavu.
+    disable: Isključi
+    enable: Uključi
+    enabled: Dvofaktorska identifikacija je uključena
+    enabled_success: Dvofaktorska identifikacija je uspešno uključena
+    generate_recovery_codes: Generiši kodove za oporavak
+    instructions_html: "<strong>Skenirajte ovaj QR kod u Google Authenticator ili nekoj sličnoj TOTP aplikaciji na Vašem telefonu</strong>. Od sada, ta aplikacija će Vam generisati tokene koje morate uneti da biste se prijavili."
+    lost_recovery_codes: Kodovi za oporavak Vam omogućavaju da povratite pristup nalogu ako izgubite telefon. Ako izgubite kodove za oporavak, možete ih regenerisati ovde. Od tog trenutka, stari kodovi za oporavak više ne važe.
+    manual_instructions: 'Ukoliko ne možete da skenirate QR kod i morate ga unesete ručno, evo je ogoljena šifra:'
+    recovery_codes: Napravite rezervu kodova za oporavak
+    recovery_codes_regenerated: Kodovi za oporavak uspešno regenerisani
+    recovery_instructions_html: Ako ikada izgubite pristup telefonu, možete iskoristiti kodove za oporavak date ispod da povratite pristup nalogu. <strong>Držite kodove za oporavak na sigurnom</strong>. Na primer, odštampajte ih i čuvajte ih sa ostalim važnim dokumentima.
+    setup: Nameštanje
+    wrong_code: Uneseni kod nije ispravan! Da li su vremena na serveru i na uređaju ispravna?
+  users:
+    invalid_email: Adresa e-pošte nije ispravna
+    invalid_otp_token: Neispravni dvofaktorski kod
+    signed_in_as: 'Prijavljen kao:'
diff --git a/config/locales/sr.yml b/config/locales/sr.yml
index e59b5379c..6961ff841 100644
--- a/config/locales/sr.yml
+++ b/config/locales/sr.yml
@@ -1,7 +1,7 @@
 ---
 sr:
   about:
-    about_hashtag_html: Ово су јавни статуси таговани са <strong>#%{hashtag}</strong>. Можете одговарати на њих ако имате налог било где у федиверзуму.
+    about_hashtag_html: Ово су јавни статуси таговани са <strong>#%{hashtag}</strong>. Можете одговарати на њих ако имате налог било где у федиверсу.
     about_mastodon_html: Мастодонт је друштвена мрежа базирана на отвореним протоколима и слободном софтверу отвореног кода. Децентрализована је као што је децентрализована е-пошта.
     about_this: О инстанци
     closed_registrations: Регистрације су тренутно затворене на овој инстанци. Ипак! Можете наћи другу инстанцу на којој ћете направити налог и одатле добити приступ истој овој мрежи.
@@ -509,8 +509,8 @@ sr:
       body: "%{name} Вас је поменуо у:"
       subject: "%{name} Вас је поменуо"
     reblog:
-      body: "%{name} Вам је погурао статус:"
-      subject: "%{name} је погурао Ваш статус"
+      body: "%{name} Вам је подржао(ла) статус:"
+      subject: "%{name} је подржао(ла) Ваш статус"
   number:
     human:
       decimal_units:
@@ -539,12 +539,12 @@ sr:
     group:
       title: "%{count} обавештења"
     mention:
-      action_boost: Погурај
+      action_boost: Подржи
       action_expand: Прикажи још
       action_favourite: Омиљени
       title: "%{name} Вас је поменуо"
     reblog:
-      title: "%{name} је погурао Ваш статус"
+      title: "%{name} је подржао(ла) Ваш статус"
   remote_follow:
     acct: Унесите Ваш корисник@домен са кога желите да пратите
     missing_resource: Не могу да нађем захтевану адресу преусмеравања за Ваш налог
@@ -611,7 +611,7 @@ sr:
       limit: Већ имате прикачен највећи број тутова
       ownership: Туђи тутови не могу да се прикаче
       private: Тутови који нису јавни не могу да се прикаче
-      reblog: Погуравање не може да се прикачи
+      reblog: Подршка не може да се прикачи
     show_more: Прикажи још
     title: '%{name}: "%{quote}"'
     visibilities:
@@ -624,7 +624,7 @@ sr:
   stream_entries:
     click_to_show: Кликни да видиш
     pinned: Прикачени тут
-    reblogged: погурано
+    reblogged: подржано
     sensitive_content: Осетљив садржај
   terms:
     body_html: |
diff --git a/spec/lib/formatter_spec.rb b/spec/lib/formatter_spec.rb
index 71b6b78d2..e79be3645 100644
--- a/spec/lib/formatter_spec.rb
+++ b/spec/lib/formatter_spec.rb
@@ -332,7 +332,7 @@ RSpec.describe Formatter do
     end
 
     context 'contains malicious classes' do
-      let(:text) { '<span class="status__content__spoiler-link">Show more</span>' }
+      let(:text) { '<span class="mention	status__content__spoiler-link">Show more</span>' }
 
       it 'strips malicious classes' do
         is_expected.to_not include 'status__content__spoiler-link'
diff --git a/spec/mailers/user_mailer_spec.rb b/spec/mailers/user_mailer_spec.rb
index 1f6d44015..9f17993e0 100644
--- a/spec/mailers/user_mailer_spec.rb
+++ b/spec/mailers/user_mailer_spec.rb
@@ -33,6 +33,20 @@ describe UserMailer, type: :mailer do
                      instance: Rails.configuration.x.local_domain
   end
 
+  describe 'reconfirmation_instructions' do
+    let(:mail) { UserMailer.confirmation_instructions(receiver, 'spec') }
+
+    it 'renders reconfirmation instructions' do
+      receiver.update!(email: 'new-email@example.com', locale: nil)
+      expect(mail.body.encoded).to include 'new-email@example.com'
+      expect(mail.body.encoded).to include 'spec'
+      expect(mail.body.encoded).to include Rails.configuration.x.local_domain
+      expect(mail.subject).to eq I18n.t('devise.mailer.reconfirmation_instructions.subject',
+                                        instance: Rails.configuration.x.local_domain,
+                                        locale: I18n.default_locale)
+    end
+  end
+
   describe 'reset_password_instructions' do
     let(:mail) { UserMailer.reset_password_instructions(receiver, 'spec') }
 
@@ -57,4 +71,16 @@ describe UserMailer, type: :mailer do
     include_examples 'localized subject',
                      'devise.mailer.password_change.subject'
   end
+
+  describe 'email_changed' do
+    let(:mail) { UserMailer.email_changed(receiver) }
+
+    it 'renders email change notification' do
+      receiver.update!(locale: nil)
+      expect(mail.body.encoded).to include receiver.email
+    end
+
+    include_examples 'localized subject',
+                     'devise.mailer.email_changed.subject'
+  end
 end