Compare commits

...

243 commits

Author SHA1 Message Date
Erin Shepherd 5d49c2c553 Merge remote-tracking branch 'upstream/main' 2022-11-01 16:21:58 +00:00
prplecake fc340c9154
Change ul, ol margin-left to 2em (#1879) 2022-11-01 09:41:58 +01:00
prplecake c199556f64
Fix 'App settings' link in basic web UI (#1880) 2022-11-01 09:38:55 +01:00
Jeremy Kescher 41885c8715
Remove/update old "tootsuite" references, except those needed for Docker (#1860) 2022-11-01 09:38:05 +01:00
Claire 968f343006
Merge pull request #1876 from ClearlyClaire/glitch-soc/merge-upstream
Merge upstream changes
2022-10-31 18:25:34 +01:00
Claire 1fe4e5e38c Merge branch 'main' into glitch-soc/merge-upstream 2022-10-31 08:37:32 +01:00
Eugen Rochko 26478f461c
Remove language filtering from hashtag timelines (#19563) 2022-10-30 21:29:23 +01:00
Claire 5fd758fad1 Merge branch 'main' into glitch-soc/merge-upstream 2022-10-30 19:35:59 +01:00
Claire a529d6d93e
Fix invites (#19560)
Fixes #19507

Fix regression from #19296
2022-10-30 19:04:39 +01:00
Eugen Rochko 8048874a3a [Glitch] Fix sidebar and tabs on settings on small screens in admin UI
Port ad83e64795 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-30 18:32:20 +01:00
Eugen Rochko ebfe393e9c [Glitch] Fix upload progress not communicating processing phase in web UI
Port 30ef110224 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-30 18:30:58 +01:00
Eugen Rochko eb307ec1bd [Glitch] Fix logged out search and changed logged-in search placeholder
Port 55af04b253 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-30 18:24:57 +01:00
Claire eee36267d6 Merge branch 'main' into glitch-soc/merge-upstream
Conflicts:
- `app/javascript/mastodon/locales/ja.json`:
  Upstream change too close to a glitch-soc-specific string.
  The glitch-soc-specific string should not have been in this file, so it
  has been moved to `app/javascript/flavours/glitch/locales/ja.js`.
- `app/javascript/packs/public.js`:
  Upstream refactored a part, that as usual is split and duplicated in various
  pack files. Updated those pack files accordingly.
- `app/views/layouts/application.html.haml`:
  Upstream fixed custom.css path in a different way than we did, went with
  upstream's change.
2022-10-30 18:15:28 +01:00
Eugen Rochko ac9fb0d654
Add reputation and followers score boost to SQL-only account search (#19251) 2022-10-30 13:23:05 +01:00
Eugen Rochko 40c7f3e830
Fix account action type validation (#19476)
* Fix account action type validation

Fix #19143

* Fix #19145

* Fix code style issues
2022-10-30 02:44:32 +02:00
Eugen Rochko 276b85bc91
Fix admin APIs returning deleted object instead of empty object upon delete (#19479)
Fix #19153
2022-10-30 02:43:57 +02:00
Eugen Rochko 5724da0780
Fix language not being saved when editing status (#19543)
Fix #19542
2022-10-30 02:43:27 +02:00
Eugen Rochko 3b024c563c
Fix not being able to input featured tag with # (#19535) 2022-10-30 02:43:20 +02:00
Eugen Rochko ad83e64795
Fix sidebar and tabs on settings on small screens in admin UI (#19533) 2022-10-30 02:43:15 +02:00
Ben Hardill 6094a916b1
Fix helm chart use of Postgres Password (#19537)
Fixes #19536
2022-10-30 01:30:16 +02:00
Eugen Rochko 30ef110224
Fix upload progress not communicating processing phase in web UI (#19530) 2022-10-29 20:05:53 +02:00
Yurii Izorkin a449ee8654
nginx: optimize locations (#19438)
* nginx: optimize locations

* nginx: don't use regex in locations

* nginx: optimize Cache-Control headaers

* nginx: use 404 error_page for missing static files

* nginx: sort locations

* nginx: add missing HSTS header
2022-10-29 15:06:23 +02:00
Eugen Rochko f910f0dc92
Fix wrong host being used for custom.css when asset host configured (#19521) 2022-10-29 14:04:24 +02:00
Matthias Bethke 7926cb1bc7
fix name of Lao language (#19520)
It said ພາສາ or pha-sa, which means just "language" in Lao. "ພາສາລາວ",
pha-sa lao, is the full name but the short "ລາວ" is commonly used.
2022-10-29 13:34:56 +02:00
Eugen Rochko 55af04b253
Fix logged out search and changed logged-in search placeholder (#19514) 2022-10-29 13:32:49 +02:00
Eugen Rochko e6d415bb1f
New Crowdin updates (#19425)
* New translations en.yml (Occitan)

* New translations doorkeeper.en.yml (Armenian)

* New translations doorkeeper.en.yml (Danish)

* New translations doorkeeper.en.yml (German)

* New translations doorkeeper.en.yml (Greek)

* New translations doorkeeper.en.yml (Frisian)

* New translations doorkeeper.en.yml (Basque)

* New translations doorkeeper.en.yml (Finnish)

* New translations doorkeeper.en.yml (Hebrew)

* New translations doorkeeper.en.yml (Hungarian)

* New translations doorkeeper.en.yml (Italian)

* New translations doorkeeper.en.yml (Catalan)

* New translations doorkeeper.en.yml (Japanese)

* New translations doorkeeper.en.yml (Georgian)

* New translations doorkeeper.en.yml (Korean)

* New translations doorkeeper.en.yml (Dutch)

* New translations doorkeeper.en.yml (Norwegian)

* New translations doorkeeper.en.yml (Polish)

* New translations doorkeeper.en.yml (Portuguese)

* New translations doorkeeper.en.yml (Czech)

* New translations doorkeeper.en.yml (Bulgarian)

* New translations en.yml (Serbian (Latin))

* New translations en.yml (Sorani (Kurdish))

* New translations en.yml (Corsican)

* New translations en.yml (Sardinian)

* New translations en.yml (Sanskrit)

* New translations en.yml (Kabyle)

* New translations doorkeeper.en.yml (Arabic)

* New translations en.yml (Taigi)

* New translations en.yml (Silesian)

* New translations en.yml (Standard Moroccan Tamazight)

* New translations doorkeeper.en.yml (Romanian)

* New translations doorkeeper.en.yml (French)

* New translations doorkeeper.en.yml (Spanish)

* New translations doorkeeper.en.yml (Afrikaans)

* New translations doorkeeper.en.yml (Russian)

* New translations doorkeeper.en.yml (Slovak)

* New translations doorkeeper.en.yml (Breton)

* New translations doorkeeper.en.yml (Welsh)

* New translations doorkeeper.en.yml (Esperanto)

* New translations doorkeeper.en.yml (Chinese Traditional, Hong Kong)

* New translations doorkeeper.en.yml (Tatar)

* New translations doorkeeper.en.yml (Malayalam)

* New translations doorkeeper.en.yml (Sinhala)

* New translations doorkeeper.en.yml (Latvian)

* New translations doorkeeper.en.yml (Scottish Gaelic)

* New translations doorkeeper.en.yml (Asturian)

* New translations doorkeeper.en.yml (Occitan)

* New translations doorkeeper.en.yml (Serbian (Latin))

* New translations doorkeeper.en.yml (Kurmanji (Kurdish))

* New translations doorkeeper.en.yml (Sorani (Kurdish))

* New translations doorkeeper.en.yml (Corsican)

* New translations doorkeeper.en.yml (Sardinian)

* New translations doorkeeper.en.yml (Hindi)

* New translations doorkeeper.en.yml (Estonian)

* New translations doorkeeper.en.yml (Slovenian)

* New translations doorkeeper.en.yml (Icelandic)

* New translations doorkeeper.en.yml (Albanian)

* New translations doorkeeper.en.yml (Serbian (Cyrillic))

* New translations doorkeeper.en.yml (Swedish)

* New translations doorkeeper.en.yml (Turkish)

* New translations doorkeeper.en.yml (Ukrainian)

* New translations doorkeeper.en.yml (Chinese Simplified)

* New translations doorkeeper.en.yml (Chinese Traditional)

* New translations doorkeeper.en.yml (Vietnamese)

* New translations doorkeeper.en.yml (Galician)

* New translations doorkeeper.en.yml (Portuguese, Brazilian)

* New translations doorkeeper.en.yml (Kazakh)

* New translations doorkeeper.en.yml (Indonesian)

* New translations doorkeeper.en.yml (Persian)

* New translations doorkeeper.en.yml (Tamil)

* New translations doorkeeper.en.yml (Spanish, Argentina)

* New translations doorkeeper.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Marathi)

* New translations doorkeeper.en.yml (Thai)

* New translations doorkeeper.en.yml (Croatian)

* New translations doorkeeper.en.yml (Norwegian Nynorsk)

* New translations doorkeeper.en.yml (Kabyle)

* New translations doorkeeper.en.yml (Ido)

* New translations doorkeeper.en.yml (Standard Moroccan Tamazight)

* New translations en.yml (Czech)

* New translations en.json (Czech)

* New translations simple_form.en.yml (Czech)

* New translations en.yml (Danish)

* New translations en.yml (Hungarian)

* New translations en.yml (Polish)

* New translations en.json (Icelandic)

* New translations en.yml (Icelandic)

* New translations simple_form.en.yml (Icelandic)

* New translations activerecord.en.yml (Icelandic)

* New translations devise.en.yml (Icelandic)

* New translations en.yml (Polish)

* New translations en.json (Russian)

* New translations en.yml (Russian)

* New translations en.json (Icelandic)

* New translations en.yml (Icelandic)

* New translations en.json (Latvian)

* New translations en.yml (Latvian)

* New translations simple_form.en.yml (Icelandic)

* New translations en.json (Finnish)

* New translations en.yml (Finnish)

* New translations en.yml (Vietnamese)

* New translations en.yml (Finnish)

* New translations en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Finnish)

* New translations en.yml (Turkish)

* New translations en.json (Finnish)

* New translations en.yml (Finnish)

* New translations simple_form.en.yml (Finnish)

* New translations simple_form.en.yml (Turkish)

* New translations en.json (Dutch)

* New translations en.yml (Catalan)

* New translations en.yml (Dutch)

* New translations simple_form.en.yml (Dutch)

* New translations en.json (Scottish Gaelic)

* New translations en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations activerecord.en.yml (Scottish Gaelic)

* New translations devise.en.yml (Scottish Gaelic)

* New translations en.yml (Greek)

* New translations en.yml (Italian)

* New translations en.yml (Dutch)

* New translations en.yml (Spanish, Argentina)

* New translations en.yml (Dutch)

* New translations en.yml (Slovenian)

* New translations en.yml (Ukrainian)

* New translations en.yml (Galician)

* New translations en.yml (Chinese Simplified)

* New translations en.json (Chinese Simplified)

* New translations en.yml (Galician)

* New translations simple_form.en.yml (Chinese Simplified)

* New translations en.yml (Chinese Simplified)

* New translations simple_form.en.yml (Chinese Simplified)

* New translations en.json (French)

* New translations en.yml (Thai)

* New translations simple_form.en.yml (Thai)

* New translations en.yml (Thai)

* New translations en.json (Thai)

* New translations simple_form.en.yml (Spanish)

* New translations en.json (French)

* New translations en.yml (French)

* New translations simple_form.en.yml (French)

* New translations en.json (Dutch)

* New translations en.yml (Dutch)

* New translations en.yml (Portuguese)

* New translations simple_form.en.yml (Portuguese)

* New translations en.yml (Dutch)

* New translations en.json (Dutch)

* New translations en.json (Arabic)

* New translations en.yml (Arabic)

* New translations en.json (Breton)

* New translations en.json (Scottish Gaelic)

* New translations en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Arabic)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations en.yml (German)

* New translations en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations en.yml (German)

* New translations activerecord.en.yml (Turkish)

* New translations activerecord.en.yml (Polish)

* New translations activerecord.en.yml (Portuguese)

* New translations activerecord.en.yml (Russian)

* New translations activerecord.en.yml (Slovak)

* New translations activerecord.en.yml (Slovenian)

* New translations activerecord.en.yml (Albanian)

* New translations activerecord.en.yml (Serbian (Cyrillic))

* New translations activerecord.en.yml (Swedish)

* New translations activerecord.en.yml (Ukrainian)

* New translations activerecord.en.yml (Dutch)

* New translations activerecord.en.yml (Chinese Simplified)

* New translations activerecord.en.yml (Chinese Traditional)

* New translations activerecord.en.yml (Vietnamese)

* New translations activerecord.en.yml (Galician)

* New translations activerecord.en.yml (Portuguese, Brazilian)

* New translations activerecord.en.yml (Indonesian)

* New translations activerecord.en.yml (Persian)

* New translations activerecord.en.yml (Tamil)

* New translations activerecord.en.yml (Spanish, Argentina)

* New translations activerecord.en.yml (Norwegian)

* New translations activerecord.en.yml (Greek)

* New translations activerecord.en.yml (Romanian)

* New translations activerecord.en.yml (French)

* New translations activerecord.en.yml (Spanish)

* New translations activerecord.en.yml (Afrikaans)

* New translations activerecord.en.yml (Arabic)

* New translations activerecord.en.yml (Bulgarian)

* New translations activerecord.en.yml (Catalan)

* New translations activerecord.en.yml (Czech)

* New translations activerecord.en.yml (Danish)

* New translations activerecord.en.yml (German)

* New translations activerecord.en.yml (Frisian)

* New translations activerecord.en.yml (Basque)

* New translations activerecord.en.yml (Finnish)

* New translations activerecord.en.yml (Hebrew)

* New translations activerecord.en.yml (Hungarian)

* New translations activerecord.en.yml (Armenian)

* New translations activerecord.en.yml (Italian)

* New translations activerecord.en.yml (Japanese)

* New translations activerecord.en.yml (Georgian)

* New translations activerecord.en.yml (Korean)

* New translations activerecord.en.yml (Spanish, Mexico)

* New translations activerecord.en.yml (Bengali)

* New translations activerecord.en.yml (Sorani (Kurdish))

* New translations activerecord.en.yml (Asturian)

* New translations activerecord.en.yml (Occitan)

* New translations activerecord.en.yml (Serbian (Latin))

* New translations activerecord.en.yml (Kurmanji (Kurdish))

* New translations activerecord.en.yml (Corsican)

* New translations activerecord.en.yml (Breton)

* New translations activerecord.en.yml (Sardinian)

* New translations activerecord.en.yml (Kabyle)

* New translations activerecord.en.yml (Ido)

* New translations activerecord.en.yml (Sinhala)

* New translations activerecord.en.yml (Malayalam)

* New translations activerecord.en.yml (Marathi)

* New translations activerecord.en.yml (Hindi)

* New translations activerecord.en.yml (Thai)

* New translations activerecord.en.yml (Croatian)

* New translations activerecord.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Kazakh)

* New translations activerecord.en.yml (Estonian)

* New translations activerecord.en.yml (Latvian)

* New translations activerecord.en.yml (Tatar)

* New translations activerecord.en.yml (Welsh)

* New translations activerecord.en.yml (Esperanto)

* New translations activerecord.en.yml (Chinese Traditional, Hong Kong)

* New translations activerecord.en.yml (Standard Moroccan Tamazight)

* New translations activerecord.en.yml (Catalan)

* New translations activerecord.en.yml (Italian)

* New translations activerecord.en.yml (Dutch)

* New translations activerecord.en.yml (Swedish)

* New translations activerecord.en.yml (Ukrainian)

* New translations activerecord.en.yml (Latvian)

* New translations activerecord.en.yml (Icelandic)

* New translations activerecord.en.yml (Chinese Traditional)

* New translations activerecord.en.yml (Vietnamese)

* New translations activerecord.en.yml (Spanish, Argentina)

* New translations en.json (Korean)

* New translations en.yml (Korean)

* New translations simple_form.en.yml (Korean)

* New translations activerecord.en.yml (Korean)

* New translations activerecord.en.yml (Portuguese)

* New translations en.yml (Korean)

* New translations en.json (Galician)

* New translations en.yml (Galician)

* New translations activerecord.en.yml (Galician)

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-29 14:35:49 +09:00
Eugen Rochko dc5c86add7
Fix account migration form ever using outdated account data (#18429) 2022-10-29 01:31:45 +02:00
Eugen Rochko 317ec06dc7
Fix error when uploading malformed CSV import (#19509) 2022-10-28 23:30:44 +02:00
Claire 26ff48ee48 Fix domain block export not exporting blocks with only media rejection 2022-10-28 20:14:25 +02:00
Claire bbdf61c9e4 Revert Home controller test to upstream 2022-10-28 20:12:04 +02:00
Eugen Rochko 8814a1b949 [Glitch] Fix closed registrations message not appearing in web UI
Port 5fa340931e to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:49:45 +02:00
Eugen Rochko 9f6c175550 [Glitch] Fix number of uses being shown again on trending hashtags in web UI
Port 923f06a07c to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:49:45 +02:00
Claire 2cb3dd9364 [Glitch] Change admin announcement edition interface to use datetime-local
Port d9d722d74b to glitch-soc

Co-authored-by: Eugen Rochko <eugen@zeonfederated.com>
Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:49:45 +02:00
Robert Laurenz 047a2f1f1b [Glitch] fix(component): adjust style of counter button to fix overflow issue
Port 10922294ff to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:49:45 +02:00
Claire b514998dc1 Merge branch 'main' into glitch-soc/merge-upstream 2022-10-28 19:49:42 +02:00
Eugen Rochko 5fa340931e
Fix closed registrations message not appearing in web UI (#19508)
Regression from #19486
2022-10-28 19:34:22 +02:00
Claire 592147b902 Remove local settings items that make no sense anymore 2022-10-28 19:30:51 +02:00
Claire f405ad69b3 [Glitch] Remove navigation links to /explore when trends are disabled
Port 267978d4fe to glithc-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:26:28 +02:00
Eugen Rochko 89fdfb8fe6 [Glitch] Fix redirecting to /publish when compose form is visible in web UI
Port 5452af2188 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:26:28 +02:00
Eugen Rochko 80b53623e1 [Glitch] Change settings area to be separated into categories in admin UI
Port 7c152acb2c to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 58e2b0973d [Glitch] Fix media, following and followers tabs in web UI
Port 73de39e632 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko c9d3c7d63a [Glitch] Fix too many featured tags causing navigation panel scroll in web UI
Port 23d367f544 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 7bb1b917b2 [Glitch] Change featured hashtags to be displayed in navigation panel
Port aefa9253d6 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 2cea6e5564 [Glitch] Remove volume number from hashtags in web UI
Port c55219efa8 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Takeshi Umeda 8be350cc82 [Glitch] Add featured tags selector for WebUI
Port 4c7b5fb6c1 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko a2942fd0b8 [Glitch] Fix nofollow rel being removed in web UI
Port 9757c917da to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko e9ccee38a7 [Glitch] Change floating action button to be a button in header in web UI
Port 1fd6460b02 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Claire 05c1dd9114 [Glitch] Add closed registrations modal
Port 2277913f3f to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko ce27c6502b [Glitch] Fix notifications about deleted reports not being also deleted
Port d2eb726962 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 5dfb7ba35c [Glitch] Fix missing delete and redraft link in web UI
Port 371d969403 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko b36c58b99e [Glitch] Change post editing to be enabled in web UI
Port 8ebff0efcb to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 2d731dbde6 [Glitch] Add ability to view previous edits of a status in admin UI
Port f8ca3bb2a1 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Claire d9f182e5f3 [Glitch] Fix WebUI notification settings for new user and new report notifications
Port dd76bbf8b7 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko bfa47eb7d6 [Glitch] Fix language dropdown causing zoom on mobile devices in web UI
Port 3ad0a2ae3d to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 1315c149c0 [Glitch] Add error boundary around routes in web UI
Port a43a823768 to glitch-soc

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 92385da9c3 [Glitch] Fix reply not opening compose page on certain screen sizes in web UI
Port 56efa8d22f to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 7d3acb1f2c [Glitch] Fix error when rendering limited account in web UI
Port 73a48318a1 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Claire bda5040085 [Glitch] Change landing page to be /about instead of /explore when trends are disabled
Port 062b3c9090 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko f9f0949bd3 [Glitch] Fix case-sensitive look-up for profiles in web UI
Port 5e908c5a95 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 5f4f37f432 [Glitch] Fix error on profile in web UI
Port 74738b4993 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
prplecake b9195f8fb7 [Glitch] Don't use "unfollow language" when cancelling follow requests
Port 1b83040bd4 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Claire 7cfb319283 fixup! [Glitch] Fix logged-out web UI on smaller screens 2022-10-28 19:24:02 +02:00
Claire 885389d279 fixup! [Glitch] Change public accounts pages to mount the web UI 2022-10-28 19:24:02 +02:00
Claire 89e9ec8ae2 fixup! [Glitch] Fix intermediary responsive layout, accessibility on navigation in web UI 2022-10-28 19:24:02 +02:00
Eugen Rochko 9363e5c24e [Glitch] Change public accounts pages to mount the web UI
Port 839f893168 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 6013eeea4c [Glitch] Fix missing rules in report modal in web UI
Port 9c7f4ab8e8 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 2aa70c112a [Glitch] Fix error while server rules are loading in report modal in web UI
Port 4c7b5fb6c1 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi 39ec0e8398 [Glitch] Fix missing isCancel
Port e02bdc14fd to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi e301cfb463 [Glitch] Replace CancelToken to AbortSignal
Port 219c38b921 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 67b4ecdd21 [Glitch] Change about page to be mounted in the web UI
Port 1bd00036c2 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi 5d4d4a69f6 [Glitch] Redirect non-logged-in user to owner statuses on single user mode
Port 7afc6a630c to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi 1850166de9 [Glitch] Hide list panel from nav bar in mobile layout
Port d787343325 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi 1e7f819c85 [Glitch] Fix ColumnLink labels not disappearing in mobile UI
Port 3eef8a7a81 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi 492ceeceb0 [Glitch] Fix fedi/local timeline nav link always hide
Port d3f1a010e5 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko c36f28ba77 [Glitch] Fix intermediary responsive layout, accessibility on navigation in web UI
Port 0765324622 to glitch-soc

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko dea951cce8 [Glitch] Add dismissable hints to various timelines in web UI
Port f41ec9af05 to glitch-soc

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi e5720cd540 [Glitch] Add title to pages with missing title in Web UI
Port a5112b51fd to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Yamagishi Kazutoshi 8491a3532d [Glitch] Remove timeline preview link from nav panel when not signed-in
Port e82467ca41 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 07df273f37 [Glitch] Change privacy policy to be rendered in web UI, add REST API
Port a2ba011326 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko b68b96a0cc [Glitch] Add server rules to sign-up flow
Port 679274465b to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 206e9593ac [Glitch] Fix logged-out web UI on smaller screens
Port e2b561e3a5 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Eugen Rochko 14ddb85c3b [Glitch] Remove code for rendering public and hashtag timelines outside the web UI
Port 02ba9cfa35 to glitch-soc

Signed-off-by: Claire <claire.github-309c@sitedethib.com>
2022-10-28 19:24:02 +02:00
Claire 84da970d6b Fix assets compilation
Not too sure why the loader behaves differently than it previously did, though.
2022-10-28 19:24:02 +02:00
Claire cb19be67d1 Merge branch 'main' into glitch-soc/merge-upstream 2022-10-28 19:23:58 +02:00
Kangwook Lee (이강욱) dae954ef11
Fix PostgreSQL password reference for jobs (#19504) 2022-10-28 16:40:47 +02:00
Kangwook Lee (이강욱) 223e152312
Add option to enable single user mode (#19503) 2022-10-28 16:29:00 +02:00
Kangwook Lee (이강욱) 9bf6a8af82
Fix PostgreSQL password reference (#19502) 2022-10-28 16:21:58 +02:00
Eugen Rochko 923f06a07c
Fix number of uses being shown again on trending hashtags in web UI (#19484) 2022-10-28 12:56:51 +02:00
Claire d9d722d74b
Change admin announcement edition interface to use datetime-local (#18321)
* Change admin announcement edition interface to use datetime-local

* Dynamically set announcement stop date as required if start date is set, set minimum date for stop date

* Change `all_day` to not be bound to presence of time-range

* Add pattern and placeholder as minimal fallback for browsers not supporting datetime-local

* Display datetime-local inputs as local time

Co-authored-by: Eugen Rochko <eugen@zeonfederated.com>
2022-10-28 12:56:32 +02:00
Robert Laurenz 10922294ff
fix(component): adjust style of counter button to fix overflow issue (#19494) 2022-10-28 12:46:41 +02:00
Eugen Rochko 8dfe5179ee
Fix avatars not using image tags in web UI (#19488)
Fix #19483
2022-10-28 00:48:45 +02:00
Eugen Rochko 07cc201acc
Fix using wrong policy on status-related actions in admin UI (#19490) 2022-10-28 00:48:30 +02:00
Eugen Rochko 8ae0936ddd
Bump version to 4.0.0rc1 (#19473) 2022-10-28 00:26:02 +02:00
Eugen Rochko 5f733ad83a
Remove unused method searchable? on accounts (#19489)
It called the wrong methods, but nothing uses it
2022-10-27 19:30:08 +02:00
Eugen Rochko 09f04d710d
Change closed_registrations_message to message and add Markdown (#19486) 2022-10-27 19:17:48 +02:00
Eugen Rochko 371d969403
Fix missing delete and redraft link in web UI (#19485) 2022-10-27 19:17:15 +02:00
Shlee c7bab3318e
Remove duplicate HSTS headers from nginx.conf (#19018)
* Update nginx.conf

* Update nginx.conf

* Update nginx.conf
2022-10-27 16:58:49 +02:00
Eugen Rochko d7595adbf4
Add --remove-role option to tootctl accounts modify (#19477)
Fix #19152
2022-10-27 14:31:10 +02:00
Eugen Rochko 3e18e05330
Fix uncaught error when invalid date is supplied to API (#19480)
Fix #19213
2022-10-27 14:30:52 +02:00
Eugen Rochko d2eb726962
Fix notifications about deleted reports not being also deleted (#19475)
* Fix notifications about deleted reports not being also deleted

* Fix notification with empty report crashing web UI

Fix #18909
2022-10-27 02:10:54 +02:00
Eugen Rochko f6bcf86caf
Fix wrong math function used in search query (#19481) 2022-10-27 02:10:38 +02:00
zunda 52ebfb7792
Store integer settings as integer (#19478) 2022-10-26 22:14:07 +02:00
Eugen Rochko 1546538de9
Fix improperly checking for blocked domain on followed hashtags (#19472)
Fix #19469
2022-10-26 20:40:56 +02:00
Claire 2277913f3f
Add closed registrations modal (#19437) 2022-10-26 19:35:55 +02:00
prplecake aafbc82d88
Add "unsafe-eval" to script-src CSP (#18817) 2022-10-26 19:23:16 +02:00
Yamagishi Kazutoshi eebbc5439a
Disable media cache on service worker (#19471) 2022-10-26 18:21:36 +02:00
Yamagishi Kazutoshi 31e23269f9
Fix /web prefix (#19468) 2022-10-26 16:56:37 +02:00
Eugen Rochko 8ebff0efcb
Change post editing to be enabled in web UI (#19103) 2022-10-26 15:23:00 +02:00
dependabot[bot] d96fac8b93
Bump utf-8-validate from 5.0.9 to 5.0.10 (#19449)
Bumps [utf-8-validate](https://github.com/websockets/utf-8-validate) from 5.0.9 to 5.0.10.
- [Release notes](https://github.com/websockets/utf-8-validate/releases)
- [Commits](https://github.com/websockets/utf-8-validate/compare/v5.0.9...v5.0.10)

---
updated-dependencies:
- dependency-name: utf-8-validate
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 21:08:16 +09:00
dependabot[bot] 1f986d2e52
Bump @babel/plugin-proposal-decorators from 7.19.3 to 7.19.6 (#19445)
Bumps [@babel/plugin-proposal-decorators](https://github.com/babel/babel/tree/HEAD/packages/babel-plugin-proposal-decorators) from 7.19.3 to 7.19.6.
- [Release notes](https://github.com/babel/babel/releases)
- [Changelog](https://github.com/babel/babel/blob/main/CHANGELOG.md)
- [Commits](https://github.com/babel/babel/commits/v7.19.6/packages/babel-plugin-proposal-decorators)

---
updated-dependencies:
- dependency-name: "@babel/plugin-proposal-decorators"
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 21:07:47 +09:00
Eugen Rochko ca6e92fdb8
Fix warning about constants in routes (#19466) 2022-10-26 14:01:02 +02:00
dependabot[bot] 1ce17cf316
Bump jest from 29.1.2 to 29.2.2 (#19467)
Bumps [jest](https://github.com/facebook/jest/tree/HEAD/packages/jest) from 29.1.2 to 29.2.2.
- [Release notes](https://github.com/facebook/jest/releases)
- [Changelog](https://github.com/facebook/jest/blob/main/CHANGELOG.md)
- [Commits](https://github.com/facebook/jest/commits/v29.2.2/packages/jest)

---
updated-dependencies:
- dependency-name: jest
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:52:01 +09:00
Eugen Rochko f8ca3bb2a1
Add ability to view previous edits of a status in admin UI (#19462)
* Add ability to view previous edits of a status in admin UI

* Change moderator access to posts to be controlled by a separate policy
2022-10-26 13:42:29 +02:00
dependabot[bot] dee69be60e
Bump jest-environment-jsdom from 29.1.2 to 29.2.1 (#19393)
Bumps [jest-environment-jsdom](https://github.com/facebook/jest/tree/HEAD/packages/jest-environment-jsdom) from 29.1.2 to 29.2.1.
- [Release notes](https://github.com/facebook/jest/releases)
- [Changelog](https://github.com/facebook/jest/blob/main/CHANGELOG.md)
- [Commits](https://github.com/facebook/jest/commits/v29.2.1/packages/jest-environment-jsdom)

---
updated-dependencies:
- dependency-name: jest-environment-jsdom
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:16:50 +09:00
dependabot[bot] 3de6c9c02d
Bump babel-jest from 29.1.2 to 29.2.1 (#19444)
Bumps [babel-jest](https://github.com/facebook/jest/tree/HEAD/packages/babel-jest) from 29.1.2 to 29.2.1.
- [Release notes](https://github.com/facebook/jest/releases)
- [Changelog](https://github.com/facebook/jest/blob/main/CHANGELOG.md)
- [Commits](https://github.com/facebook/jest/commits/v29.2.1/packages/babel-jest)

---
updated-dependencies:
- dependency-name: babel-jest
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:16:26 +09:00
dependabot[bot] 940e80a81b
Bump ws from 8.9.0 to 8.10.0 (#19450)
Bumps [ws](https://github.com/websockets/ws) from 8.9.0 to 8.10.0.
- [Release notes](https://github.com/websockets/ws/releases)
- [Commits](https://github.com/websockets/ws/compare/8.9.0...8.10.0)

---
updated-dependencies:
- dependency-name: ws
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:15:38 +09:00
dependabot[bot] 945f44fb6e
Bump npmlog from 7.0.0 to 7.0.1 (#19447)
Bumps [npmlog](https://github.com/npm/npmlog) from 7.0.0 to 7.0.1.
- [Release notes](https://github.com/npm/npmlog/releases)
- [Changelog](https://github.com/npm/npmlog/blob/main/CHANGELOG.md)
- [Commits](https://github.com/npm/npmlog/compare/v7.0.0...v7.0.1)

---
updated-dependencies:
- dependency-name: npmlog
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:14:33 +09:00
dependabot[bot] 2015e6b331
Bump react-select from 5.5.1 to 5.5.4 (#19451)
Bumps [react-select](https://github.com/JedWatson/react-select) from 5.5.1 to 5.5.4.
- [Release notes](https://github.com/JedWatson/react-select/releases)
- [Changelog](https://github.com/JedWatson/react-select/blob/master/docs/CHANGELOG.md)
- [Commits](https://github.com/JedWatson/react-select/compare/react-select@5.5.1...react-select@5.5.4)

---
updated-dependencies:
- dependency-name: react-select
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:13:37 +09:00
dependabot[bot] 1a05258cd1
Bump eslint-plugin-promise from 6.1.0 to 6.1.1 (#19443)
Bumps [eslint-plugin-promise](https://github.com/eslint-community/eslint-plugin-promise) from 6.1.0 to 6.1.1.
- [Release notes](https://github.com/eslint-community/eslint-plugin-promise/releases)
- [Changelog](https://github.com/eslint-community/eslint-plugin-promise/blob/main/CHANGELOG.md)
- [Commits](https://github.com/eslint-community/eslint-plugin-promise/compare/v6.1.0...v6.1.1)

---
updated-dependencies:
- dependency-name: eslint-plugin-promise
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:13:05 +09:00
dependabot[bot] 89fbdcdf30
Bump @babel/plugin-transform-runtime from 7.19.1 to 7.19.6 (#19446)
Bumps [@babel/plugin-transform-runtime](https://github.com/babel/babel/tree/HEAD/packages/babel-plugin-transform-runtime) from 7.19.1 to 7.19.6.
- [Release notes](https://github.com/babel/babel/releases)
- [Changelog](https://github.com/babel/babel/blob/main/CHANGELOG.md)
- [Commits](https://github.com/babel/babel/commits/v7.19.6/packages/babel-plugin-transform-runtime)

---
updated-dependencies:
- dependency-name: "@babel/plugin-transform-runtime"
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:12:38 +09:00
dependabot[bot] 0f02e97c01
Bump @babel/core from 7.19.3 to 7.19.6 (#19448)
Bumps [@babel/core](https://github.com/babel/babel/tree/HEAD/packages/babel-core) from 7.19.3 to 7.19.6.
- [Release notes](https://github.com/babel/babel/releases)
- [Changelog](https://github.com/babel/babel/blob/main/CHANGELOG.md)
- [Commits](https://github.com/babel/babel/commits/v7.19.6/packages/babel-core)

---
updated-dependencies:
- dependency-name: "@babel/core"
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:11:55 +09:00
dependabot[bot] 54189e9fc4
Bump bufferutil from 4.0.6 to 4.0.7 (#19442)
Bumps [bufferutil](https://github.com/websockets/bufferutil) from 4.0.6 to 4.0.7.
- [Release notes](https://github.com/websockets/bufferutil/releases)
- [Commits](https://github.com/websockets/bufferutil/compare/v4.0.6...v4.0.7)

---
updated-dependencies:
- dependency-name: bufferutil
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-26 20:11:05 +09:00
Eugen Rochko 7d25f72b9f
Fix negatives values in search index causing queries to fail (#19464) 2022-10-26 13:00:43 +02:00
Eugen Rochko bf0ab3e0fa
Fix vacuum scheduler missing lock, locks never expiring (#19458)
Remove vacuuming of orphaned preview cards
2022-10-26 12:10:48 +02:00
Eugen Rochko 1ae508bf2f
Change unauthenticated search to not support pagination in REST API (#19326)
- Only exact search matches for queries with < 5 characters
- Do not support queries with `offset` (pagination)
- Return HTTP 401 on truthy `resolve` instead of overriding to false
2022-10-26 12:10:02 +02:00
Eugen Rochko 8f07381856
Revert "Remove preference to aggregate reblogs in home/list feeds (#18112)" (#19463)
This reverts commit af396fa35f.
2022-10-26 09:10:18 +02:00
Eugen Rochko 487d81fb92
Fix IP blocks not having a unique index (#19456) 2022-10-25 21:43:44 +02:00
Eugen Rochko 6f01111863
Fix wrong size of avatars in admin UI (#19457) 2022-10-25 21:43:33 +02:00
Claire 267978d4fe
Remove navigation links to /explore when trends are disabled (#19415)
* Remove navigation links to /explore when trends are disabled

* Do not display trends interface when trends are disabled
2022-10-25 19:03:16 +02:00
Eugen Rochko 0ca29eaa3f
Change layout of posts in web UI (#19423) 2022-10-25 19:02:21 +02:00
Eugen Rochko fcca781aae
Change design of translations in web UI (#19453) 2022-10-25 18:47:21 +02:00
Eugen Rochko 9757c917da
Fix nofollow rel being removed in web UI (#19455) 2022-10-25 18:47:04 +02:00
Claire 30453fab80
Add mention of the translation provider when translating a post (#19433) 2022-10-24 18:37:57 +02:00
Claire 8046cf34d6
Change “Translate” button to only show up when a translation backend is configured (#19434)
* Change “Translate” button to only show up when a translation backend is configured

Fixes #19346

* Add `translation` attribute to /api/v2/instance to expose whether the translation feature is enabled

Fixes #19328
2022-10-24 18:30:58 +02:00
Claire dd76bbf8b7
Fix WebUI notification settings for new user and new report notifications (#19436)
Due to an error in operator priority, those settings would only show up if the
user role included the all-encompassing `administrator` permission and would
display `0` otherwise.
2022-10-24 17:37:46 +02:00
Eugen Rochko 3ad0a2ae3d
Fix language dropdown causing zoom on mobile devices in web UI (#19428) 2022-10-23 23:38:20 +02:00
Eugen Rochko 73de39e632
Fix media, following and followers tabs in web UI (#19426) 2022-10-23 23:38:08 +02:00
Eugen Rochko 5452af2188
Fix redirecting to /publish when compose form is visible in web UI (#19427) 2022-10-23 23:37:58 +02:00
Eugen Rochko 3124f946ee
New Crowdin updates (#19405)
* New translations en.yml (Kazakh)

* New translations en.json (English, United Kingdom)

* New translations en.json (Estonian)

* New translations en.yml (Estonian)

* New translations en.json (Latvian)

* New translations en.yml (Latvian)

* New translations en.json (Hindi)

* New translations en.yml (Hindi)

* New translations en.json (Malay)

* New translations en.yml (Malay)

* New translations en.json (Telugu)

* New translations en.yml (Telugu)

* New translations en.yml (Occitan)

* New translations en.json (Serbian (Latin))

* New translations en.yml (Sanskrit)

* New translations en.json (Standard Moroccan Tamazight)

* New translations en.yml (Silesian)

* New translations en.json (Silesian)

* New translations en.yml (Taigi)

* New translations en.json (Taigi)

* New translations en.yml (Kabyle)

* New translations en.json (Kabyle)

* New translations en.json (Sanskrit)

* New translations en.yml (Serbian (Latin))

* New translations en.yml (Sardinian)

* New translations en.json (Sardinian)

* New translations en.yml (Corsican)

* New translations en.json (Corsican)

* New translations en.yml (Sorani (Kurdish))

* New translations en.json (Sorani (Kurdish))

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.json (Kurmanji (Kurdish))

* New translations en.yml (Standard Moroccan Tamazight)

* New translations en.json (Catalan)

* New translations en.json (Polish)

* New translations en.json (Slovenian)

* New translations en.json (Ukrainian)

* New translations en.json (Latvian)

* New translations en.json (Portuguese)

* New translations en.json (Kurmanji (Kurdish))

* New translations en.json (Hungarian)

* New translations en.json (Italian)

* New translations en.json (Greek)

* New translations en.json (Ukrainian)

* New translations en.json (Spanish, Argentina)

* New translations en.json (Ido)

* New translations en.json (Chinese Traditional)

* New translations en.json (Danish)

* New translations en.json (Japanese)

* New translations en.json (Japanese)

* New translations en.json (Galician)

* New translations en.yml (Hungarian)

* New translations en.yml (Arabic)

* New translations en.yml (Catalan)

* New translations en.yml (Danish)

* New translations en.yml (Greek)

* New translations en.yml (French)

* New translations en.yml (Basque)

* New translations en.yml (Finnish)

* New translations en.yml (Hebrew)

* New translations simple_form.en.yml (Czech)

* New translations en.yml (German)

* New translations en.yml (Czech)

* New translations en.yml (Spanish)

* New translations en.yml (Turkish)

* New translations en.yml (Albanian)

* New translations en.yml (Ukrainian)

* New translations en.yml (Ido)

* New translations en.yml (Chinese Simplified)

* New translations en.yml (Thai)

* New translations en.yml (Italian)

* New translations en.yml (Japanese)

* New translations en.yml (Georgian)

* New translations en.yml (Armenian)

* New translations en.yml (Swedish)

* New translations en.yml (Chinese Traditional)

* New translations en.yml (Vietnamese)

* New translations en.yml (Galician)

* New translations en.yml (Icelandic)

* New translations en.yml (Portuguese, Brazilian)

* New translations en.yml (Indonesian)

* New translations en.yml (Serbian (Cyrillic))

* New translations en.yml (Slovenian)

* New translations en.yml (Norwegian)

* New translations en.yml (Korean)

* New translations en.yml (Lithuanian)

* New translations en.yml (Dutch)

* New translations simple_form.en.yml (Dutch)

* New translations en.yml (Polish)

* New translations en.yml (Portuguese)

* New translations en.yml (Russian)

* New translations en.yml (Slovak)

* New translations en.yml (Persian)

* New translations en.yml (Welsh)

* New translations en.yml (Esperanto)

* New translations en.yml (Chinese Traditional, Hong Kong)

* New translations en.yml (Breton)

* New translations en.yml (Sinhala)

* New translations en.yml (Scottish Gaelic)

* New translations en.yml (Spanish, Argentina)

* New translations en.yml (Spanish, Mexico)

* New translations en.yml (Norwegian Nynorsk)

* New translations en.yml (Kazakh)

* New translations en.yml (Estonian)

* New translations en.yml (Latvian)

* New translations en.yml (Malay)

* New translations en.yml (Asturian)

* New translations simple_form.en.yml (French)

* New translations simple_form.en.yml (Basque)

* New translations simple_form.en.yml (Spanish)

* New translations simple_form.en.yml (Afrikaans)

* New translations simple_form.en.yml (Arabic)

* New translations simple_form.en.yml (Bulgarian)

* New translations simple_form.en.yml (Catalan)

* New translations simple_form.en.yml (Danish)

* New translations simple_form.en.yml (German)

* New translations simple_form.en.yml (Greek)

* New translations simple_form.en.yml (Frisian)

* New translations simple_form.en.yml (Finnish)

* New translations simple_form.en.yml (Romanian)

* New translations simple_form.en.yml (Hebrew)

* New translations simple_form.en.yml (Hungarian)

* New translations simple_form.en.yml (Armenian)

* New translations simple_form.en.yml (Italian)

* New translations simple_form.en.yml (Japanese)

* New translations simple_form.en.yml (Georgian)

* New translations simple_form.en.yml (Korean)

* New translations simple_form.en.yml (Vietnamese)

* New translations en.yml (Occitan)

* New translations en.yml (Serbian (Latin))

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.yml (Sorani (Kurdish))

* New translations en.yml (Corsican)

* New translations en.yml (Sardinian)

* New translations simple_form.en.yml (Chinese Simplified)

* New translations en.yml (Kabyle)

* New translations en.yml (Standard Moroccan Tamazight)

* New translations simple_form.en.yml (Sinhala)

* New translations simple_form.en.yml (Polish)

* New translations simple_form.en.yml (Norwegian)

* New translations simple_form.en.yml (Malayalam)

* New translations simple_form.en.yml (Welsh)

* New translations simple_form.en.yml (Esperanto)

* New translations simple_form.en.yml (Chinese Traditional, Hong Kong)

* New translations simple_form.en.yml (Tatar)

* New translations simple_form.en.yml (Breton)

* New translations simple_form.en.yml (Estonian)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Asturian)

* New translations simple_form.en.yml (Occitan)

* New translations simple_form.en.yml (Serbian (Latin))

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations simple_form.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Corsican)

* New translations simple_form.en.yml (Sardinian)

* New translations simple_form.en.yml (Latvian)

* New translations simple_form.en.yml (Kazakh)

* New translations simple_form.en.yml (Portuguese)

* New translations simple_form.en.yml (Galician)

* New translations simple_form.en.yml (Russian)

* New translations simple_form.en.yml (Slovak)

* New translations simple_form.en.yml (Slovenian)

* New translations simple_form.en.yml (Albanian)

* New translations simple_form.en.yml (Serbian (Cyrillic))

* New translations simple_form.en.yml (Swedish)

* New translations simple_form.en.yml (Turkish)

* New translations simple_form.en.yml (Ukrainian)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Icelandic)

* New translations simple_form.en.yml (Norwegian Nynorsk)

* New translations simple_form.en.yml (Portuguese, Brazilian)

* New translations simple_form.en.yml (Indonesian)

* New translations simple_form.en.yml (Persian)

* New translations simple_form.en.yml (Tamil)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Spanish, Mexico)

* New translations simple_form.en.yml (Bengali)

* New translations simple_form.en.yml (Thai)

* New translations simple_form.en.yml (Croatian)

* New translations simple_form.en.yml (Kabyle)

* New translations simple_form.en.yml (Ido)

* New translations simple_form.en.yml (Standard Moroccan Tamazight)

* New translations en.yml (Catalan)

* New translations en.yml (Greek)

* New translations en.yml (Italian)

* New translations en.yml (Polish)

* New translations simple_form.en.yml (Polish)

* New translations simple_form.en.yml (Greek)

* New translations simple_form.en.yml (Italian)

* New translations en.yml (Czech)

* New translations en.yml (Spanish)

* New translations simple_form.en.yml (Czech)

* New translations en.json (Spanish)

* New translations en.yml (Catalan)

* New translations simple_form.en.yml (Polish)

* New translations simple_form.en.yml (Spanish)

* New translations simple_form.en.yml (Catalan)

* New translations simple_form.en.yml (Italian)

* New translations en.yml (Portuguese)

* New translations en.yml (Latvian)

* New translations simple_form.en.yml (Portuguese)

* New translations en.json (Czech)

* New translations simple_form.en.yml (Czech)

* New translations en.yml (Portuguese)

* New translations en.yml (Latvian)

* New translations simple_form.en.yml (Polish)

* New translations simple_form.en.yml (Portuguese)

* New translations simple_form.en.yml (Latvian)

* New translations en.yml (Korean)

* New translations en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Hungarian)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations en.yml (Ukrainian)

* New translations en.yml (Danish)

* New translations en.json (Hungarian)

* New translations en.yml (Hungarian)

* New translations en.yml (Chinese Traditional)

* New translations en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Hungarian)

* New translations devise.en.yml (Hungarian)

* New translations doorkeeper.en.yml (Hungarian)

* New translations simple_form.en.yml (Ukrainian)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations en.yml (Ukrainian)

* New translations en.yml (Danish)

* New translations en.yml (Hungarian)

* New translations en.yml (Japanese)

* New translations simple_form.en.yml (Danish)

* New translations simple_form.en.yml (Hungarian)

* New translations simple_form.en.yml (Ukrainian)

* New translations en.yml (Hungarian)

* New translations en.yml (Japanese)

* New translations simple_form.en.yml (Ukrainian)

* New translations en.yml (Thai)

* New translations en.json (Thai)

* New translations simple_form.en.yml (Thai)

* New translations en.yml (Ido)

* New translations simple_form.en.yml (Ido)

* New translations en.yml (Ido)

* New translations simple_form.en.yml (Ido)

* New translations en.yml (Kurmanji (Kurdish))

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations en.json (Vietnamese)

* New translations en.yml (Slovenian)

* New translations simple_form.en.yml (Slovenian)

* New translations en.json (Irish)

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-24 00:46:35 +09:00
Eugen Rochko 1fd6460b02
Change floating action button to be a button in header in web UI (#19422)
- Fix theme color
- Fix elephant being too big on error page on small screens
- Remove "Follows and Followers" link from navigation panel
2022-10-23 15:58:24 +02:00
Eugen Rochko c2c14331b2
Fix PWA manifest using /web paths (#19421) 2022-10-23 14:05:18 +02:00
Eugen Rochko a43a823768
Add error boundary around routes in web UI (#19412)
* Add error boundary around routes in web UI

* Update app/javascript/mastodon/features/ui/util/react_router_helpers.js

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>

* Update app/javascript/mastodon/features/ui/util/react_router_helpers.js

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>

* Update app/javascript/mastodon/features/ui/components/bundle_column_error.js

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-22 23:18:32 +02:00
Eugen Rochko 56efa8d22f
Fix reply not opening compose page on certain screen sizes in web UI (#19417)
Fix ellipsis next to icons on navigation panel on some browsers
2022-10-22 23:15:14 +02:00
Yamagishi Kazutoshi 45d3b32488
Fix Settings::FeaturedTagsController (#19418)
Regression from #19409
2022-10-22 23:14:58 +02:00
Takeshi Umeda 74ead7d106
Change featured tag updates to add/remove activity (#19409)
* Change featured tag updates to add/remove activity

* Fix to check for the existence of feature tag

* Rename service and worker

* Merge AddHashtagSerializer with AddSerializer

* Undo removal of sidekiq_options
2022-10-22 18:30:55 +02:00
Eugen Rochko 73a48318a1
Fix error when rendering limited account in web UI (#19413) 2022-10-22 18:30:20 +02:00
Claire 062b3c9090
Change landing page to be /about instead of /explore when trends are disabled (#19414) 2022-10-22 18:09:51 +02:00
Takeshi Umeda 53e86747e4
Fix duplicate featured tags (#19403)
* Fix duplicate featured tags

* Add unique tag name validator

* Fix error message
2022-10-22 14:30:59 +02:00
Takeshi Umeda 1d34eff63f
Add featured tag add/remove activity handler (#19408) 2022-10-22 11:49:41 +02:00
Eugen Rochko 7c152acb2c
Change settings area to be separated into categories in admin UI (#19407)
And update all descriptions
2022-10-22 11:44:41 +02:00
Eugen Rochko abf6c87ee8
Fix remote account in contact account setting not being used (#19351) 2022-10-21 14:07:02 +02:00
dependabot[bot] c60f9cb865
Bump npmlog from 6.0.2 to 7.0.0 (#19376)
Bumps [npmlog](https://github.com/npm/npmlog) from 6.0.2 to 7.0.0.
- [Release notes](https://github.com/npm/npmlog/releases)
- [Changelog](https://github.com/npm/npmlog/blob/main/CHANGELOG.md)
- [Commits](https://github.com/npm/npmlog/compare/v6.0.2...v7.0.0)

---
updated-dependencies:
- dependency-name: npmlog
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-21 20:48:29 +09:00
Eugen Rochko e623c07372
New Crowdin updates (#19350)
* New translations en.yml (Danish)

* New translations en.yml (Spanish, Argentina)

* New translations en.yml (Icelandic)

* New translations en.yml (Czech)

* New translations en.json (Czech)

* New translations en.yml (Latvian)

* New translations en.yml (Polish)

* New translations en.json (Thai)

* New translations simple_form.en.yml (Thai)

* New translations en.yml (Galician)

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.yml (Thai)

* New translations en.json (Korean)

* New translations en.yml (German)

* New translations en.yml (Turkish)

* New translations en.yml (Polish)

* New translations en.yml (Scottish Gaelic)

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.json (Kabyle)

* New translations en.json (Kabyle)

* New translations en.yml (Kabyle)

* New translations doorkeeper.en.yml (Kabyle)

* New translations en.json (Scottish Gaelic)

* New translations en.json (Spanish, Mexico)

* New translations en.json (Greek)

* New translations en.json (Chinese Traditional)

* New translations en.json (Kabyle)

* New translations en.json (Czech)

* New translations en.json (Catalan)

* New translations en.json (Korean)

* New translations en.json (Ukrainian)

* New translations en.yml (Spanish)

* New translations en.json (Albanian)

* New translations en.yml (Albanian)

* New translations en.json (Spanish)

* New translations en.json (Polish)

* New translations en.json (Icelandic)

* New translations en.json (Scottish Gaelic)

* New translations en.json (Italian)

* New translations en.json (Danish)

* New translations en.json (Russian)

* New translations en.json (Slovenian)

* New translations en.yml (Slovenian)

* New translations en.json (Spanish, Argentina)

* New translations en.json (Latvian)

* New translations en.json (German)

* New translations en.json (Dutch)

* New translations en.yml (Dutch)

* New translations en.json (Dutch)

* New translations en.yml (Dutch)

* New translations simple_form.en.yml (Dutch)

* New translations en.json (Dutch)

* New translations en.yml (Dutch)

* New translations simple_form.en.yml (Dutch)

* New translations en.json (Dutch)

* New translations en.yml (Dutch)

* New translations simple_form.en.yml (Dutch)

* New translations en.yml (Ido)

* New translations en.json (Turkish)

* New translations simple_form.en.yml (Ido)

* New translations en.json (Galician)

* New translations en.json (Portuguese)

* New translations en.yml (Portuguese)

* New translations en.json (Portuguese)

* New translations en.yml (Portuguese)

* New translations en.json (Vietnamese)

* New translations en.yml (Vietnamese)

* New translations en.yml (Vietnamese)

* New translations en.json (Hebrew)

* New translations en.json (Slovak)

* New translations en.json (Korean)

* New translations en.json (Macedonian)

* New translations en.json (Norwegian)

* New translations en.json (Polish)

* New translations en.json (Portuguese)

* New translations en.json (Russian)

* New translations en.json (Slovenian)

* New translations en.json (Armenian)

* New translations en.json (Serbian (Cyrillic))

* New translations en.json (Swedish)

* New translations en.json (Turkish)

* New translations en.json (Ukrainian)

* New translations en.json (Chinese Simplified)

* New translations en.json (Chinese Traditional)

* New translations en.json (Urdu (Pakistan))

* New translations en.json (Vietnamese)

* New translations en.json (Galician)

* New translations en.json (Icelandic)

* New translations en.json (Italian)

* New translations en.json (Hungarian)

* New translations en.json (Thai)

* New translations en.json (Sinhala)

* New translations en.json (Bulgarian)

* New translations en.json (Ido)

* New translations en.json (German)

* New translations en.json (Tamil)

* New translations en.json (Esperanto)

* New translations en.json (Czech)

* New translations en.json (Dutch)

* New translations en.json (Albanian)

* New translations en.json (Japanese)

* New translations en.json (Indonesian)

* New translations en.json (Romanian)

* New translations en.json (Irish)

* New translations en.json (French)

* New translations en.json (Spanish)

* New translations en.json (Afrikaans)

* New translations en.json (Arabic)

* New translations en.json (Catalan)

* New translations en.json (Danish)

* New translations en.json (Greek)

* New translations en.json (Basque)

* New translations en.json (Finnish)

* New translations en.json (Portuguese, Brazilian)

* New translations en.json (Persian)

* New translations en.json (Kurmanji (Kurdish))

* New translations en.json (Cornish)

* New translations en.json (Scottish Gaelic)

* New translations en.json (Asturian)

* New translations en.json (Occitan)

* New translations en.json (Sorani (Kurdish))

* New translations en.json (Malayalam)

* New translations en.json (Corsican)

* New translations en.json (Sardinian)

* New translations en.json (Sanskrit)

* New translations en.json (Kabyle)

* New translations en.json (Breton)

* New translations en.json (Tatar)

* New translations en.json (Spanish, Argentina)

* New translations en.json (Estonian)

* New translations en.json (Spanish, Mexico)

* New translations en.json (Bengali)

* New translations en.json (Marathi)

* New translations en.json (Croatian)

* New translations en.json (Norwegian Nynorsk)

* New translations en.json (Kazakh)

* New translations en.json (Latvian)

* New translations en.json (Chinese Traditional, Hong Kong)

* New translations en.json (Hindi)

* New translations en.json (Malay)

* New translations en.json (Welsh)

* New translations en.json (Standard Moroccan Tamazight)

* New translations en.json (Catalan)

* New translations en.json (Danish)

* New translations en.json (Ido)

* New translations en.json (Korean)

* New translations en.json (Chinese Traditional)

* New translations en.json (Spanish, Argentina)

* New translations en.json (Ido)

* New translations en.json (Galician)

* New translations en.json (Greek)

* New translations en.json (Polish)

* New translations en.json (Ukrainian)

* New translations en.json (Italian)

* New translations en.json (Icelandic)

* New translations en.json (Turkish)

* New translations en.json (Ido)

* New translations en.json (Hungarian)

* New translations en.yml (Hungarian)

* New translations en.json (Russian)

* New translations en.yml (Russian)

* New translations en.json (Vietnamese)

* New translations simple_form.en.yml (Hungarian)

* New translations simple_form.en.yml (Russian)

* New translations en.json (Portuguese)

* New translations en.json (Latvian)

* New translations en.json (Portuguese)

* New translations en.json (Ukrainian)

* New translations en.yml (Galician)

* New translations en.yml (Greek)

* New translations en.yml (Afrikaans)

* New translations en.yml (Arabic)

* New translations en.yml (Bulgarian)

* New translations en.yml (Catalan)

* New translations en.yml (Danish)

* New translations en.yml (Basque)

* New translations en.yml (Finnish)

* New translations en.yml (Irish)

* New translations en.yml (Hebrew)

* New translations en.yml (Hungarian)

* New translations en.yml (French)

* New translations en.yml (Turkish)

* New translations en.yml (German)

* New translations en.yml (Czech)

* New translations en.yml (Chinese Simplified)

* New translations en.yml (Spanish)

* New translations en.yml (Albanian)

* New translations en.yml (Ukrainian)

* New translations en.yml (Romanian)

* New translations en.yml (Ido)

* New translations en.yml (Thai)

* New translations en.yml (Armenian)

* New translations en.yml (Russian)

* New translations en.yml (Slovak)

* New translations en.yml (Slovenian)

* New translations en.yml (Serbian (Cyrillic))

* New translations en.yml (Swedish)

* New translations en.yml (Chinese Traditional)

* New translations en.yml (Portuguese)

* New translations en.yml (Polish)

* New translations en.yml (Italian)

* New translations en.yml (Georgian)

* New translations en.yml (Korean)

* New translations en.yml (Japanese)

* New translations en.yml (Lithuanian)

* New translations en.yml (Dutch)

* New translations en.yml (Norwegian)

* New translations en.yml (Icelandic)

* New translations en.yml (Persian)

* New translations en.yml (Indonesian)

* New translations en.yml (Portuguese, Brazilian)

* New translations en.yml (Vietnamese)

* New translations en.yml (Galician)

* New translations en.yml (Tamil)

* New translations en.yml (Esperanto)

* New translations en.yml (Chinese Traditional, Hong Kong)

* New translations en.yml (Tatar)

* New translations en.yml (Malayalam)

* New translations en.yml (Breton)

* New translations en.yml (Sinhala)

* New translations en.yml (Cornish)

* New translations en.yml (Scottish Gaelic)

* New translations en.yml (Asturian)

* New translations en.yml (Welsh)

* New translations en.yml (Spanish, Argentina)

* New translations en.yml (Spanish, Mexico)

* New translations en.yml (Bengali)

* New translations en.yml (Croatian)

* New translations en.yml (Norwegian Nynorsk)

* New translations en.yml (Kazakh)

* New translations en.yml (Estonian)

* New translations en.yml (Latvian)

* New translations en.yml (Malay)

* New translations en.yml (Telugu)

* New translations en.yml (Occitan)

* New translations en.yml (Taigi)

* New translations en.yml (Kabyle)

* New translations en.yml (Serbian (Latin))

* New translations en.yml (Sardinian)

* New translations en.yml (Corsican)

* New translations en.yml (Sorani (Kurdish))

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.yml (Standard Moroccan Tamazight)

* New translations en.json (Kurmanji (Kurdish))

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

* New translations en.json (Spanish)

* Run `yarn manage:translations`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-21 20:47:56 +09:00
Takeshi Umeda 7777524145
Fix featured tag display name in setting (#19404) 2022-10-21 13:22:02 +02:00
dependabot[bot] 6faa51edc7
Bump regenerator-runtime from 0.13.9 to 0.13.10 (#19371)
Bumps [regenerator-runtime](https://github.com/facebook/regenerator) from 0.13.9 to 0.13.10.
- [Release notes](https://github.com/facebook/regenerator/releases)
- [Commits](https://github.com/facebook/regenerator/compare/regenerator-runtime@0.13.9...regenerator-runtime@0.13.10)

---
updated-dependencies:
- dependency-name: regenerator-runtime
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-21 20:09:17 +09:00
dependabot[bot] 6e1be17b61
Bump stackprof from 0.2.21 to 0.2.22 (#19367)
Bumps [stackprof](https://github.com/tmm1/stackprof) from 0.2.21 to 0.2.22.
- [Release notes](https://github.com/tmm1/stackprof/releases)
- [Changelog](https://github.com/tmm1/stackprof/blob/master/CHANGELOG.md)
- [Commits](https://github.com/tmm1/stackprof/compare/v0.2.21...v0.2.22)

---
updated-dependencies:
- dependency-name: stackprof
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-21 19:17:18 +09:00
Yamagishi Kazutoshi 94feb2b93f
Fix FetchFeaturedCollectionService spec (#19401)
Regression from #19380
2022-10-21 11:48:22 +02:00
Eugen Rochko 5e908c5a95
Fix case-sensitive look-up for profiles in web UI (#19397) 2022-10-21 10:06:03 +02:00
Eugen Rochko 23d367f544
Fix too many featured tags causing navigation panel scroll in web UI (#19398) 2022-10-21 10:05:50 +02:00
dependabot[bot] 9215ad5f19
Bump postcss from 8.4.17 to 8.4.18 (#19375)
Bumps [postcss](https://github.com/postcss/postcss) from 8.4.17 to 8.4.18.
- [Release notes](https://github.com/postcss/postcss/releases)
- [Changelog](https://github.com/postcss/postcss/blob/main/CHANGELOG.md)
- [Commits](https://github.com/postcss/postcss/compare/8.4.17...8.4.18)

---
updated-dependencies:
- dependency-name: postcss
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-21 09:17:03 +09:00
dependabot[bot] 21af674fb2
Bump axios from 1.1.2 to 1.1.3 (#19372)
Bumps [axios](https://github.com/axios/axios) from 1.1.2 to 1.1.3.
- [Release notes](https://github.com/axios/axios/releases)
- [Changelog](https://github.com/axios/axios/blob/v1.x/CHANGELOG.md)
- [Commits](https://github.com/axios/axios/compare/v1.1.2...v1.1.3)

---
updated-dependencies:
- dependency-name: axios
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-21 09:16:33 +09:00
Eugen Rochko 74738b4993
Fix error on profile in web UI (#19396) 2022-10-20 14:47:42 +02:00
Eugen Rochko 839f893168
Change public accounts pages to mount the web UI (#19319)
* Change public accounts pages to mount the web UI

* Fix handling of remote usernames in routes

- When logged in, serve web app
- When logged out, redirect to permalink
- Fix `app-body` class not being set sometimes due to name conflict

* Fix missing `multiColumn` prop

* Fix failing test

* Use `discoverable` attribute to control indexing directives

* Fix `<ColumnLoading />` not using `multiColumn`

* Add `noindex` to accounts in REST API

* Change noindex directive to not be rendered by default before a route is mounted

* Add loading indicator for detailed status in web UI

* Fix missing indicator appearing while account is loading in web UI
2022-10-20 14:35:29 +02:00
Takeshi Umeda b0e3f0312c
Add synchronization of remote featured tags (#19380)
* Add LIMIT of featured tag to instance API response

* Add featured_tags_collection_url to Account

* Add synchronization of remote featured tags

* Deliver update activity when updating featured tag

* Remove featured_tags_collection_url

* Revert "Add featured_tags_collection_url to Account"

This reverts commit cff349fc27b104ded2df6bb5665132dc24dab09c.

* Add hashtag sync from featured collections

* Fix tag name normalize

* Add target option to fetch featured collection

* Refactor fetch_featured_tags_collection_service

* Add LIMIT of featured tag to v1/instance API response
2022-10-20 09:15:52 +02:00
dependabot[bot] d19c7f4a4c
Bump eslint-plugin-react from 7.31.9 to 7.31.10 (#19370)
Bumps [eslint-plugin-react](https://github.com/jsx-eslint/eslint-plugin-react) from 7.31.9 to 7.31.10.
- [Release notes](https://github.com/jsx-eslint/eslint-plugin-react/releases)
- [Changelog](https://github.com/jsx-eslint/eslint-plugin-react/blob/master/CHANGELOG.md)
- [Commits](https://github.com/jsx-eslint/eslint-plugin-react/compare/v7.31.9...v7.31.10)

---
updated-dependencies:
- dependency-name: eslint-plugin-react
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-20 11:54:45 +09:00
dependabot[bot] 4d9a3f8ab0
Bump react-select from 5.4.0 to 5.5.1 (#19377)
Bumps [react-select](https://github.com/JedWatson/react-select) from 5.4.0 to 5.5.1.
- [Release notes](https://github.com/JedWatson/react-select/releases)
- [Changelog](https://github.com/JedWatson/react-select/blob/master/docs/CHANGELOG.md)
- [Commits](https://github.com/JedWatson/react-select/compare/react-select@5.4.0...react-select@5.5.1)

---
updated-dependencies:
- dependency-name: react-select
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-20 09:49:52 +09:00
dependabot[bot] 2792184907
Bump stylelint from 14.13.0 to 14.14.0 (#19373)
Bumps [stylelint](https://github.com/stylelint/stylelint) from 14.13.0 to 14.14.0.
- [Release notes](https://github.com/stylelint/stylelint/releases)
- [Changelog](https://github.com/stylelint/stylelint/blob/main/CHANGELOG.md)
- [Commits](https://github.com/stylelint/stylelint/compare/14.13.0...14.14.0)

---
updated-dependencies:
- dependency-name: stylelint
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-20 09:47:48 +09:00
dependabot[bot] 7d3d29c418
Bump eslint-plugin-promise from 6.0.1 to 6.1.0 (#19369)
Bumps [eslint-plugin-promise](https://github.com/eslint-community/eslint-plugin-promise) from 6.0.1 to 6.1.0.
- [Release notes](https://github.com/eslint-community/eslint-plugin-promise/releases)
- [Changelog](https://github.com/eslint-community/eslint-plugin-promise/blob/main/CHANGELOG.md)
- [Commits](https://github.com/eslint-community/eslint-plugin-promise/compare/v6.0.1...v6.1.0)

---
updated-dependencies:
- dependency-name: eslint-plugin-promise
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-20 09:47:06 +09:00
Eugen Rochko aefa9253d6
Change featured hashtags to be displayed in navigation panel (#19382) 2022-10-19 11:30:59 +02:00
prplecake 1b83040bd4
Don't use "unfollow language" when cancelling follow requests (#19363)
* Don't use "unfollow language" when cancelling follow requests

- Adds two new i18n keys: `confirmations.cancel_follow_request.confirm`
  and `confirmations.cancel_follow_request.message`
- Update the header container to use new language

* "Withdraw follow request" instead of "cancel follow request"
2022-10-19 00:12:55 +02:00
Eugen Rochko 4adb267f91
Fix showing translate button when status has no language in web UI (#19388) 2022-10-18 21:21:20 +02:00
Eugen Rochko 9c7f4ab8e8
Fix missing rules in report modal in web UI (#19387) 2022-10-18 19:33:11 +02:00
Eugen Rochko dd5d99f83f
Fix error on migration page (#19386) 2022-10-18 19:01:59 +02:00
Eugen Rochko 8a1d10cb35
Fix error while server rules are loading in report modal in web UI (#19385) 2022-10-18 18:57:01 +02:00
Yamagishi Kazutoshi 3702afec9f
Add detailed description section to issue template (#19365) 2022-10-17 08:32:48 +02:00
Takeshi Umeda 4c7b5fb6c1
Add featured tags selector for WebUI (#19358)
* Add featured tags selector for WebUI

* Add title to tag count
2022-10-16 08:43:59 +02:00
prplecake c618d3a0a5
Make "No $entity selected" errors more accurate (#19356)
Previously all controllers would use the single "No accounts changed as
none were selected" message. This commit changes them to read "tags",
"posts", "emojis", etc. where necessary.
2022-10-15 00:20:54 +02:00
Yamagishi Kazutoshi e02bdc14fd
Fix missing isCancel (#19354) 2022-10-14 16:14:22 +02:00
Yamagishi Kazutoshi 219c38b921
Replace CancelToken to AbortSignal (#19352) 2022-10-14 03:16:37 +02:00
Eugen Rochko f01310dadb
Fix trending statuses returning more than one post by the same author (#19349) 2022-10-14 01:44:23 +02:00
Eugen Rochko 8a9d774a84
New Crowdin updates (#19344)
* New translations simple_form.en.yml (Norwegian)

* New translations activerecord.en.yml (Korean)

* New translations devise.en.yml (Korean)

* New translations doorkeeper.en.yml (Korean)

* New translations devise.en.yml (Dutch)

* New translations doorkeeper.en.yml (Dutch)

* New translations activerecord.en.yml (Norwegian)

* New translations devise.en.yml (Norwegian)

* New translations doorkeeper.en.yml (Norwegian)

* New translations activerecord.en.yml (Slovenian)

* New translations devise.en.yml (Slovenian)

* New translations devise.en.yml (Galician)

* New translations doorkeeper.en.yml (Chinese Traditional)

* New translations devise.en.yml (Urdu (Pakistan))

* New translations activerecord.en.yml (Vietnamese)

* New translations devise.en.yml (Vietnamese)

* New translations doorkeeper.en.yml (Vietnamese)

* New translations doorkeeper.en.yml (Galician)

* New translations activerecord.en.yml (Chinese Traditional)

* New translations activerecord.en.yml (Icelandic)

* New translations devise.en.yml (Icelandic)

* New translations doorkeeper.en.yml (Icelandic)

* New translations simple_form.en.yml (Portuguese, Brazilian)

* New translations activerecord.en.yml (Portuguese, Brazilian)

* New translations devise.en.yml (Portuguese, Brazilian)

* New translations doorkeeper.en.yml (Portuguese, Brazilian)

* New translations simple_form.en.yml (Indonesian)

* New translations activerecord.en.yml (Indonesian)

* New translations devise.en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations doorkeeper.en.yml (Slovenian)

* New translations devise.en.yml (Swedish)

* New translations simple_form.en.yml (Albanian)

* New translations activerecord.en.yml (Albanian)

* New translations devise.en.yml (Albanian)

* New translations doorkeeper.en.yml (Albanian)

* New translations simple_form.en.yml (Serbian (Cyrillic))

* New translations activerecord.en.yml (Serbian (Cyrillic))

* New translations devise.en.yml (Serbian (Cyrillic))

* New translations doorkeeper.en.yml (Serbian (Cyrillic))

* New translations simple_form.en.yml (Swedish)

* New translations activerecord.en.yml (Swedish)

* New translations doorkeeper.en.yml (Swedish)

* New translations doorkeeper.en.yml (Chinese Simplified)

* New translations simple_form.en.yml (Turkish)

* New translations activerecord.en.yml (Turkish)

* New translations devise.en.yml (Turkish)

* New translations doorkeeper.en.yml (Turkish)

* New translations simple_form.en.yml (Ukrainian)

* New translations activerecord.en.yml (Ukrainian)

* New translations devise.en.yml (Ukrainian)

* New translations doorkeeper.en.yml (Ukrainian)

* New translations activerecord.en.yml (Chinese Simplified)

* New translations devise.en.yml (Chinese Simplified)

* New translations devise.en.yml (Indonesian)

* New translations doorkeeper.en.yml (Indonesian)

* New translations simple_form.en.yml (Kazakh)

* New translations doorkeeper.en.yml (Thai)

* New translations simple_form.en.yml (Croatian)

* New translations activerecord.en.yml (Croatian)

* New translations devise.en.yml (Croatian)

* New translations doorkeeper.en.yml (Croatian)

* New translations simple_form.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Norwegian Nynorsk)

* New translations devise.en.yml (Norwegian Nynorsk)

* New translations doorkeeper.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Kazakh)

* New translations activerecord.en.yml (Thai)

* New translations devise.en.yml (Kazakh)

* New translations doorkeeper.en.yml (Kazakh)

* New translations simple_form.en.yml (Estonian)

* New translations activerecord.en.yml (Estonian)

* New translations devise.en.yml (Estonian)

* New translations doorkeeper.en.yml (Estonian)

* New translations simple_form.en.yml (Latvian)

* New translations activerecord.en.yml (Latvian)

* New translations devise.en.yml (Latvian)

* New translations doorkeeper.en.yml (Latvian)

* New translations devise.en.yml (Thai)

* New translations simple_form.en.yml (Thai)

* New translations simple_form.en.yml (Persian)

* New translations doorkeeper.en.yml (Spanish, Argentina)

* New translations activerecord.en.yml (Persian)

* New translations devise.en.yml (Persian)

* New translations doorkeeper.en.yml (Persian)

* New translations simple_form.en.yml (Tamil)

* New translations activerecord.en.yml (Tamil)

* New translations devise.en.yml (Tamil)

* New translations doorkeeper.en.yml (Tamil)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations activerecord.en.yml (Spanish, Argentina)

* New translations devise.en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Marathi)

* New translations activerecord.en.yml (Spanish, Mexico)

* New translations devise.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Spanish, Mexico)

* New translations simple_form.en.yml (Bengali)

* New translations activerecord.en.yml (Bengali)

* New translations devise.en.yml (Bengali)

* New translations activerecord.en.yml (Marathi)

* New translations activerecord.en.yml (Hindi)

* New translations devise.en.yml (Malayalam)

* New translations activerecord.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Chinese Traditional, Hong Kong)

* New translations doorkeeper.en.yml (Chinese Traditional, Hong Kong)

* New translations simple_form.en.yml (Tatar)

* New translations activerecord.en.yml (Tatar)

* New translations devise.en.yml (Tatar)

* New translations doorkeeper.en.yml (Tatar)

* New translations simple_form.en.yml (Malayalam)

* New translations activerecord.en.yml (Malayalam)

* New translations doorkeeper.en.yml (Malayalam)

* New translations simple_form.en.yml (Breton)

* New translations activerecord.en.yml (Breton)

* New translations devise.en.yml (Breton)

* New translations doorkeeper.en.yml (Breton)

* New translations simple_form.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Hindi)

* New translations doorkeeper.en.yml (Hindi)

* New translations simple_form.en.yml (Welsh)

* New translations activerecord.en.yml (Welsh)

* New translations devise.en.yml (Welsh)

* New translations doorkeeper.en.yml (Welsh)

* New translations simple_form.en.yml (Esperanto)

* New translations activerecord.en.yml (Esperanto)

* New translations devise.en.yml (Esperanto)

* New translations doorkeeper.en.yml (Esperanto)

* New translations simple_form.en.yml (Corsican)

* New translations activerecord.en.yml (Corsican)

* New translations devise.en.yml (Corsican)

* New translations doorkeeper.en.yml (Corsican)

* New translations simple_form.en.yml (Sardinian)

* New translations activerecord.en.yml (Sardinian)

* New translations devise.en.yml (Sardinian)

* New translations doorkeeper.en.yml (Sardinian)

* New translations devise.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Kabyle)

* New translations activerecord.en.yml (Kabyle)

* New translations devise.en.yml (Kabyle)

* New translations doorkeeper.en.yml (Kabyle)

* New translations simple_form.en.yml (Ido)

* New translations activerecord.en.yml (Ido)

* New translations devise.en.yml (Ido)

* New translations doorkeeper.en.yml (Ido)

* New translations doorkeeper.en.yml (Sorani (Kurdish))

* New translations activerecord.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Occitan)

* New translations devise.en.yml (Kannada)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations activerecord.en.yml (Scottish Gaelic)

* New translations devise.en.yml (Scottish Gaelic)

* New translations doorkeeper.en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Asturian)

* New translations activerecord.en.yml (Asturian)

* New translations devise.en.yml (Asturian)

* New translations doorkeeper.en.yml (Asturian)

* New translations activerecord.en.yml (Occitan)

* New translations simple_form.en.yml (Sorani (Kurdish))

* New translations devise.en.yml (Occitan)

* New translations doorkeeper.en.yml (Occitan)

* New translations simple_form.en.yml (Serbian (Latin))

* New translations activerecord.en.yml (Serbian (Latin))

* New translations devise.en.yml (Serbian (Latin))

* New translations doorkeeper.en.yml (Serbian (Latin))

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations activerecord.en.yml (Kurmanji (Kurdish))

* New translations devise.en.yml (Kurmanji (Kurdish))

* New translations doorkeeper.en.yml (Kurmanji (Kurdish))

* New translations simple_form.en.yml (Standard Moroccan Tamazight)

* New translations activerecord.en.yml (Standard Moroccan Tamazight)

* New translations devise.en.yml (Standard Moroccan Tamazight)

* New translations doorkeeper.en.yml (Standard Moroccan Tamazight)

* New translations en.yml (Hungarian)

* New translations en.yml (Arabic)

* New translations en.yml (Bulgarian)

* New translations en.yml (Catalan)

* New translations en.yml (Danish)

* New translations en.yml (Greek)

* New translations en.yml (French)

* New translations en.yml (Basque)

* New translations en.yml (Finnish)

* New translations en.yml (Irish)

* New translations en.yml (Hebrew)

* New translations en.yml (German)

* New translations en.yml (Czech)

* New translations en.yml (Romanian)

* New translations en.yml (Spanish)

* New translations en.yml (Albanian)

* New translations en.yml (Turkish)

* New translations en.yml (Ukrainian)

* New translations en.yml (Ido)

* New translations en.yml (Chinese Simplified)

* New translations en.yml (Thai)

* New translations en.yml (Swedish)

* New translations en.yml (Serbian (Cyrillic))

* New translations en.yml (Slovenian)

* New translations en.yml (Armenian)

* New translations en.yml (Russian)

* New translations en.yml (Portuguese)

* New translations en.yml (Polish)

* New translations en.yml (Slovak)

* New translations en.yml (Norwegian)

* New translations en.yml (Italian)

* New translations en.yml (Japanese)

* New translations en.yml (Georgian)

* New translations en.yml (Korean)

* New translations en.yml (Lithuanian)

* New translations en.yml (Dutch)

* New translations en.yml (Indonesian)

* New translations en.yml (Portuguese, Brazilian)

* New translations en.yml (Icelandic)

* New translations en.yml (Galician)

* New translations en.yml (Vietnamese)

* New translations en.yml (Chinese Traditional)

* New translations en.yml (Persian)

* New translations en.yml (Tamil)

* New translations en.yml (Malayalam)

* New translations en.yml (Welsh)

* New translations en.yml (Esperanto)

* New translations en.yml (Chinese Traditional, Hong Kong)

* New translations en.yml (Tatar)

* New translations en.yml (Breton)

* New translations en.yml (Sinhala)

* New translations en.yml (Cornish)

* New translations en.yml (Scottish Gaelic)

* New translations en.yml (Asturian)

* New translations en.yml (Norwegian Nynorsk)

* New translations en.yml (Spanish, Argentina)

* New translations en.yml (Spanish, Mexico)

* New translations en.yml (Bengali)

* New translations en.yml (Croatian)

* New translations en.yml (Telugu)

* New translations en.yml (Kazakh)

* New translations en.yml (Estonian)

* New translations en.yml (Latvian)

* New translations en.yml (Hindi)

* New translations en.yml (Malay)

* New translations en.yml (Sardinian)

* New translations en.yml (Serbian (Latin))

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.yml (Sorani (Kurdish))

* New translations en.yml (Corsican)

* New translations en.yml (Kabyle)

* New translations en.yml (Taigi)

* New translations en.yml (Standard Moroccan Tamazight)

* New translations en.yml (Occitan)

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-13 23:14:11 +09:00
Eugen Rochko 1bd00036c2
Change about page to be mounted in the web UI (#19345) 2022-10-13 14:42:37 +02:00
Eugen Rochko b04633a961
Add image processing and generate blurhash for server thumbnail (#19348)
Remove separate server hero setting
2022-10-13 11:29:19 +02:00
Yamagishi Kazutoshi 7afc6a630c
Redirect non-logged-in user to owner statuses on single user mode (#19333) 2022-10-12 21:07:30 +02:00
dependabot[bot] 5f6c0d63e3
Bump axios from 0.27.2 to 1.1.2 (#19341)
Bumps [axios](https://github.com/axios/axios) from 0.27.2 to 1.1.2.
- [Release notes](https://github.com/axios/axios/releases)
- [Changelog](https://github.com/axios/axios/blob/v1.x/CHANGELOG.md)
- [Commits](https://github.com/axios/axios/compare/v0.27.2...v1.1.2)

---
updated-dependencies:
- dependency-name: axios
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-12 06:30:38 +09:00
dependabot[bot] de345e70d8
Bump express from 4.18.1 to 4.18.2 (#19340)
Bumps [express](https://github.com/expressjs/express) from 4.18.1 to 4.18.2.
- [Release notes](https://github.com/expressjs/express/releases)
- [Changelog](https://github.com/expressjs/express/blob/master/History.md)
- [Commits](https://github.com/expressjs/express/compare/4.18.1...4.18.2)

---
updated-dependencies:
- dependency-name: express
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-11 19:46:58 +09:00
dependabot[bot] 7f036be169
Bump eslint-plugin-react from 7.31.8 to 7.31.9 (#19342)
Bumps [eslint-plugin-react](https://github.com/jsx-eslint/eslint-plugin-react) from 7.31.8 to 7.31.9.
- [Release notes](https://github.com/jsx-eslint/eslint-plugin-react/releases)
- [Changelog](https://github.com/jsx-eslint/eslint-plugin-react/blob/master/CHANGELOG.md)
- [Commits](https://github.com/jsx-eslint/eslint-plugin-react/compare/v7.31.8...v7.31.9)

---
updated-dependencies:
- dependency-name: eslint-plugin-react
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-11 19:46:28 +09:00
dependabot[bot] d868c1ced5
Bump @babel/preset-env from 7.19.3 to 7.19.4 (#19339)
Bumps [@babel/preset-env](https://github.com/babel/babel/tree/HEAD/packages/babel-preset-env) from 7.19.3 to 7.19.4.
- [Release notes](https://github.com/babel/babel/releases)
- [Changelog](https://github.com/babel/babel/blob/main/CHANGELOG.md)
- [Commits](https://github.com/babel/babel/commits/v7.19.4/packages/babel-preset-env)

---
updated-dependencies:
- dependency-name: "@babel/preset-env"
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-11 19:46:03 +09:00
dependabot[bot] adf6fdf0a9
Bump @babel/runtime from 7.19.0 to 7.19.4 (#19343)
Bumps [@babel/runtime](https://github.com/babel/babel/tree/HEAD/packages/babel-runtime) from 7.19.0 to 7.19.4.
- [Release notes](https://github.com/babel/babel/releases)
- [Changelog](https://github.com/babel/babel/blob/main/CHANGELOG.md)
- [Commits](https://github.com/babel/babel/commits/v7.19.4/packages/babel-runtime)

---
updated-dependencies:
- dependency-name: "@babel/runtime"
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-11 19:45:39 +09:00
Eugen Rochko c70bffd89f
New Crowdin updates (#19330)
* New translations doorkeeper.en.yml (Afrikaans)

* New translations simple_form.en.yml (Arabic)

* New translations activerecord.en.yml (Arabic)

* New translations doorkeeper.en.yml (Arabic)

* New translations simple_form.en.yml (Bulgarian)

* New translations activerecord.en.yml (Bulgarian)

* New translations doorkeeper.en.yml (Bulgarian)

* New translations simple_form.en.yml (Catalan)

* New translations activerecord.en.yml (Catalan)

* New translations simple_form.en.yml (Chinese Simplified)

* New translations simple_form.en.yml (Vietnamese)

* New translations activerecord.en.yml (Dutch)

* New translations en.yml (Asturian)

* New translations en.yml (Sardinian)

* New translations en.yml (Occitan)

* New translations en.yml (Serbian (Latin))

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.yml (Sorani (Kurdish))

* New translations en.yml (Corsican)

* New translations activerecord.en.yml (Galician)

* New translations en.yml (Sanskrit)

* New translations en.yml (Kabyle)

* New translations en.yml (Taigi)

* New translations en.yml (Silesian)

* New translations en.yml (Standard Moroccan Tamazight)

* New translations simple_form.en.yml (Sinhala)

* New translations simple_form.en.yml (Polish)

* New translations doorkeeper.en.yml (Czech)

* New translations simple_form.en.yml (Basque)

* New translations simple_form.en.yml (Danish)

* New translations activerecord.en.yml (Hebrew)

* New translations simple_form.en.yml (Hebrew)

* New translations activerecord.en.yml (Finnish)

* New translations simple_form.en.yml (Finnish)

* New translations doorkeeper.en.yml (Basque)

* New translations activerecord.en.yml (Basque)

* New translations doorkeeper.en.yml (Finnish)

* New translations doorkeeper.en.yml (Frisian)

* New translations simple_form.en.yml (Frisian)

* New translations doorkeeper.en.yml (Greek)

* New translations activerecord.en.yml (Greek)

* New translations simple_form.en.yml (Greek)

* New translations doorkeeper.en.yml (German)

* New translations activerecord.en.yml (German)

* New translations simple_form.en.yml (German)

* New translations doorkeeper.en.yml (Danish)

* New translations activerecord.en.yml (Frisian)

* New translations activerecord.en.yml (Danish)

* New translations doorkeeper.en.yml (Georgian)

* New translations simple_form.en.yml (Korean)

* New translations activerecord.en.yml (Korean)

* New translations doorkeeper.en.yml (Korean)

* New translations simple_form.en.yml (Georgian)

* New translations activerecord.en.yml (Georgian)

* New translations simple_form.en.yml (Hungarian)

* New translations doorkeeper.en.yml (Japanese)

* New translations activerecord.en.yml (Japanese)

* New translations simple_form.en.yml (Japanese)

* New translations doorkeeper.en.yml (Italian)

* New translations activerecord.en.yml (Italian)

* New translations simple_form.en.yml (Italian)

* New translations doorkeeper.en.yml (Armenian)

* New translations activerecord.en.yml (Armenian)

* New translations simple_form.en.yml (Armenian)

* New translations doorkeeper.en.yml (Hungarian)

* New translations activerecord.en.yml (Hungarian)

* New translations doorkeeper.en.yml (Hebrew)

* New translations doorkeeper.en.yml (Dutch)

* New translations simple_form.en.yml (Norwegian)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations doorkeeper.en.yml (Swedish)

* New translations simple_form.en.yml (Turkish)

* New translations activerecord.en.yml (Turkish)

* New translations doorkeeper.en.yml (Turkish)

* New translations simple_form.en.yml (Ukrainian)

* New translations activerecord.en.yml (Ukrainian)

* New translations doorkeeper.en.yml (Ukrainian)

* New translations activerecord.en.yml (Chinese Simplified)

* New translations doorkeeper.en.yml (Chinese Simplified)

* New translations activerecord.en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Swedish)

* New translations doorkeeper.en.yml (Chinese Traditional)

* New translations activerecord.en.yml (Vietnamese)

* New translations doorkeeper.en.yml (Vietnamese)

* New translations simple_form.en.yml (Galician)

* New translations doorkeeper.en.yml (Galician)

* New translations simple_form.en.yml (Icelandic)

* New translations activerecord.en.yml (Icelandic)

* New translations activerecord.en.yml (Swedish)

* New translations doorkeeper.en.yml (Serbian (Cyrillic))

* New translations activerecord.en.yml (Norwegian)

* New translations activerecord.en.yml (Russian)

* New translations doorkeeper.en.yml (Norwegian)

* New translations activerecord.en.yml (Polish)

* New translations doorkeeper.en.yml (Polish)

* New translations simple_form.en.yml (Portuguese)

* New translations activerecord.en.yml (Portuguese)

* New translations doorkeeper.en.yml (Portuguese)

* New translations simple_form.en.yml (Russian)

* New translations doorkeeper.en.yml (Russian)

* New translations activerecord.en.yml (Serbian (Cyrillic))

* New translations simple_form.en.yml (Slovak)

* New translations activerecord.en.yml (Slovak)

* New translations doorkeeper.en.yml (Slovak)

* New translations simple_form.en.yml (Slovenian)

* New translations activerecord.en.yml (Slovenian)

* New translations doorkeeper.en.yml (Slovenian)

* New translations simple_form.en.yml (Albanian)

* New translations activerecord.en.yml (Albanian)

* New translations doorkeeper.en.yml (Albanian)

* New translations simple_form.en.yml (Serbian (Cyrillic))

* New translations doorkeeper.en.yml (Icelandic)

* New translations simple_form.en.yml (Portuguese, Brazilian)

* New translations activerecord.en.yml (Estonian)

* New translations activerecord.en.yml (Croatian)

* New translations doorkeeper.en.yml (Croatian)

* New translations simple_form.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Norwegian Nynorsk)

* New translations doorkeeper.en.yml (Norwegian Nynorsk)

* New translations simple_form.en.yml (Kazakh)

* New translations activerecord.en.yml (Kazakh)

* New translations doorkeeper.en.yml (Kazakh)

* New translations simple_form.en.yml (Estonian)

* New translations doorkeeper.en.yml (Estonian)

* New translations doorkeeper.en.yml (Thai)

* New translations simple_form.en.yml (Latvian)

* New translations activerecord.en.yml (Latvian)

* New translations doorkeeper.en.yml (Latvian)

* New translations activerecord.en.yml (Hindi)

* New translations doorkeeper.en.yml (Hindi)

* New translations simple_form.en.yml (Croatian)

* New translations activerecord.en.yml (Thai)

* New translations activerecord.en.yml (Portuguese, Brazilian)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations doorkeeper.en.yml (Portuguese, Brazilian)

* New translations simple_form.en.yml (Indonesian)

* New translations activerecord.en.yml (Indonesian)

* New translations doorkeeper.en.yml (Indonesian)

* New translations simple_form.en.yml (Persian)

* New translations activerecord.en.yml (Persian)

* New translations doorkeeper.en.yml (Persian)

* New translations simple_form.en.yml (Tamil)

* New translations activerecord.en.yml (Tamil)

* New translations doorkeeper.en.yml (Tamil)

* New translations activerecord.en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Thai)

* New translations doorkeeper.en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Spanish, Mexico)

* New translations activerecord.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Spanish, Mexico)

* New translations simple_form.en.yml (Bengali)

* New translations activerecord.en.yml (Bengali)

* New translations activerecord.en.yml (Marathi)

* New translations doorkeeper.en.yml (Marathi)

* New translations activerecord.en.yml (Asturian)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations activerecord.en.yml (Scottish Gaelic)

* New translations doorkeeper.en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Asturian)

* New translations doorkeeper.en.yml (Asturian)

* New translations doorkeeper.en.yml (Sinhala)

* New translations simple_form.en.yml (Occitan)

* New translations activerecord.en.yml (Occitan)

* New translations doorkeeper.en.yml (Occitan)

* New translations simple_form.en.yml (Serbian (Latin))

* New translations activerecord.en.yml (Serbian (Latin))

* New translations doorkeeper.en.yml (Serbian (Latin))

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations activerecord.en.yml (Kurmanji (Kurdish))

* New translations doorkeeper.en.yml (Kurmanji (Kurdish))

* New translations simple_form.en.yml (Sorani (Kurdish))

* New translations activerecord.en.yml (Sinhala)

* New translations simple_form.en.yml (Welsh)

* New translations activerecord.en.yml (Welsh)

* New translations doorkeeper.en.yml (Welsh)

* New translations simple_form.en.yml (Esperanto)

* New translations activerecord.en.yml (Esperanto)

* New translations doorkeeper.en.yml (Esperanto)

* New translations simple_form.en.yml (Chinese Traditional, Hong Kong)

* New translations doorkeeper.en.yml (Breton)

* New translations activerecord.en.yml (Chinese Traditional, Hong Kong)

* New translations doorkeeper.en.yml (Chinese Traditional, Hong Kong)

* New translations simple_form.en.yml (Tatar)

* New translations activerecord.en.yml (Tatar)

* New translations doorkeeper.en.yml (Tatar)

* New translations simple_form.en.yml (Malayalam)

* New translations activerecord.en.yml (Malayalam)

* New translations doorkeeper.en.yml (Malayalam)

* New translations simple_form.en.yml (Breton)

* New translations activerecord.en.yml (Breton)

* New translations activerecord.en.yml (Sorani (Kurdish))

* New translations doorkeeper.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Ido)

* New translations activerecord.en.yml (Standard Moroccan Tamazight)

* New translations simple_form.en.yml (Standard Moroccan Tamazight)

* New translations doorkeeper.en.yml (Ido)

* New translations activerecord.en.yml (Ido)

* New translations doorkeeper.en.yml (Kabyle)

* New translations simple_form.en.yml (Corsican)

* New translations activerecord.en.yml (Kabyle)

* New translations simple_form.en.yml (Kabyle)

* New translations doorkeeper.en.yml (Sardinian)

* New translations activerecord.en.yml (Sardinian)

* New translations simple_form.en.yml (Sardinian)

* New translations doorkeeper.en.yml (Corsican)

* New translations activerecord.en.yml (Corsican)

* New translations doorkeeper.en.yml (Standard Moroccan Tamazight)

* New translations en.json (Japanese)

* New translations en.yml (Japanese)

* New translations simple_form.en.yml (Japanese)

* New translations activerecord.en.yml (Japanese)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations en.json (Turkish)

* New translations simple_form.en.yml (Turkish)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations en.json (Vietnamese)

* New translations simple_form.en.yml (Latvian)

* New translations simple_form.en.yml (Polish)

* New translations simple_form.en.yml (Catalan)

* New translations simple_form.en.yml (Slovenian)

* New translations simple_form.en.yml (Ukrainian)

* New translations en.json (Czech)

* New translations simple_form.en.yml (Czech)

* New translations en.json (Albanian)

* New translations en.yml (Albanian)

* New translations simple_form.en.yml (Albanian)

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations en.json (Portuguese)

* New translations en.yml (Portuguese)

* New translations en.yml (Ukrainian)

* New translations en.json (Portuguese)

* New translations en.json (Vietnamese)

* New translations simple_form.en.yml (Portuguese)

* New translations simple_form.en.yml (Ukrainian)

* New translations en.json (Vietnamese)

* New translations simple_form.en.yml (Danish)

* New translations en.json (Japanese)

* New translations en.json (Hungarian)

* New translations en.yml (Japanese)

* New translations simple_form.en.yml (Hungarian)

* New translations simple_form.en.yml (Italian)

* New translations en.json (German)

* New translations en.json (German)

* New translations en.json (Spanish)

* New translations simple_form.en.yml (Spanish)

* New translations en.json (Galician)

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-11 12:59:29 +09:00
Yamagishi Kazutoshi d787343325
Hide list panel from nav bar in mobile layout (#19337) 2022-10-10 21:41:25 +02:00
Yamagishi Kazutoshi 05148e2c77
Fix missing skip_review? (#19335) 2022-10-10 08:03:19 +02:00
Yamagishi Kazutoshi 3eef8a7a81
Fix ColumnLink labels not disappearing in mobile UI (#19334) 2022-10-10 06:51:16 +02:00
Jeremy Kescher 5f79200a5e
Remove/update old "tootsuite" references, except those needed for Docker (#19327) 2022-10-10 00:33:38 +02:00
Yamagishi Kazutoshi 32c3bd3c53
Use pep440 for Docker image tag rules (#19332) 2022-10-10 00:32:40 +02:00
Yamagishi Kazutoshi d3f1a010e5
Fix fedi/local timeline nav link always hide (#19329) 2022-10-09 19:26:14 +02:00
Eugen Rochko f879c42747
New Crowdin updates (#19317)
* New translations activerecord.en.yml (Catalan)

* New translations devise.en.yml (Catalan)

* New translations doorkeeper.en.yml (Catalan)

* New translations devise.en.yml (Czech)

* New translations doorkeeper.en.yml (Czech)

* New translations simple_form.en.yml (Danish)

* New translations activerecord.en.yml (Danish)

* New translations devise.en.yml (Danish)

* New translations simple_form.en.yml (German)

* New translations doorkeeper.en.yml (Frisian)

* New translations activerecord.en.yml (German)

* New translations devise.en.yml (German)

* New translations doorkeeper.en.yml (German)

* New translations simple_form.en.yml (Greek)

* New translations activerecord.en.yml (Greek)

* New translations devise.en.yml (Greek)

* New translations doorkeeper.en.yml (Greek)

* New translations simple_form.en.yml (Frisian)

* New translations activerecord.en.yml (Frisian)

* New translations devise.en.yml (Frisian)

* New translations simple_form.en.yml (Italian)

* New translations activerecord.en.yml (Italian)

* New translations devise.en.yml (Italian)

* New translations doorkeeper.en.yml (Italian)

* New translations activerecord.en.yml (Portuguese)

* New translations doorkeeper.en.yml (Norwegian)

* New translations activerecord.en.yml (Polish)

* New translations devise.en.yml (Polish)

* New translations doorkeeper.en.yml (Polish)

* New translations simple_form.en.yml (Portuguese)

* New translations devise.en.yml (Portuguese)

* New translations simple_form.en.yml (Slovenian)

* New translations devise.en.yml (Norwegian)

* New translations simple_form.en.yml (Russian)

* New translations activerecord.en.yml (Russian)

* New translations devise.en.yml (Russian)

* New translations doorkeeper.en.yml (Russian)

* New translations simple_form.en.yml (Slovak)

* New translations activerecord.en.yml (Slovak)

* New translations devise.en.yml (Slovak)

* New translations doorkeeper.en.yml (Slovak)

* New translations doorkeeper.en.yml (Portuguese)

* New translations simple_form.en.yml (Norwegian)

* New translations activerecord.en.yml (Norwegian)

* New translations devise.en.yml (Korean)

* New translations activerecord.en.yml (Japanese)

* New translations devise.en.yml (Japanese)

* New translations doorkeeper.en.yml (Japanese)

* New translations simple_form.en.yml (Georgian)

* New translations activerecord.en.yml (Georgian)

* New translations devise.en.yml (Georgian)

* New translations doorkeeper.en.yml (Georgian)

* New translations simple_form.en.yml (Korean)

* New translations activerecord.en.yml (Korean)

* New translations doorkeeper.en.yml (Korean)

* New translations doorkeeper.en.yml (Dutch)

* New translations devise.en.yml (Dutch)

* New translations activerecord.en.yml (Slovenian)

* New translations devise.en.yml (Slovenian)

* New translations devise.en.yml (Galician)

* New translations doorkeeper.en.yml (Chinese Traditional)

* New translations devise.en.yml (Urdu (Pakistan))

* New translations activerecord.en.yml (Vietnamese)

* New translations devise.en.yml (Vietnamese)

* New translations doorkeeper.en.yml (Vietnamese)

* New translations simple_form.en.yml (Galician)

* New translations doorkeeper.en.yml (Galician)

* New translations activerecord.en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Icelandic)

* New translations activerecord.en.yml (Icelandic)

* New translations devise.en.yml (Icelandic)

* New translations doorkeeper.en.yml (Icelandic)

* New translations simple_form.en.yml (Portuguese, Brazilian)

* New translations activerecord.en.yml (Portuguese, Brazilian)

* New translations devise.en.yml (Portuguese, Brazilian)

* New translations doorkeeper.en.yml (Portuguese, Brazilian)

* New translations simple_form.en.yml (Indonesian)

* New translations activerecord.en.yml (Indonesian)

* New translations devise.en.yml (Chinese Traditional)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations doorkeeper.en.yml (Slovenian)

* New translations devise.en.yml (Swedish)

* New translations simple_form.en.yml (Albanian)

* New translations activerecord.en.yml (Albanian)

* New translations devise.en.yml (Albanian)

* New translations doorkeeper.en.yml (Albanian)

* New translations simple_form.en.yml (Serbian (Cyrillic))

* New translations activerecord.en.yml (Serbian (Cyrillic))

* New translations devise.en.yml (Serbian (Cyrillic))

* New translations doorkeeper.en.yml (Serbian (Cyrillic))

* New translations simple_form.en.yml (Swedish)

* New translations activerecord.en.yml (Swedish)

* New translations doorkeeper.en.yml (Swedish)

* New translations doorkeeper.en.yml (Chinese Simplified)

* New translations simple_form.en.yml (Turkish)

* New translations activerecord.en.yml (Turkish)

* New translations devise.en.yml (Turkish)

* New translations doorkeeper.en.yml (Turkish)

* New translations simple_form.en.yml (Ukrainian)

* New translations activerecord.en.yml (Ukrainian)

* New translations devise.en.yml (Ukrainian)

* New translations doorkeeper.en.yml (Ukrainian)

* New translations activerecord.en.yml (Chinese Simplified)

* New translations devise.en.yml (Chinese Simplified)

* New translations devise.en.yml (Indonesian)

* New translations doorkeeper.en.yml (Indonesian)

* New translations simple_form.en.yml (Kazakh)

* New translations doorkeeper.en.yml (Thai)

* New translations simple_form.en.yml (Croatian)

* New translations activerecord.en.yml (Croatian)

* New translations devise.en.yml (Croatian)

* New translations doorkeeper.en.yml (Croatian)

* New translations simple_form.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Norwegian Nynorsk)

* New translations devise.en.yml (Norwegian Nynorsk)

* New translations doorkeeper.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Kazakh)

* New translations activerecord.en.yml (Thai)

* New translations devise.en.yml (Kazakh)

* New translations doorkeeper.en.yml (Kazakh)

* New translations simple_form.en.yml (Estonian)

* New translations activerecord.en.yml (Estonian)

* New translations devise.en.yml (Estonian)

* New translations doorkeeper.en.yml (Estonian)

* New translations simple_form.en.yml (Latvian)

* New translations activerecord.en.yml (Latvian)

* New translations devise.en.yml (Latvian)

* New translations doorkeeper.en.yml (Latvian)

* New translations devise.en.yml (Thai)

* New translations simple_form.en.yml (Thai)

* New translations simple_form.en.yml (Persian)

* New translations doorkeeper.en.yml (Spanish, Argentina)

* New translations activerecord.en.yml (Persian)

* New translations devise.en.yml (Persian)

* New translations doorkeeper.en.yml (Persian)

* New translations simple_form.en.yml (Tamil)

* New translations activerecord.en.yml (Tamil)

* New translations devise.en.yml (Tamil)

* New translations doorkeeper.en.yml (Tamil)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations activerecord.en.yml (Spanish, Argentina)

* New translations devise.en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Marathi)

* New translations activerecord.en.yml (Spanish, Mexico)

* New translations devise.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Spanish, Mexico)

* New translations simple_form.en.yml (Bengali)

* New translations activerecord.en.yml (Bengali)

* New translations devise.en.yml (Bengali)

* New translations activerecord.en.yml (Marathi)

* New translations activerecord.en.yml (Hindi)

* New translations devise.en.yml (Malayalam)

* New translations activerecord.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Chinese Traditional, Hong Kong)

* New translations doorkeeper.en.yml (Chinese Traditional, Hong Kong)

* New translations simple_form.en.yml (Tatar)

* New translations activerecord.en.yml (Tatar)

* New translations devise.en.yml (Tatar)

* New translations doorkeeper.en.yml (Tatar)

* New translations simple_form.en.yml (Malayalam)

* New translations activerecord.en.yml (Malayalam)

* New translations doorkeeper.en.yml (Malayalam)

* New translations simple_form.en.yml (Breton)

* New translations activerecord.en.yml (Breton)

* New translations devise.en.yml (Breton)

* New translations doorkeeper.en.yml (Breton)

* New translations activerecord.en.yml (Sinhala)

* New translations devise.en.yml (Sinhala)

* New translations doorkeeper.en.yml (Sinhala)

* New translations simple_form.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Hindi)

* New translations doorkeeper.en.yml (Hindi)

* New translations simple_form.en.yml (Welsh)

* New translations activerecord.en.yml (Welsh)

* New translations devise.en.yml (Welsh)

* New translations doorkeeper.en.yml (Welsh)

* New translations simple_form.en.yml (Esperanto)

* New translations activerecord.en.yml (Esperanto)

* New translations devise.en.yml (Esperanto)

* New translations doorkeeper.en.yml (Esperanto)

* New translations simple_form.en.yml (Corsican)

* New translations activerecord.en.yml (Corsican)

* New translations devise.en.yml (Corsican)

* New translations doorkeeper.en.yml (Corsican)

* New translations simple_form.en.yml (Sardinian)

* New translations activerecord.en.yml (Sardinian)

* New translations devise.en.yml (Sardinian)

* New translations doorkeeper.en.yml (Sardinian)

* New translations devise.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Kabyle)

* New translations activerecord.en.yml (Kabyle)

* New translations devise.en.yml (Kabyle)

* New translations doorkeeper.en.yml (Kabyle)

* New translations simple_form.en.yml (Ido)

* New translations activerecord.en.yml (Ido)

* New translations devise.en.yml (Ido)

* New translations doorkeeper.en.yml (Ido)

* New translations doorkeeper.en.yml (Sorani (Kurdish))

* New translations activerecord.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Occitan)

* New translations devise.en.yml (Kannada)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations activerecord.en.yml (Scottish Gaelic)

* New translations devise.en.yml (Scottish Gaelic)

* New translations doorkeeper.en.yml (Scottish Gaelic)

* New translations activerecord.en.yml (Asturian)

* New translations devise.en.yml (Asturian)

* New translations activerecord.en.yml (Occitan)

* New translations simple_form.en.yml (Sorani (Kurdish))

* New translations devise.en.yml (Occitan)

* New translations doorkeeper.en.yml (Occitan)

* New translations simple_form.en.yml (Serbian (Latin))

* New translations activerecord.en.yml (Serbian (Latin))

* New translations devise.en.yml (Serbian (Latin))

* New translations doorkeeper.en.yml (Serbian (Latin))

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations activerecord.en.yml (Kurmanji (Kurdish))

* New translations devise.en.yml (Kurmanji (Kurdish))

* New translations doorkeeper.en.yml (Kurmanji (Kurdish))

* New translations simple_form.en.yml (Standard Moroccan Tamazight)

* New translations activerecord.en.yml (Standard Moroccan Tamazight)

* New translations devise.en.yml (Standard Moroccan Tamazight)

* New translations doorkeeper.en.yml (Standard Moroccan Tamazight)

* New translations en.yml (German)

* New translations en.json (German)

* New translations en.json (Kurmanji (Kurdish))

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.json (Ukrainian)

* New translations en.json (Dutch)

* New translations en.json (Dutch)

* New translations en.yml (Dutch)

* New translations en.yml (Dutch)

* New translations en.json (Dutch)

* New translations en.yml (Dutch)

* New translations en.json (Danish)

* New translations en.yml (Danish)

* New translations en.json (Danish)

* New translations en.json (Vietnamese)

* New translations en.yml (Turkish)

* New translations en.json (Turkish)

* New translations en.json (Vietnamese)

* New translations en.yml (Vietnamese)

* New translations simple_form.en.yml (Turkish)

* New translations simple_form.en.yml (Turkish)

* New translations en.yml (Spanish)

* New translations en.json (Spanish)

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-10 01:27:03 +09:00
Eugen Rochko 0765324622
Fix intermediary responsive layout, accessibility on navigation in web UI (#19324)
* Fix intermediary responsive layout, accessibility on navigation in web UI

* `yarn test:jest -u`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-09 15:55:32 +02:00
Claire 2b00ccdbd5
Fix button to dismiss suggestions not showing up in search results (#19325)
Fix a typo. The scope of this fix is pretty minor as that view only ever
shows up in one corner case, now.
2022-10-09 12:28:59 +02:00
Eugen Rochko f41ec9af05
Add dismissable hints to various timelines in web UI (#19315)
Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-09 06:08:37 +02:00
Yamagishi Kazutoshi a5112b51fd
Add title to pages with missing title in Web UI (#19322) 2022-10-09 03:55:09 +02:00
Yamagishi Kazutoshi e82467ca41
Remove timeline preview link from nav panel when not signed-in (#19320)
* Remove timeline preview link from nav panel when not signed-in

* Always enable server stats
2022-10-09 03:49:51 +02:00
Eugen Rochko 45ebdb72ca
Add support for language preferences for trending statuses and links (#18288) 2022-10-08 16:45:40 +02:00
Eugen Rochko 678fc4d292
Fix privacy policy being empty if custom setting exists but is empty (#19318) 2022-10-08 08:34:00 +02:00
Eugen Rochko d4b0aa7450
Fix trying to connect to streaming API when logged out in web UI (#19316) 2022-10-08 07:15:50 +02:00
dependabot[bot] d84c53e769
Bump sidekiq-scheduler from 4.0.2 to 4.0.3 (#19314)
Bumps [sidekiq-scheduler](https://github.com/moove-it/sidekiq-scheduler) from 4.0.2 to 4.0.3.
- [Release notes](https://github.com/moove-it/sidekiq-scheduler/releases)
- [Changelog](https://github.com/sidekiq-scheduler/sidekiq-scheduler/blob/master/CHANGELOG.md)
- [Commits](https://github.com/moove-it/sidekiq-scheduler/compare/v4.0.2...v4.0.3)

---
updated-dependencies:
- dependency-name: sidekiq-scheduler
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-08 14:14:13 +09:00
Eugen Rochko 9a685e2f8c
New Crowdin updates (#19297)
* New translations en.yml (Corsican)

* New translations en.yml (Kabyle)

* New translations en.yml (Taigi)

* New translations simple_form.en.yml (Vietnamese)

* New translations en.yml (Standard Moroccan Tamazight)

* New translations simple_form.en.yml (Sinhala)

* New translations en.yml (Asturian)

* New translations activerecord.en.yml (Bulgarian)

* New translations simple_form.en.yml (Hebrew)

* New translations simple_form.en.yml (Finnish)

* New translations activerecord.en.yml (Finnish)

* New translations devise.en.yml (Finnish)

* New translations activerecord.en.yml (Hebrew)

* New translations activerecord.en.yml (Basque)

* New translations devise.en.yml (Hebrew)

* New translations simple_form.en.yml (Hungarian)

* New translations activerecord.en.yml (Hungarian)

* New translations devise.en.yml (Hungarian)

* New translations simple_form.en.yml (Armenian)

* New translations activerecord.en.yml (Armenian)

* New translations devise.en.yml (Armenian)

* New translations devise.en.yml (Basque)

* New translations simple_form.en.yml (Basque)

* New translations devise.en.yml (Bulgarian)

* New translations simple_form.en.yml (Catalan)

* New translations activerecord.en.yml (Catalan)

* New translations devise.en.yml (Catalan)

* New translations devise.en.yml (Czech)

* New translations simple_form.en.yml (Danish)

* New translations activerecord.en.yml (Danish)

* New translations devise.en.yml (Danish)

* New translations simple_form.en.yml (German)

* New translations activerecord.en.yml (German)

* New translations devise.en.yml (German)

* New translations simple_form.en.yml (Greek)

* New translations activerecord.en.yml (Greek)

* New translations devise.en.yml (Greek)

* New translations simple_form.en.yml (Frisian)

* New translations activerecord.en.yml (Frisian)

* New translations devise.en.yml (Frisian)

* New translations simple_form.en.yml (Italian)

* New translations activerecord.en.yml (Italian)

* New translations activerecord.en.yml (Portuguese)

* New translations activerecord.en.yml (Polish)

* New translations devise.en.yml (Polish)

* New translations simple_form.en.yml (Portuguese)

* New translations devise.en.yml (Portuguese)

* New translations activerecord.en.yml (Norwegian)

* New translations simple_form.en.yml (Russian)

* New translations activerecord.en.yml (Russian)

* New translations devise.en.yml (Russian)

* New translations simple_form.en.yml (Slovak)

* New translations activerecord.en.yml (Slovak)

* New translations devise.en.yml (Slovak)

* New translations simple_form.en.yml (Slovenian)

* New translations devise.en.yml (Norwegian)

* New translations simple_form.en.yml (Norwegian)

* New translations devise.en.yml (Italian)

* New translations activerecord.en.yml (Korean)

* New translations simple_form.en.yml (Japanese)

* New translations activerecord.en.yml (Japanese)

* New translations devise.en.yml (Japanese)

* New translations simple_form.en.yml (Georgian)

* New translations activerecord.en.yml (Georgian)

* New translations devise.en.yml (Georgian)

* New translations simple_form.en.yml (Korean)

* New translations devise.en.yml (Korean)

* New translations devise.en.yml (Dutch)

* New translations activerecord.en.yml (Slovenian)

* New translations devise.en.yml (Slovenian)

* New translations devise.en.yml (Urdu (Pakistan))

* New translations devise.en.yml (Chinese Traditional)

* New translations activerecord.en.yml (Chinese Traditional)

* New translations devise.en.yml (Chinese Simplified)

* New translations activerecord.en.yml (Chinese Simplified)

* New translations devise.en.yml (Ukrainian)

* New translations activerecord.en.yml (Ukrainian)

* New translations simple_form.en.yml (Ukrainian)

* New translations simple_form.en.yml (Chinese Traditional)

* New translations devise.en.yml (Turkish)

* New translations activerecord.en.yml (Serbian (Cyrillic))

* New translations activerecord.en.yml (Turkish)

* New translations simple_form.en.yml (Albanian)

* New translations activerecord.en.yml (Albanian)

* New translations devise.en.yml (Albanian)

* New translations simple_form.en.yml (Serbian (Cyrillic))

* New translations devise.en.yml (Serbian (Cyrillic))

* New translations simple_form.en.yml (Swedish)

* New translations activerecord.en.yml (Swedish)

* New translations devise.en.yml (Swedish)

* New translations simple_form.en.yml (Turkish)

* New translations devise.en.yml (Icelandic)

* New translations activerecord.en.yml (Indonesian)

* New translations simple_form.en.yml (Indonesian)

* New translations devise.en.yml (Portuguese, Brazilian)

* New translations activerecord.en.yml (Portuguese, Brazilian)

* New translations simple_form.en.yml (Portuguese, Brazilian)

* New translations activerecord.en.yml (Vietnamese)

* New translations activerecord.en.yml (Icelandic)

* New translations simple_form.en.yml (Icelandic)

* New translations devise.en.yml (Galician)

* New translations simple_form.en.yml (Galician)

* New translations devise.en.yml (Vietnamese)

* New translations devise.en.yml (Indonesian)

* New translations simple_form.en.yml (Kazakh)

* New translations simple_form.en.yml (Croatian)

* New translations activerecord.en.yml (Croatian)

* New translations devise.en.yml (Croatian)

* New translations simple_form.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Norwegian Nynorsk)

* New translations devise.en.yml (Norwegian Nynorsk)

* New translations activerecord.en.yml (Kazakh)

* New translations activerecord.en.yml (Thai)

* New translations devise.en.yml (Kazakh)

* New translations simple_form.en.yml (Estonian)

* New translations activerecord.en.yml (Estonian)

* New translations devise.en.yml (Estonian)

* New translations simple_form.en.yml (Latvian)

* New translations activerecord.en.yml (Latvian)

* New translations devise.en.yml (Latvian)

* New translations devise.en.yml (Thai)

* New translations simple_form.en.yml (Thai)

* New translations simple_form.en.yml (Persian)

* New translations activerecord.en.yml (Persian)

* New translations devise.en.yml (Persian)

* New translations simple_form.en.yml (Tamil)

* New translations activerecord.en.yml (Tamil)

* New translations devise.en.yml (Tamil)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations activerecord.en.yml (Spanish, Argentina)

* New translations devise.en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Spanish, Mexico)

* New translations activerecord.en.yml (Spanish, Mexico)

* New translations devise.en.yml (Spanish, Mexico)

* New translations simple_form.en.yml (Bengali)

* New translations activerecord.en.yml (Bengali)

* New translations devise.en.yml (Bengali)

* New translations activerecord.en.yml (Marathi)

* New translations activerecord.en.yml (Hindi)

* New translations devise.en.yml (Malayalam)

* New translations activerecord.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Chinese Traditional, Hong Kong)

* New translations simple_form.en.yml (Tatar)

* New translations activerecord.en.yml (Tatar)

* New translations devise.en.yml (Tatar)

* New translations simple_form.en.yml (Malayalam)

* New translations activerecord.en.yml (Malayalam)

* New translations simple_form.en.yml (Breton)

* New translations activerecord.en.yml (Breton)

* New translations devise.en.yml (Breton)

* New translations activerecord.en.yml (Sinhala)

* New translations devise.en.yml (Sinhala)

* New translations simple_form.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Hindi)

* New translations simple_form.en.yml (Welsh)

* New translations activerecord.en.yml (Welsh)

* New translations devise.en.yml (Welsh)

* New translations simple_form.en.yml (Esperanto)

* New translations activerecord.en.yml (Esperanto)

* New translations devise.en.yml (Esperanto)

* New translations simple_form.en.yml (Corsican)

* New translations activerecord.en.yml (Corsican)

* New translations devise.en.yml (Corsican)

* New translations simple_form.en.yml (Sardinian)

* New translations activerecord.en.yml (Sardinian)

* New translations devise.en.yml (Sardinian)

* New translations devise.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Kabyle)

* New translations activerecord.en.yml (Kabyle)

* New translations devise.en.yml (Kabyle)

* New translations simple_form.en.yml (Ido)

* New translations activerecord.en.yml (Ido)

* New translations devise.en.yml (Ido)

* New translations activerecord.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Occitan)

* New translations devise.en.yml (Kannada)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations activerecord.en.yml (Scottish Gaelic)

* New translations devise.en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Asturian)

* New translations activerecord.en.yml (Asturian)

* New translations devise.en.yml (Asturian)

* New translations activerecord.en.yml (Occitan)

* New translations simple_form.en.yml (Sorani (Kurdish))

* New translations devise.en.yml (Occitan)

* New translations simple_form.en.yml (Serbian (Latin))

* New translations activerecord.en.yml (Serbian (Latin))

* New translations devise.en.yml (Serbian (Latin))

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations activerecord.en.yml (Kurmanji (Kurdish))

* New translations devise.en.yml (Kurmanji (Kurdish))

* New translations simple_form.en.yml (Standard Moroccan Tamazight)

* New translations activerecord.en.yml (Standard Moroccan Tamazight)

* New translations devise.en.yml (Standard Moroccan Tamazight)

* New translations en.yml (Chinese Simplified)

* New translations en.yml (Russian)

* New translations en.json (Chinese Simplified)

* New translations en.yml (Icelandic)

* New translations en.yml (Vietnamese)

* New translations en.yml (Turkish)

* New translations en.yml (Spanish)

* New translations en.yml (Ukrainian)

* New translations en.yml (Hungarian)

* New translations en.yml (Hungarian)

* New translations en.yml (Czech)

* New translations en.yml (Albanian)

* New translations en.json (Polish)

* New translations en.yml (Polish)

* New translations en.json (French)

* New translations en.yml (French)

* New translations simple_form.en.yml (French)

* New translations en.json (French)

* New translations en.yml (French)

* New translations en.yml (Thai)

* New translations en.yml (Greek)

* New translations en.yml (Catalan)

* New translations en.yml (Danish)

* New translations en.yml (Hebrew)

* New translations en.yml (Hungarian)

* New translations en.yml (French)

* New translations en.yml (German)

* New translations en.yml (Czech)

* New translations en.yml (Chinese Simplified)

* New translations en.yml (Ido)

* New translations en.yml (Spanish)

* New translations en.yml (Turkish)

* New translations en.yml (Albanian)

* New translations en.yml (Ukrainian)

* New translations en.yml (Chinese Traditional)

* New translations en.yml (Slovenian)

* New translations en.yml (Vietnamese)

* New translations en.yml (Galician)

* New translations en.yml (Icelandic)

* New translations en.yml (Dutch)

* New translations en.yml (Italian)

* New translations en.yml (Japanese)

* New translations en.yml (Korean)

* New translations en.yml (Polish)

* New translations en.yml (Portuguese)

* New translations en.yml (Russian)

* New translations en.yml (Scottish Gaelic)

* New translations en.yml (Asturian)

* New translations en.yml (Spanish, Argentina)

* New translations en.yml (Spanish, Mexico)

* New translations en.yml (Latvian)

* New translations en.yml (Kurmanji (Kurdish))

* Fix platform-specific code

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-08 13:34:58 +09:00
Eugen Rochko a2ba011326
Change privacy policy to be rendered in web UI, add REST API (#19310)
Source string no longer localized, Markdown instead of raw HTML
2022-10-08 06:01:11 +02:00
Eugen Rochko 7fb738c837
Add interaction modal to logged-out web UI (#19306) 2022-10-07 10:14:31 +02:00
trwnh 99a43f0282
Fix #19304 (#19305) 2022-10-07 05:53:14 +02:00
dependabot[bot] 402ee73e24
Bump jest from 29.0.3 to 29.1.2 (#19285)
Bumps [jest](https://github.com/facebook/jest/tree/HEAD/packages/jest) from 29.0.3 to 29.1.2.
- [Release notes](https://github.com/facebook/jest/releases)
- [Changelog](https://github.com/facebook/jest/blob/main/CHANGELOG.md)
- [Commits](https://github.com/facebook/jest/commits/v29.1.2/packages/jest)

---
updated-dependencies:
- dependency-name: jest
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-07 03:34:03 +09:00
dependabot[bot] 021ccf46af
Bump babel-jest from 29.0.3 to 29.1.2 (#19275)
Bumps [babel-jest](https://github.com/facebook/jest/tree/HEAD/packages/babel-jest) from 29.0.3 to 29.1.2.
- [Release notes](https://github.com/facebook/jest/releases)
- [Changelog](https://github.com/facebook/jest/blob/main/CHANGELOG.md)
- [Commits](https://github.com/facebook/jest/commits/v29.1.2/packages/babel-jest)

---
updated-dependencies:
- dependency-name: babel-jest
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-07 02:24:59 +09:00
dependabot[bot] 34c8707dec
Bump jest-environment-jsdom from 29.0.3 to 29.1.2 (#19282)
Bumps [jest-environment-jsdom](https://github.com/facebook/jest/tree/HEAD/packages/jest-environment-jsdom) from 29.0.3 to 29.1.2.
- [Release notes](https://github.com/facebook/jest/releases)
- [Changelog](https://github.com/facebook/jest/blob/main/CHANGELOG.md)
- [Commits](https://github.com/facebook/jest/commits/v29.1.2/packages/jest-environment-jsdom)

---
updated-dependencies:
- dependency-name: jest-environment-jsdom
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-10-07 02:23:58 +09:00
Eugen Rochko 93f340a4bf
Remove setting that disables account deletes (#17683) 2022-10-06 10:16:47 +02:00
Eugen Rochko 62782babd0
Change public statuses pages to mount the web UI (#19301) 2022-10-06 02:26:34 +02:00
Eugen Rochko 58d5b28cb0
Remove previous landing page (#19300) 2022-10-06 02:19:45 +02:00
Eugen Rochko 5fd46dddd7
Remove unnecessary sections from welcome e-mail (#19299) 2022-10-06 00:03:52 +02:00
Eugen Rochko 679274465b
Add server rules to sign-up flow (#19296) 2022-10-05 18:57:33 +02:00
Eugen Rochko 26f2586b62
New Crowdin updates (#19289)
* New translations devise.en.yml (Tamil)

* New translations doorkeeper.en.yml (Tamil)

* New translations simple_form.en.yml (Spanish, Argentina)

* New translations activerecord.en.yml (Spanish, Argentina)

* New translations devise.en.yml (Spanish, Argentina)

* New translations simple_form.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Marathi)

* New translations activerecord.en.yml (Spanish, Mexico)

* New translations devise.en.yml (Spanish, Mexico)

* New translations doorkeeper.en.yml (Spanish, Mexico)

* New translations simple_form.en.yml (Bengali)

* New translations activerecord.en.yml (Bengali)

* New translations devise.en.yml (Bengali)

* New translations activerecord.en.yml (Marathi)

* New translations activerecord.en.yml (Hindi)

* New translations devise.en.yml (Malayalam)

* New translations activerecord.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Chinese Traditional, Hong Kong)

* New translations doorkeeper.en.yml (Chinese Traditional, Hong Kong)

* New translations simple_form.en.yml (Tatar)

* New translations activerecord.en.yml (Tatar)

* New translations devise.en.yml (Tatar)

* New translations doorkeeper.en.yml (Tatar)

* New translations simple_form.en.yml (Malayalam)

* New translations activerecord.en.yml (Malayalam)

* New translations doorkeeper.en.yml (Malayalam)

* New translations simple_form.en.yml (Breton)

* New translations activerecord.en.yml (Breton)

* New translations devise.en.yml (Breton)

* New translations doorkeeper.en.yml (Breton)

* New translations activerecord.en.yml (Sinhala)

* New translations devise.en.yml (Sinhala)

* New translations doorkeeper.en.yml (Sinhala)

* New translations simple_form.en.yml (Chinese Traditional, Hong Kong)

* New translations devise.en.yml (Hindi)

* New translations doorkeeper.en.yml (Hindi)

* New translations simple_form.en.yml (Welsh)

* New translations activerecord.en.yml (Welsh)

* New translations devise.en.yml (Welsh)

* New translations doorkeeper.en.yml (Welsh)

* New translations simple_form.en.yml (Esperanto)

* New translations activerecord.en.yml (Esperanto)

* New translations devise.en.yml (Esperanto)

* New translations doorkeeper.en.yml (Esperanto)

* New translations simple_form.en.yml (Corsican)

* New translations activerecord.en.yml (Corsican)

* New translations devise.en.yml (Corsican)

* New translations doorkeeper.en.yml (Corsican)

* New translations simple_form.en.yml (Sardinian)

* New translations activerecord.en.yml (Sardinian)

* New translations devise.en.yml (Sardinian)

* New translations doorkeeper.en.yml (Sardinian)

* New translations devise.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Kabyle)

* New translations activerecord.en.yml (Kabyle)

* New translations devise.en.yml (Kabyle)

* New translations doorkeeper.en.yml (Kabyle)

* New translations simple_form.en.yml (Ido)

* New translations activerecord.en.yml (Ido)

* New translations devise.en.yml (Ido)

* New translations doorkeeper.en.yml (Ido)

* New translations doorkeeper.en.yml (Sorani (Kurdish))

* New translations activerecord.en.yml (Sorani (Kurdish))

* New translations simple_form.en.yml (Occitan)

* New translations devise.en.yml (Kannada)

* New translations simple_form.en.yml (Scottish Gaelic)

* New translations activerecord.en.yml (Scottish Gaelic)

* New translations devise.en.yml (Scottish Gaelic)

* New translations doorkeeper.en.yml (Scottish Gaelic)

* New translations simple_form.en.yml (Asturian)

* New translations activerecord.en.yml (Asturian)

* New translations devise.en.yml (Asturian)

* New translations doorkeeper.en.yml (Asturian)

* New translations activerecord.en.yml (Occitan)

* New translations simple_form.en.yml (Sorani (Kurdish))

* New translations devise.en.yml (Occitan)

* New translations doorkeeper.en.yml (Occitan)

* New translations simple_form.en.yml (Serbian (Latin))

* New translations activerecord.en.yml (Serbian (Latin))

* New translations devise.en.yml (Serbian (Latin))

* New translations doorkeeper.en.yml (Serbian (Latin))

* New translations simple_form.en.yml (Kurmanji (Kurdish))

* New translations activerecord.en.yml (Kurmanji (Kurdish))

* New translations devise.en.yml (Kurmanji (Kurdish))

* New translations doorkeeper.en.yml (Kurmanji (Kurdish))

* New translations simple_form.en.yml (Standard Moroccan Tamazight)

* New translations activerecord.en.yml (Standard Moroccan Tamazight)

* New translations devise.en.yml (Standard Moroccan Tamazight)

* New translations doorkeeper.en.yml (Standard Moroccan Tamazight)

* New translations en.yml (Vietnamese)

* New translations en.yml (Vietnamese)

* New translations en.yml (Romanian)

* New translations en.json (Arabic)

* New translations en.yml (Afrikaans)

* New translations en.json (Spanish)

* New translations en.yml (French)

* New translations en.json (French)

* New translations en.json (Catalan)

* New translations en.json (Romanian)

* New translations en.yml (Catalan)

* New translations en.json (Danish)

* New translations en.yml (Danish)

* New translations en.json (Greek)

* New translations en.yml (Greek)

* New translations en.yml (Bulgarian)

* New translations en.json (Bulgarian)

* New translations en.yml (German)

* New translations en.yml (Czech)

* New translations en.json (German)

* New translations en.json (Czech)

* New translations en.yml (Spanish)

* New translations en.yml (Arabic)

* New translations en.yml (Basque)

* New translations en.json (Finnish)

* New translations en.yml (Finnish)

* New translations en.json (Irish)

* New translations en.json (Basque)

* New translations en.json (Frisian)

* New translations en.yml (Hebrew)

* New translations en.yml (Thai)

* New translations en.json (Hebrew)

* New translations en.json (Sinhala)

* New translations en.json (Indonesian)

* New translations en.json (Japanese)

* New translations en.yml (Ukrainian)

* New translations en.yml (Albanian)

* New translations en.json (Albanian)

* New translations en.json (Dutch)

* New translations en.yml (Turkish)

* New translations en.json (Esperanto)

* New translations en.json (Tamil)

* New translations en.json (Ido)

* New translations en.yml (Ido)

* New translations en.yml (Chinese Simplified)

* New translations en.json (Thai)

* New translations en.json (Hungarian)

* New translations en.yml (Hungarian)

* New translations en.json (Chinese Traditional)

* New translations en.json (Slovenian)

* New translations en.yml (Slovenian)

* New translations en.json (Serbian (Cyrillic))

* New translations en.yml (Serbian (Cyrillic))

* New translations en.json (Swedish)

* New translations en.yml (Swedish)

* New translations en.json (Turkish)

* New translations en.json (Ukrainian)

* New translations en.json (Chinese Simplified)

* New translations en.yml (Chinese Traditional)

* New translations en.json (Slovak)

* New translations en.json (Urdu (Pakistan))

* New translations en.json (Vietnamese)

* New translations en.yml (Vietnamese)

* New translations en.json (Galician)

* New translations en.yml (Galician)

* New translations en.json (Icelandic)

* New translations en.yml (Icelandic)

* New translations en.json (Portuguese, Brazilian)

* New translations en.yml (Portuguese, Brazilian)

* New translations en.yml (Slovak)

* New translations en.yml (Russian)

* New translations en.json (Armenian)

* New translations en.json (Macedonian)

* New translations en.yml (Armenian)

* New translations en.json (Italian)

* New translations en.yml (Italian)

* New translations en.yml (Japanese)

* New translations en.json (Georgian)

* New translations en.yml (Georgian)

* New translations en.json (Korean)

* New translations en.yml (Korean)

* New translations en.yml (Lithuanian)

* New translations en.json (Russian)

* New translations en.yml (Dutch)

* New translations en.json (Norwegian)

* New translations en.yml (Norwegian)

* New translations en.json (Polish)

* New translations en.yml (Polish)

* New translations en.json (Portuguese)

* New translations en.yml (Portuguese)

* New translations en.yml (Indonesian)

* New translations en.json (Persian)

* New translations en.json (Welsh)

* New translations en.yml (Welsh)

* New translations en.yml (Esperanto)

* New translations en.json (Chinese Traditional, Hong Kong)

* New translations en.yml (Chinese Traditional, Hong Kong)

* New translations en.json (Malayalam)

* New translations en.yml (Telugu)

* New translations en.yml (Malayalam)

* New translations en.json (Breton)

* New translations en.yml (Breton)

* New translations en.yml (Sinhala)

* New translations en.json (Cornish)

* New translations en.json (Scottish Gaelic)

* New translations en.yml (Scottish Gaelic)

* New translations en.json (Telugu)

* New translations en.yml (Persian)

* New translations en.yml (Croatian)

* New translations en.yml (Tamil)

* New translations en.json (Spanish, Argentina)

* New translations en.yml (Spanish, Argentina)

* New translations en.json (Spanish, Mexico)

* New translations en.yml (Spanish, Mexico)

* New translations en.json (Bengali)

* New translations en.yml (Bengali)

* New translations en.json (Croatian)

* New translations en.json (Norwegian Nynorsk)

* New translations en.yml (Malay)

* New translations en.yml (Norwegian Nynorsk)

* New translations en.json (Kazakh)

* New translations en.yml (Kazakh)

* New translations en.json (Estonian)

* New translations en.yml (Estonian)

* New translations en.json (Latvian)

* New translations en.yml (Latvian)

* New translations en.json (Hindi)

* New translations en.json (Malay)

* New translations en.json (Asturian)

* New translations en.yml (Asturian)

* New translations en.json (Occitan)

* New translations en.yml (Sardinian)

* New translations en.yml (Occitan)

* New translations en.json (Serbian (Latin))

* New translations en.yml (Serbian (Latin))

* New translations en.json (Kurmanji (Kurdish))

* New translations en.yml (Kurmanji (Kurdish))

* New translations en.json (Sorani (Kurdish))

* New translations en.yml (Sorani (Kurdish))

* New translations en.json (Corsican)

* New translations en.yml (Corsican)

* New translations en.json (Sardinian)

* New translations en.json (Kabyle)

* New translations en.yml (Kabyle)

* New translations en.json (Standard Moroccan Tamazight)

* New translations en.json (German)

* New translations en.json (Catalan)

* New translations en.json (Greek)

* New translations en.json (Slovenian)

* New translations en.json (Spanish, Argentina)

* New translations en.json (Czech)

* New translations en.json (Russian)

* New translations en.json (Chinese Traditional)

* New translations en.json (Ido)

* New translations en.json (Ukrainian)

* New translations en.json (Icelandic)

* New translations en.json (Korean)

* New translations en.json (Galician)

* Run `yarn manage:translations`

* Run `bundle exec i18n-tasks normalize`

Co-authored-by: Yamagishi Kazutoshi <ykzts@desire.sh>
2022-10-05 16:14:38 +09:00
Eugen Rochko 0e41d360c0
Change font size of active users in server banner to be larger in web UI (#19295) 2022-10-05 07:02:09 +02:00
Eugen Rochko 9f65909f42
Change public timelines to be filtered by current locale by default (#19291)
In the absence of an opt-in to multiple specific languages in the
preferences, it makes more sense to filter by the user's presumed
language only (interface language or `lang` override)
2022-10-05 03:48:06 +02:00
Eugen Rochko d2528b26b6
Add server banner to web app, add GET /api/v2/instance to REST API (#19294) 2022-10-05 03:47:56 +02:00
Claire cedcece0cc
Fix deleted pinned posts potentially counting towards the pinned posts limit (#19005)
Fixes #18938
2022-10-05 00:16:40 +02:00
Eugen Rochko 02ba9cfa35
Remove code for rendering public and hashtag timelines outside the web UI (#19257) 2022-10-04 20:13:46 +02:00
Eugen Rochko e2b561e3a5
Fix logged-out web UI on smaller screens (#19263) 2022-10-04 20:13:23 +02:00
embr 54c532cf45 Merge branch 'main' of https://github.com/glitch-soc/mastodon 2022-03-16 13:08:18 +01:00
embr e2971a743f Merge branch 'main' of https://github.com/glitch-soc/mastodon 2022-03-03 13:50:22 +01:00
embr 010cfac43e Merge branch 'main' of https://github.com/glitch-soc/mastodon 2022-02-06 17:18:51 +01:00
embr ca8e8d389d Merge branch 'main' of https://github.com/glitch-soc/mastodon 2022-02-03 14:28:58 +01:00
embr 1dd461349a status.show_less: 'Show less' -> 'Wait no' 2022-02-02 11:37:40 +01:00
embr 390c517c6f Merge branch 'main' of https://github.com/glitch-soc/mastodon 2022-02-02 11:37:26 +01:00
embr 80f9fdb8bc Merge remote-tracking branch 'glitch/main' 2021-10-18 15:11:45 +02:00
embr 2afd297091 fix custom CSS loading from port 80 in dev 2021-10-12 15:12:13 +02:00
embr 7e794b1a24 single-option polls lol 2021-10-12 15:12:13 +02:00
embr 99691e9a5a s/Toot/Honk/ 2021-10-12 15:12:13 +02:00
embr 2d3e8bf64a queer.af: change footer text and source link 2021-10-12 15:12:13 +02:00
embr 1e404025d9 add nix-shell for local development 2021-10-12 15:12:13 +02:00
embr 28287ad4aa nix: remove old version date 2021-10-12 15:12:13 +02:00
Riley Shepard 0ed8464092 Merged in new-default-avatar (pull request #2)
New custom stock avatar for new profiles
2021-10-12 15:12:13 +02:00
Riley Shepard b95609f86a Merged in favicon (pull request #1)
New custom favicons
2021-10-12 15:12:13 +02:00
embr 35ba1f089e nix: add default.nix and gemset.nix
Thank you, kind person who wrote this package with forks in mind.
2021-10-12 15:12:05 +02:00
embr 38887f24a8 nix: move kind-of from resolutions to dependencies
I'm not sure what `resolutions` actually does, but yarn2nix doesn't pick
it up there, so the build fails. Moving it to `dependencies` fixes it,
and is what upstream nixpkgs' `pkgs.mastodon` does.

Whenever upstream package.json or yarn.lock change, revert to upstream,
move all the resolutions back to dependencies, then re-run `yarn` and
`yarn2nix`.
2021-10-12 15:10:57 +02:00
embr 61fb0a9137 nix: add missing version to package.json
nix2yarn needs this, and it has to be semver-ish, or you end up in a
world of bizarre build failures.
2021-10-12 14:52:11 +02:00
765 changed files with 35458 additions and 24749 deletions

View file

@ -17,7 +17,7 @@
LOCAL_DOMAIN=example.com
# Use this only if you need to run mastodon on a different domain than the one used for federation.
# You can read more about this option on https://github.com/tootsuite/documentation/blob/master/Running-Mastodon/Serving_a_different_domain.md
# You can read more about this option on https://docs.joinmastodon.org/admin/config/#web-domain
# DO *NOT* USE THIS UNLESS YOU KNOW *EXACTLY* WHAT YOU ARE DOING.
# WEB_DOMAIN=mastodon.example.com
@ -247,7 +247,7 @@ SMTP_FROM_ADDRESS=notifications@example.com
# ---------------
# Various ways to customize Mastodon's behavior
# ---------------
# Maximum allowed character count
MAX_TOOT_CHARS=500

View file

@ -31,6 +31,11 @@ body:
description: What happened?
validations:
required: true
- type: textarea
attributes:
label: Detailed description
validations:
required: false
- type: textarea
attributes:
label: Specifications
@ -38,5 +43,14 @@ body:
What version or commit hash of Mastodon did you find this bug in?
If a front-end issue, what browser and operating systems were you using?
placeholder: |
Mastodon 3.5.3 (or Edge)
Ruby 2.7.6 (or v3.1.2)
Node.js 16.18.0
Google Chrome 106.0.5249.119
Firefox 105.0.3
etc...
validations:
required: true

View file

@ -34,7 +34,8 @@ jobs:
latest=auto
tags: |
type=edge,branch=main
type=match,pattern=v(.*),group=0
type=pep440,pattern={{raw}}
type=pep440,pattern=v{{major}}.{{minor}}
type=ref,event=pr
- uses: docker/build-push-action@v3
with:
@ -42,5 +43,5 @@ jobs:
platforms: linux/amd64,linux/arm64
push: ${{ github.event_name != 'pull_request' }}
tags: ${{ steps.meta.outputs.tags }}
cache-from: type=registry,ref=ghcr.io/${{ github.repository_owner }}/mastodon:latest
cache-from: type=registry,ref=ghcr.io/${{ github.repository_owner }}/mastodon:edge
cache-to: type=inline

3
.gitignore vendored
View file

@ -66,3 +66,6 @@ yarn-debug.log
# Ignore Docker option files
docker-compose.override.yml
# Ignore nix build output
/result

View file

@ -3,6 +3,132 @@ Changelog
All notable changes to this project will be documented in this file.
## [Unreleased]
Some of the features in this release have been funded through the [NGI0 Discovery](https://nlnet.nl/discovery) Fund, a fund established by [NLnet](https://nlnet.nl/) with financial support from the European Commission's [Next Generation Internet](https://ngi.eu/) programme, under the aegis of DG Communications Networks, Content and Technology under grant agreement No 825322.
### Added
- Add ability to filter followed accounts' posts by language ([Gargron](https://github.com/mastodon/mastodon/pull/19095), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19268))
- **Add ability to follow hashtags** ([Gargron](https://github.com/mastodon/mastodon/pull/18809), [Gargron](https://github.com/mastodon/mastodon/pull/18862), [Gargron](https://github.com/mastodon/mastodon/pull/19472), [noellabo](https://github.com/mastodon/mastodon/pull/18924))
- Add ability to filter individual posts ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18945))
- **Add ability to translate posts** ([Gargron](https://github.com/mastodon/mastodon/pull/19218), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19433), [Gargron](https://github.com/mastodon/mastodon/pull/19453), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19434), [Gargron](https://github.com/mastodon/mastodon/pull/19388), [ykzts](https://github.com/mastodon/mastodon/pull/19244), [Gargron](https://github.com/mastodon/mastodon/pull/19245))
- Add featured tags to web UI ([noellabo](https://github.com/mastodon/mastodon/pull/19408), [noellabo](https://github.com/mastodon/mastodon/pull/19380), [noellabo](https://github.com/mastodon/mastodon/pull/19358), [noellabo](https://github.com/mastodon/mastodon/pull/19409), [Gargron](https://github.com/mastodon/mastodon/pull/19382), [ykzts](https://github.com/mastodon/mastodon/pull/19418), [noellabo](https://github.com/mastodon/mastodon/pull/19403), [noellabo](https://github.com/mastodon/mastodon/pull/19404), [Gargron](https://github.com/mastodon/mastodon/pull/19398))
- **Add support for language preferences for trending statuses and links** ([Gargron](https://github.com/mastodon/mastodon/pull/18288), [Gargron](https://github.com/mastodon/mastodon/pull/19349), [ykzts](https://github.com/mastodon/mastodon/pull/19335))
- Previously, you could only see trends in your current language
- For less popular languages, that meant empty trends
- Now, trends in your preferred languages' are shown on top, with others beneath
- Add server rules to sign-up flow ([Gargron](https://github.com/mastodon/mastodon/pull/19296))
- Add privacy icons to report modal in web UI ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/19190))
- Add `noopener` to links to remote profiles in web UI ([shleeable](https://github.com/mastodon/mastodon/pull/19014))
- Add warning for sensitive audio posts in web UI ([rgroothuijsen](https://github.com/mastodon/mastodon/pull/17885))
- Add language attribute to posts in web UI ([tribela](https://github.com/mastodon/mastodon/pull/18544))
- Add meta tag for official iOS app ([Gargron](https://github.com/mastodon/mastodon/pull/16599))
- Add support for uploading WebP files ([Saiv46](https://github.com/mastodon/mastodon/pull/18506))
- Add support for uploading `audio/vnd.wave` files ([tribela](https://github.com/mastodon/mastodon/pull/18737))
- Add more debug information when processing remote accounts ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/15605), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19209))
- **Add retention policy for cached content and media** ([Gargron](https://github.com/mastodon/mastodon/pull/19232), [zunda](https://github.com/mastodon/mastodon/pull/19478), [Gargron](https://github.com/mastodon/mastodon/pull/19458), [Gargron](https://github.com/mastodon/mastodon/pull/19248))
- Set for how long remote posts or media should be cached on your server
- Hands-off alternative to `tootctl` commands
- **Add customizable user roles** ([Gargron](https://github.com/mastodon/mastodon/pull/18641), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18812), [Gargron](https://github.com/mastodon/mastodon/pull/19040), [tribela](https://github.com/mastodon/mastodon/pull/18825), [tribela](https://github.com/mastodon/mastodon/pull/18826), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18776), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18777), [unextro](https://github.com/mastodon/mastodon/pull/18786), [tribela](https://github.com/mastodon/mastodon/pull/18824), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19436))
- Previously, there were 3 hard-coded roles, user, moderator, and admin
- Create your own roles and decide which permissions they should have
- Add notifications for new reports ([Gargron](https://github.com/mastodon/mastodon/pull/18697), [Gargron](https://github.com/mastodon/mastodon/pull/19475))
- Add ability to select all accounts matching search for batch actions in admin UI ([Gargron](https://github.com/mastodon/mastodon/pull/19053), [Gargron](https://github.com/mastodon/mastodon/pull/19054))
- Add ability to view previous edits of a status in admin UI ([Gargron](https://github.com/mastodon/mastodon/pull/19462))
- Add ability to block sign-ups from IP ([Gargron](https://github.com/mastodon/mastodon/pull/19037))
- **Add webhooks to admin UI** ([Gargron](https://github.com/mastodon/mastodon/pull/18510))
- Add admin API for managing domain allows ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18668))
- Add admin API for managing domain blocks ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18247))
- Add admin API for managing e-mail domain blocks ([Gargron](https://github.com/mastodon/mastodon/pull/19066))
- Add admin API for managing canonical e-mail blocks ([Gargron](https://github.com/mastodon/mastodon/pull/19067))
- Add admin API for managing IP blocks ([Gargron](https://github.com/mastodon/mastodon/pull/19065))
- Add `services` and `metadata` to the NodeInfo endpoint ([MFTabriz](https://github.com/mastodon/mastodon/pull/18563))
- Add `--remove-role` option to `tootctl accounts modify` ([Gargron](https://github.com/mastodon/mastodon/pull/19477))
- Add `--days` option to `tootctl media refresh` ([tribela](https://github.com/mastodon/mastodon/pull/18425))
- Add `EMAIL_DOMAIN_LISTS_APPLY_AFTER_CONFIRMATION` environment variable ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18642))
- Add `IP_RETENTION_PERIOD` and `SESSION_RETENTION_PERIOD` environment variables ([kescherCode](https://github.com/mastodon/mastodon/pull/18757))
- Add `http_hidden_proxy` environment variable ([tribela](https://github.com/mastodon/mastodon/pull/18427))
### Changed
- **Change brand color and logotypes** ([Gargron](https://github.com/mastodon/mastodon/pull/18592), [Gargron](https://github.com/mastodon/mastodon/pull/18639), [Gargron](https://github.com/mastodon/mastodon/pull/18691), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18634), [Gargron](https://github.com/mastodon/mastodon/pull/19254), [mayaeh](https://github.com/mastodon/mastodon/pull/18710))
- **Change post editing to be enabled in web UI** ([Gargron](https://github.com/mastodon/mastodon/pull/19103))
- **Change web UI to work for logged-out users** ([Gargron](https://github.com/mastodon/mastodon/pull/18961), [Gargron](https://github.com/mastodon/mastodon/pull/19250), [Gargron](https://github.com/mastodon/mastodon/pull/19294), [Gargron](https://github.com/mastodon/mastodon/pull/19306), [Gargron](https://github.com/mastodon/mastodon/pull/19315), [ykzts](https://github.com/mastodon/mastodon/pull/19322), [Gargron](https://github.com/mastodon/mastodon/pull/19412), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19437), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19415), [Gargron](https://github.com/mastodon/mastodon/pull/19348), [Gargron](https://github.com/mastodon/mastodon/pull/19295), [Gargron](https://github.com/mastodon/mastodon/pull/19422), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19414), [Gargron](https://github.com/mastodon/mastodon/pull/19319), [Gargron](https://github.com/mastodon/mastodon/pull/19345), [Gargron](https://github.com/mastodon/mastodon/pull/19310), [Gargron](https://github.com/mastodon/mastodon/pull/19301), [Gargron](https://github.com/mastodon/mastodon/pull/19423), [ykzts](https://github.com/mastodon/mastodon/pull/19471), [ykzts](https://github.com/mastodon/mastodon/pull/19333), [ykzts](https://github.com/mastodon/mastodon/pull/19337), [ykzts](https://github.com/mastodon/mastodon/pull/19272), [ykzts](https://github.com/mastodon/mastodon/pull/19468), [Gargron](https://github.com/mastodon/mastodon/pull/19466), [Gargron](https://github.com/mastodon/mastodon/pull/19457), [Gargron](https://github.com/mastodon/mastodon/pull/19426), [Gargron](https://github.com/mastodon/mastodon/pull/19427), [Gargron](https://github.com/mastodon/mastodon/pull/19421), [Gargron](https://github.com/mastodon/mastodon/pull/19417), [Gargron](https://github.com/mastodon/mastodon/pull/19413), [Gargron](https://github.com/mastodon/mastodon/pull/19397), [Gargron](https://github.com/mastodon/mastodon/pull/19387), [Gargron](https://github.com/mastodon/mastodon/pull/19396), [Gargron](https://github.com/mastodon/mastodon/pull/19385), [ykzts](https://github.com/mastodon/mastodon/pull/19334), [ykzts](https://github.com/mastodon/mastodon/pull/19329), [Gargron](https://github.com/mastodon/mastodon/pull/19324), [Gargron](https://github.com/mastodon/mastodon/pull/19318), [Gargron](https://github.com/mastodon/mastodon/pull/19316), [Gargron](https://github.com/mastodon/mastodon/pull/19263), [trwnh](https://github.com/mastodon/mastodon/pull/19305), [ykzts](https://github.com/mastodon/mastodon/pull/19273))
- The web app can now be accessed without being logged in
- No more `/web` prefix on web app paths
- Profiles, posts, and other public pages now use the same interface for logged in and logged out users
- The web app displays a server information banner
- Pop-up windows for remote interaction have been replaced with a modal window
- No need to type in your username for remote interaction, copy-paste-to-search method explained
- Various hints throughout the app explain what the different timelines are
- New about page design
- New privacy policy page design shows when the policy was last updated
- All sections of the web app now have appropriate window titles
- The layout of the interface has been streamlined between different screen sizes
- Posts now use more horizontal space
- Change label of publish button to be "Publish" again in web UI ([Gargron](https://github.com/mastodon/mastodon/pull/18583))
- Change language to be carried over on reply in web UI ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18557))
- Change "Unfollow" to "Cancel follow request" when request still pending in web UI ([prplecake](https://github.com/mastodon/mastodon/pull/19363))
- **Change post filtering system** ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18058), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19050), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18894), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/19051), [noellabo](https://github.com/mastodon/mastodon/pull/18923), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18956), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18744))
- Filtered keywords and phrases can now be grouped into named categories
- Filtered posts show which exact filter was hit
- Individual posts can be added to a filter
- You can peek inside filtered posts anyway
- Change path of privacy policy page from `/terms` to `/privacy-policy` ([Gargron](https://github.com/mastodon/mastodon/pull/19249))
- Change how hashtags are normalized ([Gargron](https://github.com/mastodon/mastodon/pull/18795), [Gargron](https://github.com/mastodon/mastodon/pull/18863), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18854))
- Change public timelines to be filtered by current locale by default ([Gargron](https://github.com/mastodon/mastodon/pull/19291))
- Change settings area to be separated into categories in admin UI ([Gargron](https://github.com/mastodon/mastodon/pull/19407))
- Change "No accounts selected" errors to use the appropriate noun in admin UI ([prplecake](https://github.com/mastodon/mastodon/pull/19356))
- Change e-mail domain blocks to match subdomains of blocked domains ([Gargron](https://github.com/mastodon/mastodon/pull/18979))
- Change custom emoji file size limit from 50 KB to 256 KB ([Gargron](https://github.com/mastodon/mastodon/pull/18788))
- Change "Allow trends without prior review" setting to also work for trending posts ([Gargron](https://github.com/mastodon/mastodon/pull/17977))
- Change search API to be accessible without being logged in ([Gargron](https://github.com/mastodon/mastodon/pull/18963), [Gargron](https://github.com/mastodon/mastodon/pull/19326))
- Change following and followers API to be accessible without being logged in ([Gargron](https://github.com/mastodon/mastodon/pull/18964))
- Change Helm configuration ([deepy](https://github.com/mastodon/mastodon/pull/18997), [jgsmith](https://github.com/mastodon/mastodon/pull/18415), [deepy](https://github.com/mastodon/mastodon/pull/18941))
### Removed
- Remove setting that disables account deletes ([Gargron](https://github.com/mastodon/mastodon/pull/17683))
- Remove digest e-mails ([Gargron](https://github.com/mastodon/mastodon/pull/17985))
- Remove unnecessary sections from welcome e-mail ([Gargron](https://github.com/mastodon/mastodon/pull/19299))
- Remove item titles from RSS feeds ([Gargron](https://github.com/mastodon/mastodon/pull/18640))
- Remove volume number from hashtags in web UI ([Gargron](https://github.com/mastodon/mastodon/pull/19253))
- Remove Nanobox configuration ([tonyjiang](https://github.com/mastodon/mastodon/pull/17881))
### Fixed
- Fix OCR not working due to Content Security Policy in web UI ([prplecake](https://github.com/mastodon/mastodon/pull/18817))
- Fix `nofollow` rel being removed in web UI ([Gargron](https://github.com/mastodon/mastodon/pull/19455))
- Fix language dropdown causing zoom on mobile devices in web UI ([Gargron](https://github.com/mastodon/mastodon/pull/19428))
- Fix button to dismiss suggestions not showing up in search results in web UI ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/19325))
- Fix language dropdown sometimes not appearing in web UI ([Gargron](https://github.com/mastodon/mastodon/pull/19246))
- Fix quickly switching notification filters resulting in empty or incorrect list in web UI ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/19052), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18960))
- Fix media modal link button in web UI ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18877))
- Fix error upon successful account migration ([Gargron](https://github.com/mastodon/mastodon/pull/19386))
- Fix negatives values in search index causing queries to fail ([Gargron](https://github.com/mastodon/mastodon/pull/19464), [Gargron](https://github.com/mastodon/mastodon/pull/19481))
- Fix error when searching for invalid URL ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18580))
- Fix IP blocks not having a unique index ([Gargron](https://github.com/mastodon/mastodon/pull/19456))
- Fix remote account in contact account setting not being used ([Gargron](https://github.com/mastodon/mastodon/pull/19351))
- Fix swallowing mentions of unconfirmed/unapproved users ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/19191))
- Fix incorrect and slow cache invalidation when blocking domain and removing media attachments ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/19062))
- Fix HTTPs redirect behaviour when running as I2P service ([gi-yt](https://github.com/mastodon/mastodon/pull/18929))
- Fix deleted pinned posts potentially counting towards the pinned posts limit ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/19005))
- Fix compatibility with OpenSSL 3.0 ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18449))
- Fix error when a remote report includes a private post the server has no access to ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18760))
- Fix suspicious sign-in mails never being sent ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18599))
- Fix fallback locale when somehow user's locale is an empty string ([tribela](https://github.com/mastodon/mastodon/pull/18543))
- Fix avatar/header not being deleted locally when deleted on remote account ([tribela](https://github.com/mastodon/mastodon/pull/18973))
- Fix missing `,` in Blurhash validation ([noellabo](https://github.com/mastodon/mastodon/pull/18660))
- Fix order by most recent not working for relationships page in admin UI ([tribela](https://github.com/mastodon/mastodon/pull/18996))
- Fix uncaught error when invalid date is supplied to API ([Gargron](https://github.com/mastodon/mastodon/pull/19480))
- Fix REST API sometimes returning HTML on error ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/19135))
- Fix ambiguous column names in `tootctl media refresh` ([tribela](https://github.com/mastodon/mastodon/pull/19206))
- Fix ambiguous column names in `tootctl search deploy` ([mashirozx](https://github.com/mastodon/mastodon/pull/18993))
- Fix `CDN_HOST` not being used in some asset URLs ([tribela](https://github.com/mastodon/mastodon/pull/18662))
- Fix `CAS_DISPLAY_NAME`, `SAML_DISPLAY_NAME` and `OIDC_DISPLAY_NAME` being ignored ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18568))
- Fix various typos in comments throughout the codebase ([luzpaz](https://github.com/mastodon/mastodon/pull/18604))
## [3.5.3] - 2022-05-26
### Added
@ -75,7 +201,7 @@ All notable changes to this project will be documented in this file.
- Remove IP matching from e-mail domain blocks ([Gargron](https://github.com/mastodon/mastodon/pull/18190))
- The IPs of the blocked e-mail domain or its MX records are no longer checked
- Previously it was too easy to block e-mail providers by mistake
## Fixed
- Fix compatibility with Friendica's pinned posts ([ClearlyClaire](https://github.com/mastodon/mastodon/pull/18254), [ClearlyClaire](https://github.com/mastodon/mastodon/pull/18260))

View file

@ -27,7 +27,7 @@ See the guidelines below.
- - -
You should also try to follow the guidelines set out in the original `CONTRIBUTING.md` from `tootsuite/mastodon`, reproduced below.
You should also try to follow the guidelines set out in the original `CONTRIBUTING.md` from `mastodon/mastodon`, reproduced below.
<blockquote>

View file

@ -72,6 +72,7 @@ gem 'rack-attack', '~> 6.6'
gem 'rack-cors', '~> 1.1', require: 'rack/cors'
gem 'rails-i18n', '~> 6.0'
gem 'rails-settings-cached', '~> 0.6'
gem 'redcarpet', '~> 3.5'
gem 'redis', '~> 4.5', require: ['redis', 'redis/connection/hiredis']
gem 'mario-redis-lock', '~> 1.2', require: 'redis_lock'
gem 'rqrcode', '~> 2.1'
@ -98,8 +99,6 @@ gem 'json-ld'
gem 'json-ld-preloaded', '~> 3.2'
gem 'rdf-normalize', '~> 0.5'
gem 'redcarpet', '~> 3.5'
group :development, :test do
gem 'fabrication', '~> 2.30'
gem 'fuubar', '~> 2.5'

View file

@ -272,7 +272,7 @@ GEM
fog-json (>= 1.0)
ipaddress (>= 0.8)
formatador (0.2.5)
fugit (1.5.3)
fugit (1.7.1)
et-orbi (~> 1, >= 1.2.7)
raabro (~> 1.4)
fuubar (2.5.1)
@ -600,7 +600,7 @@ GEM
nokogiri (>= 1.10.5)
rexml
ruby2_keywords (0.0.5)
rufus-scheduler (3.8.1)
rufus-scheduler (3.8.2)
fugit (~> 1.1, >= 1.1.6)
safety_net_attestation (0.4.0)
jwt (~> 2.0)
@ -617,10 +617,10 @@ GEM
redis (>= 4.5.0, < 5)
sidekiq-bulk (0.2.0)
sidekiq
sidekiq-scheduler (4.0.2)
sidekiq-scheduler (4.0.3)
redis (>= 4.2.0)
rufus-scheduler (~> 3.2)
sidekiq (>= 4)
sidekiq (>= 4, < 7)
tilt (>= 1.4.0)
sidekiq-unique-jobs (7.1.27)
brpoplpush-redis_script (> 0.1.1, <= 2.0.0)
@ -649,7 +649,7 @@ GEM
sshkit (1.21.2)
net-scp (>= 1.1.2)
net-ssh (>= 2.8.0)
stackprof (0.2.21)
stackprof (0.2.22)
statsd-ruby (1.5.0)
stoplight (3.0.0)
strong_migrations (0.7.9)
@ -664,7 +664,7 @@ GEM
terrapin (0.6.0)
climate_control (>= 0.0.3, < 1.0)
thor (1.2.1)
tilt (2.0.10)
tilt (2.0.11)
tpm-key_attestation (0.11.0)
bindata (~> 2.4)
openssl (> 2.0, < 3.1)

View file

@ -1,72 +1,19 @@
# frozen_string_literal: true
class AboutController < ApplicationController
include RegistrationSpamConcern
include WebAppControllerConcern
before_action :set_pack
skip_before_action :require_functional!
layout 'public'
before_action :require_open_federation!, only: [:show, :more]
before_action :set_body_classes, only: :show
before_action :set_instance_presenter
before_action :set_expires_in, only: [:more]
before_action :set_registration_form_time, only: :show
skip_before_action :require_functional!, only: [:more]
def show; end
def more
flash.now[:notice] = I18n.t('about.instance_actor_flash') if params[:instance_actor]
toc_generator = TOCGenerator.new(@instance_presenter.extended_description)
@rules = Rule.ordered
@contents = toc_generator.html
@table_of_contents = toc_generator.toc
@blocks = DomainBlock.with_user_facing_limitations.by_severity if display_blocks?
def show
expires_in 0, public: true unless user_signed_in?
end
helper_method :display_blocks?
helper_method :display_blocks_rationale?
helper_method :public_fetch_mode?
helper_method :new_user
private
def require_open_federation!
not_found if whitelist_mode?
end
def display_blocks?
Setting.show_domain_blocks == 'all' || (Setting.show_domain_blocks == 'users' && user_signed_in?)
end
def display_blocks_rationale?
Setting.show_domain_blocks_rationale == 'all' || (Setting.show_domain_blocks_rationale == 'users' && user_signed_in?)
end
def new_user
User.new.tap do |user|
user.build_account
user.build_invite_request
end
end
def set_pack
use_pack 'public'
end
def set_instance_presenter
@instance_presenter = InstancePresenter.new
end
def set_body_classes
@hide_navbar = true
end
def set_expires_in
expires_in 0, public: true
end
end

View file

@ -1,12 +0,0 @@
# frozen_string_literal: true
class AccountFollowController < ApplicationController
include AccountControllerConcern
before_action :authenticate_user!
def create
FollowService.new.call(current_user.account, @account, with_rate_limit: true)
redirect_to account_path(@account)
end
end

View file

@ -1,12 +0,0 @@
# frozen_string_literal: true
class AccountUnfollowController < ApplicationController
include AccountControllerConcern
before_action :authenticate_user!
def create
UnfollowService.new.call(current_user.account, @account)
redirect_to account_path(@account)
end
end

View file

@ -9,7 +9,6 @@ class AccountsController < ApplicationController
before_action :require_account_signature!, if: -> { request.format == :json && authorized_fetch_mode? }
before_action :set_cache_headers
before_action :set_body_classes
skip_around_action :set_locale, if: -> { [:json, :rss].include?(request.format&.to_sym) }
skip_before_action :require_functional!, unless: :whitelist_mode?
@ -17,26 +16,7 @@ class AccountsController < ApplicationController
def show
respond_to do |format|
format.html do
use_pack 'public'
expires_in 0, public: true unless user_signed_in?
@pinned_statuses = []
@endorsed_accounts = @account.endorsed_accounts.to_a.sample(4)
@featured_hashtags = @account.featured_tags.order(statuses_count: :desc)
if current_account && @account.blocking?(current_account)
@statuses = []
return
end
@pinned_statuses = cached_filtered_status_pins if show_pinned_statuses?
@statuses = cached_filtered_status_page
@rss_url = rss_url
unless @statuses.empty?
@older_url = older_url if @statuses.last.id > filtered_statuses.last.id
@newer_url = newer_url if @statuses.first.id < filtered_statuses.first.id
end
end
format.rss do
@ -56,18 +36,6 @@ class AccountsController < ApplicationController
private
def set_body_classes
@body_classes = 'with-modals'
end
def show_pinned_statuses?
[replies_requested?, media_requested?, tag_requested?, params[:max_id].present?, params[:min_id].present?].none?
end
def filtered_pinned_statuses
@account.pinned_statuses.not_local_only.where(visibility: [:public, :unlisted])
end
def filtered_statuses
default_statuses.tap do |statuses|
statuses.merge!(hashtag_scope) if tag_requested?
@ -114,26 +82,6 @@ class AccountsController < ApplicationController
end
end
def older_url
pagination_url(max_id: @statuses.last.id)
end
def newer_url
pagination_url(min_id: @statuses.first.id)
end
def pagination_url(max_id: nil, min_id: nil)
if tag_requested?
short_account_tag_url(@account, params[:tag], max_id: max_id, min_id: min_id)
elsif media_requested?
short_account_media_url(@account, max_id: max_id, min_id: min_id)
elsif replies_requested?
short_account_with_replies_url(@account, max_id: max_id, min_id: min_id)
else
short_account_url(@account, max_id: max_id, min_id: min_id)
end
end
def media_requested?
request.path.split('.').first.end_with?('/media') && !tag_requested?
end
@ -146,13 +94,6 @@ class AccountsController < ApplicationController
request.path.split('.').first.end_with?(Addressable::URI.parse("/tagged/#{params[:tag]}").normalize)
end
def cached_filtered_status_pins
cache_collection(
filtered_pinned_statuses,
Status
)
end
def cached_filtered_status_page
cache_collection_paginated_by_id(
filtered_statuses,

View file

@ -34,7 +34,7 @@ module Admin
@form = Form::CustomEmojiBatch.new(form_custom_emoji_batch_params.merge(current_account: current_account, action: action_from_button))
@form.save
rescue ActionController::ParameterMissing
flash[:alert] = I18n.t('admin.accounts.no_account_selected')
flash[:alert] = I18n.t('admin.custom_emojis.no_emoji_selected')
rescue Mastodon::NotPermittedError
flash[:alert] = I18n.t('admin.custom_emojis.not_permitted')
rescue ActiveRecord::RecordInvalid => e

View file

@ -62,7 +62,7 @@ module Admin
def export_data
CSV.generate(headers: export_headers, write_headers: true) do |content|
DomainBlock.with_user_facing_limitations.each do |instance|
DomainBlock.with_limitations.each do |instance|
content << [instance.domain, instance.severity, instance.reject_media, instance.reject_reports, instance.public_comment, instance.obfuscate]
end
end

View file

@ -5,7 +5,7 @@ module Admin
def index
authorize :ip_block, :index?
@ip_blocks = IpBlock.page(params[:page])
@ip_blocks = IpBlock.order(ip: :asc).page(params[:page])
@form = Form::IpBlockBatch.new
end

View file

@ -0,0 +1,9 @@
# frozen_string_literal: true
class Admin::Settings::AboutController < Admin::SettingsController
private
def after_update_redirect_path
admin_settings_about_path
end
end

View file

@ -0,0 +1,9 @@
# frozen_string_literal: true
class Admin::Settings::AppearanceController < Admin::SettingsController
private
def after_update_redirect_path
admin_settings_appearance_path
end
end

View file

@ -0,0 +1,9 @@
# frozen_string_literal: true
class Admin::Settings::BrandingController < Admin::SettingsController
private
def after_update_redirect_path
admin_settings_branding_path
end
end

View file

@ -0,0 +1,9 @@
# frozen_string_literal: true
class Admin::Settings::ContentRetentionController < Admin::SettingsController
private
def after_update_redirect_path
admin_settings_content_retention_path
end
end

View file

@ -0,0 +1,9 @@
# frozen_string_literal: true
class Admin::Settings::DiscoveryController < Admin::SettingsController
private
def after_update_redirect_path
admin_settings_discovery_path
end
end

View file

@ -0,0 +1,9 @@
# frozen_string_literal: true
class Admin::Settings::RegistrationsController < Admin::SettingsController
private
def after_update_redirect_path
admin_settings_registrations_path
end
end

View file

@ -2,7 +2,7 @@
module Admin
class SettingsController < BaseController
def edit
def show
authorize :settings, :show?
@admin_settings = Form::AdminSettings.new
@ -15,14 +15,18 @@ module Admin
if @admin_settings.save
flash[:notice] = I18n.t('generic.changes_saved_msg')
redirect_to edit_admin_settings_path
redirect_to after_update_redirect_path
else
render :edit
render :show
end
end
private
def after_update_redirect_path
raise NotImplementedError
end
def settings_params
params.require(:form_admin_settings).permit(*Form::AdminSettings::KEYS)
end

View file

@ -9,7 +9,7 @@ module Admin
@site_upload.destroy!
redirect_to edit_admin_settings_path, notice: I18n.t('admin.site_uploads.destroyed_msg')
redirect_to admin_settings_path, notice: I18n.t('admin.site_uploads.destroyed_msg')
end
private

View file

@ -3,18 +3,23 @@
module Admin
class StatusesController < BaseController
before_action :set_account
before_action :set_statuses
before_action :set_statuses, except: :show
before_action :set_status, only: :show
PER_PAGE = 20
def index
authorize :status, :index?
authorize [:admin, :status], :index?
@status_batch_action = Admin::StatusBatchAction.new
end
def show
authorize [:admin, @status], :show?
end
def batch
authorize :status, :index?
authorize [:admin, :status], :index?
@status_batch_action = Admin::StatusBatchAction.new(admin_status_batch_action_params.merge(current_account: current_account, report_id: params[:report_id], type: action_from_button))
@status_batch_action.save!
@ -32,6 +37,7 @@ module Admin
def after_create_redirect_path
report_id = @status_batch_action&.report_id || params[:report_id]
if report_id.present?
admin_report_path(report_id)
else
@ -43,6 +49,10 @@ module Admin
@account = Account.find(params[:account_id])
end
def set_status
@status = @account.statuses.find(params[:id])
end
def set_statuses
@statuses = Admin::StatusFilter.new(@account, filter_params).results.preload(:application, :preloadable_poll, :media_attachments, active_mentions: :account, reblog: [:account, :application, :preloadable_poll, :media_attachments, active_mentions: :account]).page(params[:page]).per(PER_PAGE)
end

View file

@ -14,7 +14,7 @@ class Admin::Trends::Links::PreviewCardProvidersController < Admin::BaseControll
@form = Trends::PreviewCardProviderBatch.new(trends_preview_card_provider_batch_params.merge(current_account: current_account, action: action_from_button))
@form.save
rescue ActionController::ParameterMissing
flash[:alert] = I18n.t('admin.accounts.no_account_selected')
flash[:alert] = I18n.t('admin.trends.links.publishers.no_publisher_selected')
ensure
redirect_to admin_trends_links_preview_card_providers_path(filter_params)
end

View file

@ -4,6 +4,7 @@ class Admin::Trends::LinksController < Admin::BaseController
def index
authorize :preview_card, :review?
@locales = PreviewCardTrend.pluck('distinct language')
@preview_cards = filtered_preview_cards.page(params[:page])
@form = Trends::PreviewCardBatch.new
end
@ -14,7 +15,7 @@ class Admin::Trends::LinksController < Admin::BaseController
@form = Trends::PreviewCardBatch.new(trends_preview_card_batch_params.merge(current_account: current_account, action: action_from_button))
@form.save
rescue ActionController::ParameterMissing
flash[:alert] = I18n.t('admin.accounts.no_account_selected')
flash[:alert] = I18n.t('admin.trends.links.no_link_selected')
ensure
redirect_to admin_trends_links_path(filter_params)
end

View file

@ -2,19 +2,20 @@
class Admin::Trends::StatusesController < Admin::BaseController
def index
authorize :status, :review?
authorize [:admin, :status], :review?
@locales = StatusTrend.pluck('distinct language')
@statuses = filtered_statuses.page(params[:page])
@form = Trends::StatusBatch.new
end
def batch
authorize :status, :review?
authorize [:admin, :status], :review?
@form = Trends::StatusBatch.new(trends_status_batch_params.merge(current_account: current_account, action: action_from_button))
@form.save
rescue ActionController::ParameterMissing
flash[:alert] = I18n.t('admin.accounts.no_account_selected')
flash[:alert] = I18n.t('admin.trends.statuses.no_status_selected')
ensure
redirect_to admin_trends_statuses_path(filter_params)
end

View file

@ -14,7 +14,7 @@ class Admin::Trends::TagsController < Admin::BaseController
@form = Trends::TagBatch.new(trends_tag_batch_params.merge(current_account: current_account, action: action_from_button))
@form.save
rescue ActionController::ParameterMissing
flash[:alert] = I18n.t('admin.accounts.no_account_selected')
flash[:alert] = I18n.t('admin.trends.tags.no_tag_selected')
ensure
redirect_to admin_trends_tags_path(filter_params)
end

View file

@ -24,6 +24,10 @@ class Api::BaseController < ApplicationController
render json: { error: 'Duplicate record' }, status: 422
end
rescue_from Date::Error do
render json: { error: 'Invalid date supplied' }, status: 422
end
rescue_from ActiveRecord::RecordNotFound do
render json: { error: 'Record not found' }, status: 404
end

View file

@ -60,14 +60,13 @@ class Api::V1::Admin::AccountsController < Api::BaseController
def reject
authorize @account.user, :reject?
DeleteAccountService.new.call(@account, reserve_email: false, reserve_username: false)
render json: @account, serializer: REST::Admin::AccountSerializer
render_empty
end
def destroy
authorize @account, :destroy?
json = render_to_body json: @account, serializer: REST::Admin::AccountSerializer
Admin::AccountDeletionWorker.perform_async(@account.id)
render json: json
render_empty
end
def unsensitive

View file

@ -35,20 +35,16 @@ class Api::V1::Admin::CanonicalEmailBlocksController < Api::BaseController
def create
authorize :canonical_email_block, :create?
@canonical_email_block = CanonicalEmailBlock.create!(resource_params)
log_action :create, @canonical_email_block
render json: @canonical_email_block, serializer: REST::Admin::CanonicalEmailBlockSerializer
end
def destroy
authorize @canonical_email_block, :destroy?
@canonical_email_block.destroy!
log_action :destroy, @canonical_email_block
render json: @canonical_email_block, serializer: REST::Admin::CanonicalEmailBlockSerializer
render_empty
end
private

View file

@ -43,7 +43,7 @@ class Api::V1::Admin::DomainAllowsController < Api::BaseController
authorize @domain_allow, :destroy?
UnallowDomainService.new.call(@domain_allow)
log_action :destroy, @domain_allow
render json: @domain_allow, serializer: REST::Admin::DomainAllowSerializer
render_empty
end
private

View file

@ -40,7 +40,6 @@ class Api::V1::Admin::DomainBlocksController < Api::BaseController
def update
authorize @domain_block, :update?
@domain_block.update(domain_block_params)
severity_changed = @domain_block.severity_changed?
@domain_block.save!
@ -53,7 +52,7 @@ class Api::V1::Admin::DomainBlocksController < Api::BaseController
authorize @domain_block, :destroy?
UnblockDomainService.new.call(@domain_block)
log_action :destroy, @domain_block
render json: @domain_block, serializer: REST::Admin::DomainBlockSerializer
render_empty
end
private

View file

@ -39,11 +39,9 @@ class Api::V1::Admin::EmailDomainBlocksController < Api::BaseController
def destroy
authorize @email_domain_block, :destroy?
@email_domain_block.destroy!
log_action :destroy, @email_domain_block
render json: @email_domain_block, serializer: REST::Admin::EmailDomainBlockSerializer
render_empty
end
private

View file

@ -20,10 +20,8 @@ class Api::V1::Admin::IpBlocksController < Api::BaseController
def create
authorize :ip_block, :create?
@ip_block = IpBlock.create!(resource_params)
log_action :create, @ip_block
render json: @ip_block, serializer: REST::Admin::IpBlockSerializer
end
@ -39,20 +37,16 @@ class Api::V1::Admin::IpBlocksController < Api::BaseController
def update
authorize @ip_block, :update?
@ip_block.update(resource_params)
log_action :update, @ip_block
render json: @ip_block, serializer: REST::Admin::IpBlockSerializer
end
def destroy
authorize @ip_block, :destroy?
@ip_block.destroy!
log_action :destroy, @ip_block
render json: @ip_block, serializer: REST::Admin::IpBlockSerializer
render_empty
end
private

View file

@ -13,12 +13,12 @@ class Api::V1::FeaturedTagsController < Api::BaseController
end
def create
@featured_tag = current_account.featured_tags.create!(featured_tag_params)
render json: @featured_tag, serializer: REST::FeaturedTagSerializer
featured_tag = CreateFeaturedTagService.new.call(current_account, featured_tag_params[:name])
render json: featured_tag, serializer: REST::FeaturedTagSerializer
end
def destroy
@featured_tag.destroy!
RemoveFeaturedTagWorker.perform_async(current_account.id, @featured_tag.id)
render_empty
end

View file

@ -0,0 +1,23 @@
# frozen_string_literal: true
class Api::V1::Instances::DomainBlocksController < Api::BaseController
skip_before_action :require_authenticated_user!, unless: :whitelist_mode?
before_action :require_enabled_api!
before_action :set_domain_blocks
def index
expires_in 3.minutes, public: true
render json: @domain_blocks, each_serializer: REST::DomainBlockSerializer, with_comment: (Setting.show_domain_blocks_rationale == 'all' || (Setting.show_domain_blocks_rationale == 'users' && user_signed_in?))
end
private
def require_enabled_api!
head 404 unless Setting.show_domain_blocks == 'all' || (Setting.show_domain_blocks == 'users' && user_signed_in?)
end
def set_domain_blocks
@domain_blocks = DomainBlock.with_user_facing_limitations.by_severity
end
end

View file

@ -0,0 +1,18 @@
# frozen_string_literal: true
class Api::V1::Instances::ExtendedDescriptionsController < Api::BaseController
skip_before_action :require_authenticated_user!, unless: :whitelist_mode?
before_action :set_extended_description
def show
expires_in 3.minutes, public: true
render json: @extended_description, serializer: REST::ExtendedDescriptionSerializer
end
private
def set_extended_description
@extended_description = ExtendedDescription.current
end
end

View file

@ -0,0 +1,18 @@
# frozen_string_literal: true
class Api::V1::Instances::PrivacyPoliciesController < Api::BaseController
skip_before_action :require_authenticated_user!, unless: :whitelist_mode?
before_action :set_privacy_policy
def show
expires_in 1.day, public: true
render json: @privacy_policy, serializer: REST::PrivacyPolicySerializer
end
private
def set_privacy_policy
@privacy_policy = PrivacyPolicy.current
end
end

View file

@ -66,6 +66,7 @@ class Api::V1::StatusesController < Api::BaseController
text: status_params[:status],
media_ids: status_params[:media_ids],
sensitive: status_params[:sensitive],
language: status_params[:language],
spoiler_text: status_params[:spoiler_text],
poll: status_params[:poll],
content_type: status_params[:content_type]
@ -79,6 +80,7 @@ class Api::V1::StatusesController < Api::BaseController
authorize @status, :destroy?
@status.discard
StatusPin.find_by(status: @status)&.destroy
@status.account.statuses_count = @status.account.statuses_count - 1
json = render_to_body json: @status, serializer: REST::StatusSerializer, source_requested: true

View file

@ -35,6 +35,7 @@ class Api::V1::Timelines::PublicController < Api::BaseController
def public_feed
PublicFeed.new(
current_account,
locale: content_locale,
local: truthy_param?(:local),
remote: truthy_param?(:remote),
only_media: truthy_param?(:only_media),

View file

@ -28,7 +28,9 @@ class Api::V1::Trends::LinksController < Api::BaseController
end
def links_from_trends
Trends.links.query.allowed.in_locale(content_locale)
scope = Trends.links.query.allowed.in_locale(content_locale)
scope = scope.filtered_for(current_account) if user_signed_in?
scope
end
def insert_pagination_headers

View file

@ -5,8 +5,8 @@ class Api::V2::SearchController < Api::BaseController
RESULTS_LIMIT = (ENV['MAX_SEARCH_RESULTS'] || 20).to_i
before_action -> { doorkeeper_authorize! :read, :'read:search' }
before_action :require_user!
before_action -> { authorize_if_got_token! :read, :'read:search' }
before_action :validate_search_params!
def index
@search = Search.new(search_results)
@ -19,6 +19,16 @@ class Api::V2::SearchController < Api::BaseController
private
def validate_search_params!
params.require(:q)
return if user_signed_in?
return render json: { error: 'Search queries pagination is not supported without authentication' }, status: 401 if params[:offset].present?
render json: { error: 'Search queries that resolve remote resources are not supported without authentication' }, status: 401 if truthy_param?(:resolve)
end
def search_results
SearchService.new.call(
params[:q],

View file

@ -15,6 +15,8 @@ class Auth::RegistrationsController < Devise::RegistrationsController
before_action :set_body_classes, only: [:new, :create, :edit, :update]
before_action :require_not_suspended!, only: [:update]
before_action :set_cache_headers, only: [:edit, :update]
before_action :set_rules, only: :new
before_action :require_rules_acceptance!, only: :new
before_action :set_registration_form_time, only: :new
skip_before_action :require_functional!, only: [:edit, :update]
@ -56,7 +58,7 @@ class Auth::RegistrationsController < Devise::RegistrationsController
def configure_sign_up_params
devise_parameter_sanitizer.permit(:sign_up) do |u|
u.permit({ account_attributes: [:username], invite_request_attributes: [:text] }, :email, :password, :password_confirmation, :invite_code, :agreement, :website, :confirm_password)
u.permit({ account_attributes: [:username, :display_name], invite_request_attributes: [:text] }, :email, :password, :password_confirmation, :invite_code, :agreement, :website, :confirm_password)
end
end
@ -143,6 +145,19 @@ class Auth::RegistrationsController < Devise::RegistrationsController
forbidden if current_account.suspended?
end
def set_rules
@rules = Rule.ordered
end
def require_rules_acceptance!
return if @rules.empty? || (session[:accept_token].present? && params[:accept] == session[:accept_token])
@accept_token = session[:accept_token] = SecureRandom.hex
@invite_code = invite_code
set_locale { render :rules }
end
def set_cache_headers
response.headers['Cache-Control'] = 'no-cache, no-store, max-age=0, must-revalidate'
end

View file

@ -3,13 +3,12 @@
module AccountControllerConcern
extend ActiveSupport::Concern
include WebAppControllerConcern
include AccountOwnedConcern
FOLLOW_PER_PAGE = 12
included do
layout 'public'
before_action :set_instance_presenter
before_action :set_link_headers, if: -> { request.format.nil? || request.format == :html }
end

View file

@ -0,0 +1,32 @@
# frozen_string_literal: true
module WebAppControllerConcern
extend ActiveSupport::Concern
included do
before_action :set_pack
before_action :redirect_unauthenticated_to_permalinks!
before_action :set_app_body_class
before_action :set_referrer_policy_header
end
def set_app_body_class
@body_classes = 'app-body'
end
def set_referrer_policy_header
response.headers['Referrer-Policy'] = 'origin'
end
def redirect_unauthenticated_to_permalinks!
return if user_signed_in?
redirect_path = PermalinkRedirector.new(request.path).redirect_path
redirect_to(redirect_path) if redirect_path.present?
end
def set_pack
use_pack 'home'
end
end

View file

@ -1,37 +0,0 @@
# frozen_string_literal: true
class DirectoriesController < ApplicationController
layout 'public'
before_action :authenticate_user!, if: :whitelist_mode?
before_action :require_enabled!
before_action :set_instance_presenter
before_action :set_accounts
before_action :set_pack
skip_before_action :require_functional!, unless: :whitelist_mode?
def index
render :index
end
private
def set_pack
use_pack 'share'
end
def require_enabled!
return not_found unless Setting.profile_directory
end
def set_accounts
@accounts = Account.local.discoverable.by_recent_status.page(params[:page]).per(20).tap do |query|
query.merge!(Account.not_excluded_by_account(current_account)) if current_account
end
end
def set_instance_presenter
@instance_presenter = InstancePresenter.new
end
end

View file

@ -3,6 +3,7 @@
class FollowerAccountsController < ApplicationController
include AccountControllerConcern
include SignatureVerification
include WebAppControllerConcern
before_action :require_account_signature!, if: -> { request.format == :json && authorized_fetch_mode? }
before_action :set_cache_headers
@ -13,12 +14,7 @@ class FollowerAccountsController < ApplicationController
def index
respond_to do |format|
format.html do
use_pack 'public'
expires_in 0, public: true unless user_signed_in?
next if @account.hide_collections?
follows
end
format.json do

View file

@ -3,6 +3,7 @@
class FollowingAccountsController < ApplicationController
include AccountControllerConcern
include SignatureVerification
include WebAppControllerConcern
before_action :require_account_signature!, if: -> { request.format == :json && authorized_fetch_mode? }
before_action :set_cache_headers
@ -13,12 +14,7 @@ class FollowingAccountsController < ApplicationController
def index
respond_to do |format|
format.html do
use_pack 'public'
expires_in 0, public: true unless user_signed_in?
next if @account.hide_collections?
follows
end
format.json do

View file

@ -1,47 +1,16 @@
# frozen_string_literal: true
class HomeController < ApplicationController
before_action :redirect_unauthenticated_to_permalinks!
include WebAppControllerConcern
before_action :set_pack
before_action :set_referrer_policy_header
before_action :set_instance_presenter
def index
@body_classes = 'app-body'
expires_in 0, public: true unless user_signed_in?
end
private
def redirect_unauthenticated_to_permalinks!
return if user_signed_in?
redirect_path = PermalinkRedirector.new(request.path).redirect_path
redirect_path ||= default_redirect_path
redirect_to(redirect_path) if redirect_path.present?
end
def set_pack
use_pack 'home'
end
def default_redirect_path
if whitelist_mode?
new_user_session_path
elsif request.path.start_with?('/web')
nil
elsif single_user_mode?
short_account_path(Account.local.without_suspended.where('id > 0').first)
else
about_path
end
end
def set_referrer_policy_header
response.headers['Referrer-Policy'] = 'origin'
end
def set_instance_presenter
@instance_presenter = InstancePresenter.new
end

View file

@ -1,28 +1,19 @@
# frozen_string_literal: true
class PrivacyController < ApplicationController
layout 'public'
before_action :set_pack
before_action :set_instance_presenter
before_action :set_expires_in
include WebAppControllerConcern
skip_before_action :require_functional!
def show; end
before_action :set_instance_presenter
def show
expires_in 0, public: true if current_account.nil?
end
private
def set_pack
use_pack 'public'
end
def set_instance_presenter
@instance_presenter = InstancePresenter.new
end
def set_expires_in
expires_in 0, public: true
end
end

View file

@ -1,31 +0,0 @@
# frozen_string_literal: true
class PublicTimelinesController < ApplicationController
before_action :set_pack
layout 'public'
before_action :authenticate_user!, if: :whitelist_mode?
before_action :require_enabled!
before_action :set_body_classes
before_action :set_instance_presenter
def show; end
private
def require_enabled!
not_found unless Setting.timeline_preview
end
def set_body_classes
@body_classes = 'with-modals'
end
def set_instance_presenter
@instance_presenter = InstancePresenter.new
end
def set_pack
use_pack 'about'
end
end

View file

@ -1,46 +0,0 @@
# frozen_string_literal: true
class RemoteFollowController < ApplicationController
include AccountOwnedConcern
layout 'modal'
before_action :set_pack
before_action :set_body_classes
skip_before_action :require_functional!
def new
@remote_follow = RemoteFollow.new(session_params)
end
def create
@remote_follow = RemoteFollow.new(resource_params)
if @remote_follow.valid?
session[:remote_follow] = @remote_follow.acct
redirect_to @remote_follow.subscribe_address_for(@account)
else
render :new
end
end
private
def resource_params
params.require(:remote_follow).permit(:acct)
end
def session_params
{ acct: session[:remote_follow] || current_account&.username }
end
def set_pack
use_pack 'modal'
end
def set_body_classes
@body_classes = 'modal-layout'
@hide_header = true
end
end

View file

@ -1,60 +0,0 @@
# frozen_string_literal: true
class RemoteInteractionController < ApplicationController
include Authorization
layout 'modal'
before_action :authenticate_user!, if: :whitelist_mode?
before_action :set_interaction_type
before_action :set_status
before_action :set_body_classes
before_action :set_pack
skip_before_action :require_functional!, unless: :whitelist_mode?
def new
@remote_follow = RemoteFollow.new(session_params)
end
def create
@remote_follow = RemoteFollow.new(resource_params)
if @remote_follow.valid?
session[:remote_follow] = @remote_follow.acct
redirect_to @remote_follow.interact_address_for(@status)
else
render :new
end
end
private
def resource_params
params.require(:remote_follow).permit(:acct)
end
def session_params
{ acct: session[:remote_follow] || current_account&.username }
end
def set_status
@status = Status.find(params[:id])
authorize @status, :show?
rescue Mastodon::NotPermittedError
not_found
end
def set_body_classes
@body_classes = 'modal-layout'
@hide_header = true
end
def set_pack
use_pack 'modal'
end
def set_interaction_type
@interaction_type = %w(reply reblog favourite).include?(params[:type]) ? params[:type] : 'reply'
end
end

View file

@ -4,7 +4,6 @@ class Settings::DeletesController < Settings::BaseController
skip_before_action :require_functional!
before_action :require_not_suspended!
before_action :check_enabled_deletion
def show
@confirmation = Form::DeleteConfirmation.new
@ -21,10 +20,6 @@ class Settings::DeletesController < Settings::BaseController
private
def check_enabled_deletion
redirect_to root_path unless Setting.open_deletion
end
def resource_params
params.require(:form_delete_confirmation).permit(:password, :username)
end

View file

@ -10,9 +10,9 @@ class Settings::FeaturedTagsController < Settings::BaseController
end
def create
@featured_tag = current_account.featured_tags.new(featured_tag_params)
@featured_tag = CreateFeaturedTagService.new.call(current_account, featured_tag_params[:name], force: false)
if @featured_tag.save
if @featured_tag.valid?
redirect_to settings_featured_tags_path
else
set_featured_tags
@ -23,7 +23,7 @@ class Settings::FeaturedTagsController < Settings::BaseController
end
def destroy
@featured_tag.destroy!
RemoveFeaturedTagWorker.perform_async(current_account.id, @featured_tag.id)
redirect_to settings_featured_tags_path
end

View file

@ -1,21 +1,19 @@
# frozen_string_literal: true
class StatusesController < ApplicationController
include WebAppControllerConcern
include StatusControllerConcern
include SignatureAuthentication
include Authorization
include AccountOwnedConcern
layout 'public'
before_action :require_account_signature!, only: [:show, :activity], if: -> { request.format == :json && authorized_fetch_mode? }
before_action :set_status
before_action :set_instance_presenter
before_action :set_link_headers
before_action :redirect_to_original, only: :show
before_action :set_referrer_policy_header, only: :show
before_action :set_cache_headers
before_action :set_body_classes
before_action :set_body_classes, only: :embed
skip_around_action :set_locale, if: -> { request.format == :json }
skip_before_action :require_functional!, only: [:show, :embed], unless: :whitelist_mode?
@ -27,11 +25,7 @@ class StatusesController < ApplicationController
def show
respond_to do |format|
format.html do
use_pack 'public'
expires_in 10.seconds, public: true if current_account.nil?
set_ancestors
set_descendants
end
format.json do
@ -80,8 +74,4 @@ class StatusesController < ApplicationController
def redirect_to_original
redirect_to ActivityPub::TagManager.instance.url_for(@status.reblog) if @status.reblog?
end
def set_referrer_policy_header
response.headers['Referrer-Policy'] = 'origin' unless @status.distributable?
end
end

View file

@ -2,18 +2,16 @@
class TagsController < ApplicationController
include SignatureVerification
include WebAppControllerConcern
PAGE_SIZE = 20
PAGE_SIZE_MAX = 200
layout 'public'
before_action :require_account_signature!, if: -> { request.format == :json && authorized_fetch_mode? }
before_action :authenticate_user!, if: :whitelist_mode?
before_action :set_local
before_action :set_tag
before_action :set_statuses
before_action :set_body_classes
before_action :set_instance_presenter
skip_before_action :require_functional!, unless: :whitelist_mode?
@ -21,8 +19,7 @@ class TagsController < ApplicationController
def show
respond_to do |format|
format.html do
use_pack 'about'
expires_in 0, public: true
expires_in 0, public: true unless user_signed_in?
end
format.rss do
@ -55,10 +52,6 @@ class TagsController < ApplicationController
end
end
def set_body_classes
@body_classes = 'with-modals'
end
def set_instance_presenter
@instance_presenter = InstancePresenter.new
end

View file

@ -20,54 +20,10 @@ module AccountsHelper
end
def account_action_button(account)
if user_signed_in?
if account.id == current_user.account_id
link_to settings_profile_url, class: 'button logo-button' do
safe_join([logo_as_symbol, t('settings.edit_profile')])
end
elsif current_account.following?(account) || current_account.requested?(account)
link_to account_unfollow_path(account), class: 'button logo-button button--destructive', data: { method: :post } do
safe_join([logo_as_symbol, t('accounts.unfollow')])
end
elsif !(account.memorial? || account.moved?)
link_to account_follow_path(account), class: "button logo-button#{account.blocking?(current_account) ? ' disabled' : ''}", data: { method: :post } do
safe_join([logo_as_symbol, t('accounts.follow')])
end
end
elsif !(account.memorial? || account.moved?)
link_to account_remote_follow_path(account), class: 'button logo-button modal-button', target: '_new' do
safe_join([logo_as_symbol, t('accounts.follow')])
end
end
end
return if account.memorial? || account.moved?
def minimal_account_action_button(account)
if user_signed_in?
return if account.id == current_user.account_id
if current_account.following?(account) || current_account.requested?(account)
link_to account_unfollow_path(account), class: 'icon-button active', data: { method: :post }, title: t('accounts.unfollow') do
fa_icon('user-times fw')
end
elsif !(account.memorial? || account.moved?)
link_to account_follow_path(account), class: "icon-button#{account.blocking?(current_account) ? ' disabled' : ''}", data: { method: :post }, title: t('accounts.follow') do
fa_icon('user-plus fw')
end
end
elsif !(account.memorial? || account.moved?)
link_to account_remote_follow_path(account), class: 'icon-button modal-button', target: '_new', title: t('accounts.follow') do
fa_icon('user-plus fw')
end
end
end
def account_badge(account)
if account.bot?
content_tag(:div, content_tag(:div, t('accounts.roles.bot'), class: 'account-role bot'), class: 'roles')
elsif account.group?
content_tag(:div, content_tag(:div, t('accounts.roles.group'), class: 'account-role group'), class: 'roles')
elsif account.user_role&.highlighted?
content_tag(:div, content_tag(:div, account.user_role.name, class: "account-role user-role-#{account.user_role.id}"), class: 'roles')
link_to ActivityPub::TagManager.instance.url_for(account), class: 'button logo-button', target: '_new' do
safe_join([logo_as_symbol, t('accounts.follow')])
end
end

View file

@ -1,14 +1,6 @@
# frozen_string_literal: true
module Admin::SettingsHelper
def site_upload_delete_hint(hint, var)
upload = SiteUpload.find_by(var: var.to_s)
return hint unless upload
link = link_to t('admin.site_uploads.delete'), admin_site_upload_path(upload), data: { method: :delete }
safe_join([hint, link], '<br/>'.html_safe)
end
def captcha_available?
ENV['HCAPTCHA_SECRET_KEY'].present? && ENV['HCAPTCHA_SITE_KEY'].present?
end

View file

@ -87,10 +87,6 @@ module ApplicationHelper
link_to label, omniauth_authorize_path(:user, provider), class: "button button-#{provider}", method: :post
end
def open_deletion?
Setting.open_deletion
end
def locale_direction
if RTL_LOCALES.include?(I18n.locale)
'rtl'
@ -199,10 +195,7 @@ module ApplicationHelper
def render_initial_state
state_params = {
settings: {
known_fediverse: Setting.show_known_fediverse_at_about_page,
},
settings: {},
text: [params[:title], params[:text], params[:url]].compact.join(' '),
}
@ -219,6 +212,10 @@ module ApplicationHelper
state_params[:admin] = Account.find_local(Setting.site_contact_username.strip.gsub(/\A@/, ''))
end
if single_user_mode?
state_params[:owner] = Account.local.without_suspended.where('id > 0').first
end
json = ActiveModelSerializers::SerializableResource.new(InitialStatePresenter.new(state_params), serializer: InitialStateSerializer).to_json
# rubocop:disable Rails/OutputSafety
content_tag(:script, json_escape(json).html_safe, id: 'initial-state', type: 'application/json')

View file

@ -23,7 +23,7 @@ module HomeHelper
else
link_to(path || ActivityPub::TagManager.instance.url_for(account), class: 'account__display-name') do
content_tag(:div, class: 'account__avatar-wrapper') do
image_tag(full_asset_url(current_account&.user&.setting_auto_play_gif ? account.avatar_original_url : account.avatar_static_url), class: 'account__avatar')
image_tag(full_asset_url(current_account&.user&.setting_auto_play_gif ? account.avatar_original_url : account.avatar_static_url), class: 'account__avatar', width: 46, height: 46)
end +
content_tag(:span, class: 'display-name') do
content_tag(:bdi) do

View file

@ -97,7 +97,7 @@ module LanguagesHelper
lg: ['Ganda', 'Luganda'].freeze,
li: ['Limburgish', 'Limburgs'].freeze,
ln: ['Lingala', 'Lingála'].freeze,
lo: ['Lao', 'ພາສາ'].freeze,
lo: ['Lao', 'ລາວ'].freeze,
lt: ['Lithuanian', 'lietuvių kalba'].freeze,
lu: ['Luba-Katanga', 'Tshiluba'].freeze,
lv: ['Latvian', 'latviešu valoda'].freeze,

View file

@ -4,6 +4,24 @@ import 'packs/public-path';
import { delegate } from '@rails/ujs';
import ready from '../mastodon/ready';
const setAnnouncementEndsAttributes = (target) => {
const valid = target?.value && target?.validity?.valid;
const element = document.querySelector('input[type="datetime-local"]#announcement_ends_at');
if (valid) {
element.classList.remove('optional');
element.required = true;
element.min = target.value;
} else {
element.classList.add('optional');
element.removeAttribute('required');
element.removeAttribute('min');
}
};
delegate(document, 'input[type="datetime-local"]#announcement_starts_at', 'change', ({ target }) => {
setAnnouncementEndsAttributes(target);
});
const batchCheckboxClassName = '.batch-checkbox input[type="checkbox"]';
const showSelectAll = () => {
@ -143,6 +161,20 @@ const onChangeRegistrationMode = (target) => {
});
};
const convertUTCDateTimeToLocal = (value) => {
const date = new Date(value + 'Z');
const twoChars = (x) => (x.toString().padStart(2, '0'));
return `${date.getFullYear()}-${twoChars(date.getMonth()+1)}-${twoChars(date.getDate())}T${twoChars(date.getHours())}:${twoChars(date.getMinutes())}`;
};
const convertLocalDatetimeToUTC = (value) => {
const re = /^([0-9]{4,})-([0-9]{2})-([0-9]{2})T([0-9]{2}):([0-9]{2})/;
const match = re.exec(value);
const date = new Date(match[1], match[2] - 1, match[3], match[4], match[5]);
const fullISO8601 = date.toISOString();
return fullISO8601.slice(0, fullISO8601.indexOf('T') + 6);
};
delegate(document, '#form_admin_settings_registrations_mode', 'change', ({ target }) => onChangeRegistrationMode(target));
ready(() => {
@ -170,4 +202,26 @@ ready(() => {
e.target.href = url;
}
});
[].forEach.call(document.querySelectorAll('input[type="datetime-local"]'), element => {
if (element.value) {
element.value = convertUTCDateTimeToLocal(element.value);
}
if (element.placeholder) {
element.placeholder = convertUTCDateTimeToLocal(element.placeholder);
}
});
delegate(document, 'form', 'submit', ({ target }) => {
[].forEach.call(target.querySelectorAll('input[type="datetime-local"]'), element => {
if (element.value && element.validity.valid) {
element.value = convertLocalDatetimeToUTC(element.value);
}
});
});
const announcementStartsAt = document.querySelector('input[type="datetime-local"]#announcement_starts_at');
if (announcementStartsAt) {
setAnnouncementEndsAttributes(announcementStartsAt);
}
});

View file

@ -6,28 +6,6 @@ import ready from '../mastodon/ready';
const { delegate } = require('@rails/ujs');
const { length } = require('stringz');
delegate(document, '.webapp-btn', 'click', ({ target, button }) => {
if (button !== 0) {
return true;
}
window.location.href = target.href;
return false;
});
delegate(document, '.modal-button', 'click', e => {
e.preventDefault();
let href;
if (e.target.nodeName !== 'A') {
href = e.target.parentNode.href;
} else {
href = e.target.href;
}
window.open(href, 'mastodon-intent', 'width=445,height=600,resizable=no,menubar=no,status=no,scrollbars=yes');
});
const getProfileAvatarAnimationHandler = (swapTo) => {
//animate avatar gifs on the profile page when moused over
return ({ target }) => {

View file

@ -1,19 +1,21 @@
import api from '../api';
import { CancelToken, isCancel } from 'axios';
import axios from 'axios';
import { throttle } from 'lodash';
import { defineMessages } from 'react-intl';
import api from 'flavours/glitch/api';
import { search as emojiSearch } from 'flavours/glitch/features/emoji/emoji_mart_search_light';
import { useEmoji } from './emojis';
import { tagHistory } from '../settings';
import { tagHistory } from 'flavours/glitch/settings';
import { recoverHashtags } from 'flavours/glitch/utils/hashtag';
import resizeImage from 'flavours/glitch/utils/resize_image';
import { showAlert, showAlertForError } from './alerts';
import { useEmoji } from './emojis';
import { importFetchedAccounts } from './importer';
import { updateTimeline } from './timelines';
import { showAlertForError } from './alerts';
import { showAlert } from './alerts';
import { openModal } from './modal';
import { defineMessages } from 'react-intl';
import { updateTimeline } from './timelines';
let cancelFetchComposeSuggestionsAccounts, cancelFetchComposeSuggestionsTags;
/** @type {AbortController | undefined} */
let fetchComposeSuggestionsAccountsController;
/** @type {AbortController | undefined} */
let fetchComposeSuggestionsTagsController;
export const COMPOSE_CHANGE = 'COMPOSE_CHANGE';
export const COMPOSE_CYCLE_ELEFRIEND = 'COMPOSE_CYCLE_ELEFRIEND';
@ -25,11 +27,13 @@ export const COMPOSE_REPLY_CANCEL = 'COMPOSE_REPLY_CANCEL';
export const COMPOSE_DIRECT = 'COMPOSE_DIRECT';
export const COMPOSE_MENTION = 'COMPOSE_MENTION';
export const COMPOSE_RESET = 'COMPOSE_RESET';
export const COMPOSE_UPLOAD_REQUEST = 'COMPOSE_UPLOAD_REQUEST';
export const COMPOSE_UPLOAD_SUCCESS = 'COMPOSE_UPLOAD_SUCCESS';
export const COMPOSE_UPLOAD_FAIL = 'COMPOSE_UPLOAD_FAIL';
export const COMPOSE_UPLOAD_PROGRESS = 'COMPOSE_UPLOAD_PROGRESS';
export const COMPOSE_UPLOAD_UNDO = 'COMPOSE_UPLOAD_UNDO';
export const COMPOSE_UPLOAD_REQUEST = 'COMPOSE_UPLOAD_REQUEST';
export const COMPOSE_UPLOAD_SUCCESS = 'COMPOSE_UPLOAD_SUCCESS';
export const COMPOSE_UPLOAD_FAIL = 'COMPOSE_UPLOAD_FAIL';
export const COMPOSE_UPLOAD_PROGRESS = 'COMPOSE_UPLOAD_PROGRESS';
export const COMPOSE_UPLOAD_PROCESSING = 'COMPOSE_UPLOAD_PROCESSING';
export const COMPOSE_UPLOAD_UNDO = 'COMPOSE_UPLOAD_UNDO';
export const THUMBNAIL_UPLOAD_REQUEST = 'THUMBNAIL_UPLOAD_REQUEST';
export const THUMBNAIL_UPLOAD_SUCCESS = 'THUMBNAIL_UPLOAD_SUCCESS';
@ -83,10 +87,8 @@ const messages = defineMessages({
uploadErrorPoll: { id: 'upload_error.poll', defaultMessage: 'File upload not allowed with polls.' },
});
const COMPOSE_PANEL_BREAKPOINT = 600 + (285 * 1) + (10 * 1);
export const ensureComposeIsVisible = (getState, routerHistory) => {
if (!getState().getIn(['compose', 'mounted']) && window.innerWidth < COMPOSE_PANEL_BREAKPOINT) {
if (!getState().getIn(['compose', 'mounted'])) {
routerHistory.push('/publish');
}
};
@ -307,13 +309,16 @@ export function uploadCompose(files) {
if (status === 200) {
dispatch(uploadComposeSuccess(data, f));
} else if (status === 202) {
dispatch(uploadComposeProcessing());
let tryCount = 1;
const poll = () => {
api(getState).get(`/api/v1/media/${data.id}`).then(response => {
if (response.status === 200) {
dispatch(uploadComposeSuccess(response.data, f));
} else if (response.status === 206) {
let retryAfter = (Math.log2(tryCount) || 1) * 1000;
const retryAfter = (Math.log2(tryCount) || 1) * 1000;
tryCount += 1;
setTimeout(() => poll(), retryAfter);
}
@ -328,6 +333,10 @@ export function uploadCompose(files) {
};
};
export const uploadComposeProcessing = () => ({
type: COMPOSE_UPLOAD_PROCESSING,
});
export const uploadThumbnail = (id, file) => (dispatch, getState) => {
dispatch(uploadThumbnailRequest());
@ -472,8 +481,8 @@ export function undoUploadCompose(media_id) {
};
export function clearComposeSuggestions() {
if (cancelFetchComposeSuggestionsAccounts) {
cancelFetchComposeSuggestionsAccounts();
if (fetchComposeSuggestionsAccountsController) {
fetchComposeSuggestionsAccountsController.abort();
}
return {
type: COMPOSE_SUGGESTIONS_CLEAR,
@ -481,14 +490,14 @@ export function clearComposeSuggestions() {
};
const fetchComposeSuggestionsAccounts = throttle((dispatch, getState, token) => {
if (cancelFetchComposeSuggestionsAccounts) {
cancelFetchComposeSuggestionsAccounts();
if (fetchComposeSuggestionsAccountsController) {
fetchComposeSuggestionsAccountsController.abort();
}
fetchComposeSuggestionsAccountsController = new AbortController();
api(getState).get('/api/v1/accounts/search', {
cancelToken: new CancelToken(cancel => {
cancelFetchComposeSuggestionsAccounts = cancel;
}),
signal: fetchComposeSuggestionsAccountsController.signal,
params: {
q: token.slice(1),
@ -499,9 +508,11 @@ const fetchComposeSuggestionsAccounts = throttle((dispatch, getState, token) =>
dispatch(importFetchedAccounts(response.data));
dispatch(readyComposeSuggestionsAccounts(token, response.data));
}).catch(error => {
if (!isCancel(error)) {
if (!axios.isCancel(error)) {
dispatch(showAlertForError(error));
}
}).finally(() => {
fetchComposeSuggestionsAccountsController = undefined;
});
}, 200, { leading: true, trailing: true });
@ -511,16 +522,16 @@ const fetchComposeSuggestionsEmojis = (dispatch, getState, token) => {
};
const fetchComposeSuggestionsTags = throttle((dispatch, getState, token) => {
if (cancelFetchComposeSuggestionsTags) {
cancelFetchComposeSuggestionsTags();
if (fetchComposeSuggestionsTagsController) {
fetchComposeSuggestionsTagsController.abort();
}
dispatch(updateSuggestionTags(token));
fetchComposeSuggestionsTagsController = new AbortController();
api(getState).get('/api/v2/search', {
cancelToken: new CancelToken(cancel => {
cancelFetchComposeSuggestionsTags = cancel;
}),
signal: fetchComposeSuggestionsTagsController.signal,
params: {
type: 'hashtags',
@ -531,9 +542,11 @@ const fetchComposeSuggestionsTags = throttle((dispatch, getState, token) => {
}).then(({ data }) => {
dispatch(readyComposeSuggestionsTags(token, data.hashtags));
}).catch(error => {
if (!isCancel(error)) {
if (!axios.isCancel(error)) {
dispatch(showAlertForError(error));
}
}).finally(() => {
fetchComposeSuggestionsTagsController = undefined;
});
}, 200, { leading: true, trailing: true });

View file

@ -0,0 +1,34 @@
import api from '../api';
export const FEATURED_TAGS_FETCH_REQUEST = 'FEATURED_TAGS_FETCH_REQUEST';
export const FEATURED_TAGS_FETCH_SUCCESS = 'FEATURED_TAGS_FETCH_SUCCESS';
export const FEATURED_TAGS_FETCH_FAIL = 'FEATURED_TAGS_FETCH_FAIL';
export const fetchFeaturedTags = (id) => (dispatch, getState) => {
if (getState().getIn(['user_lists', 'featured_tags', id, 'items'])) {
return;
}
dispatch(fetchFeaturedTagsRequest(id));
api(getState).get(`/api/v1/accounts/${id}/featured_tags`)
.then(({ data }) => dispatch(fetchFeaturedTagsSuccess(id, data)))
.catch(err => dispatch(fetchFeaturedTagsFail(id, err)));
};
export const fetchFeaturedTagsRequest = (id) => ({
type: FEATURED_TAGS_FETCH_REQUEST,
id,
});
export const fetchFeaturedTagsSuccess = (id, tags) => ({
type: FEATURED_TAGS_FETCH_SUCCESS,
id,
tags,
});
export const fetchFeaturedTagsFail = (id, error) => ({
type: FEATURED_TAGS_FETCH_FAIL,
id,
error,
});

View file

@ -29,7 +29,8 @@ export function clearSearch() {
export function submitSearch() {
return (dispatch, getState) => {
const value = getState().getIn(['search', 'value']);
const value = getState().getIn(['search', 'value']);
const signedIn = !!getState().getIn(['meta', 'me']);
if (value.length === 0) {
dispatch(fetchSearchSuccess({ accounts: [], statuses: [], hashtags: [] }, ''));
@ -41,7 +42,7 @@ export function submitSearch() {
api(getState).get('/api/v2/search', {
params: {
q: value,
resolve: true,
resolve: signedIn,
limit: 10,
},
}).then(response => {

View file

@ -5,6 +5,14 @@ export const SERVER_FETCH_REQUEST = 'Server_FETCH_REQUEST';
export const SERVER_FETCH_SUCCESS = 'Server_FETCH_SUCCESS';
export const SERVER_FETCH_FAIL = 'Server_FETCH_FAIL';
export const EXTENDED_DESCRIPTION_REQUEST = 'EXTENDED_DESCRIPTION_REQUEST';
export const EXTENDED_DESCRIPTION_SUCCESS = 'EXTENDED_DESCRIPTION_SUCCESS';
export const EXTENDED_DESCRIPTION_FAIL = 'EXTENDED_DESCRIPTION_FAIL';
export const SERVER_DOMAIN_BLOCKS_FETCH_REQUEST = 'SERVER_DOMAIN_BLOCKS_FETCH_REQUEST';
export const SERVER_DOMAIN_BLOCKS_FETCH_SUCCESS = 'SERVER_DOMAIN_BLOCKS_FETCH_SUCCESS';
export const SERVER_DOMAIN_BLOCKS_FETCH_FAIL = 'SERVER_DOMAIN_BLOCKS_FETCH_FAIL';
export const fetchServer = () => (dispatch, getState) => {
dispatch(fetchServerRequest());
@ -28,3 +36,56 @@ const fetchServerFail = error => ({
type: SERVER_FETCH_FAIL,
error,
});
export const fetchExtendedDescription = () => (dispatch, getState) => {
dispatch(fetchExtendedDescriptionRequest());
api(getState)
.get('/api/v1/instance/extended_description')
.then(({ data }) => dispatch(fetchExtendedDescriptionSuccess(data)))
.catch(err => dispatch(fetchExtendedDescriptionFail(err)));
};
const fetchExtendedDescriptionRequest = () => ({
type: EXTENDED_DESCRIPTION_REQUEST,
});
const fetchExtendedDescriptionSuccess = description => ({
type: EXTENDED_DESCRIPTION_SUCCESS,
description,
});
const fetchExtendedDescriptionFail = error => ({
type: EXTENDED_DESCRIPTION_FAIL,
error,
});
export const fetchDomainBlocks = () => (dispatch, getState) => {
dispatch(fetchDomainBlocksRequest());
api(getState)
.get('/api/v1/instance/domain_blocks')
.then(({ data }) => dispatch(fetchDomainBlocksSuccess(true, data)))
.catch(err => {
if (err.response.status === 404) {
dispatch(fetchDomainBlocksSuccess(false, []));
} else {
dispatch(fetchDomainBlocksFail(err));
}
});
};
const fetchDomainBlocksRequest = () => ({
type: SERVER_DOMAIN_BLOCKS_FETCH_REQUEST,
});
const fetchDomainBlocksSuccess = (isAvailable, blocks) => ({
type: SERVER_DOMAIN_BLOCKS_FETCH_SUCCESS,
isAvailable,
blocks,
});
const fetchDomainBlocksFail = error => ({
type: SERVER_DOMAIN_BLOCKS_FETCH_FAIL,
error,
});

View file

@ -156,8 +156,8 @@ export const expandHomeTimeline = ({ maxId } = {}, done = noOp) => ex
export const expandPublicTimeline = ({ maxId, onlyMedia, onlyRemote, allowLocalOnly } = {}, done = noOp) => expandTimeline(`public${onlyRemote ? ':remote' : (allowLocalOnly ? ':allow_local_only' : '')}${onlyMedia ? ':media' : ''}`, '/api/v1/timelines/public', { remote: !!onlyRemote, allow_local_only: !!allowLocalOnly, max_id: maxId, only_media: !!onlyMedia }, done);
export const expandCommunityTimeline = ({ maxId, onlyMedia } = {}, done = noOp) => expandTimeline(`community${onlyMedia ? ':media' : ''}`, '/api/v1/timelines/public', { local: true, max_id: maxId, only_media: !!onlyMedia }, done);
export const expandDirectTimeline = ({ maxId } = {}, done = noOp) => expandTimeline('direct', '/api/v1/timelines/direct', { max_id: maxId }, done);
export const expandAccountTimeline = (accountId, { maxId, withReplies } = {}) => expandTimeline(`account:${accountId}${withReplies ? ':with_replies' : ''}`, `/api/v1/accounts/${accountId}/statuses`, { exclude_replies: !withReplies, max_id: maxId });
export const expandAccountFeaturedTimeline = accountId => expandTimeline(`account:${accountId}:pinned`, `/api/v1/accounts/${accountId}/statuses`, { pinned: true });
export const expandAccountTimeline = (accountId, { maxId, withReplies, tagged } = {}) => expandTimeline(`account:${accountId}${withReplies ? ':with_replies' : ''}${tagged ? `:${tagged}` : ''}`, `/api/v1/accounts/${accountId}/statuses`, { exclude_replies: !withReplies, tagged, max_id: maxId });
export const expandAccountFeaturedTimeline = (accountId, { tagged } = {}) => expandTimeline(`account:${accountId}:pinned`, `/api/v1/accounts/${accountId}/statuses`, { pinned: true, tagged });
export const expandAccountMediaTimeline = (accountId, { maxId } = {}) => expandTimeline(`account:${accountId}:media`, `/api/v1/accounts/${accountId}/statuses`, { max_id: maxId, only_media: true, limit: 40 });
export const expandListTimeline = (id, { maxId } = {}, done = noOp) => expandTimeline(`list:${id}`, `/api/v1/timelines/list/${id}`, { max_id: maxId }, done);
export const expandHashtagTimeline = (hashtag, { maxId, tags, local } = {}, done = noOp) => {

View file

@ -1,20 +1,31 @@
// @ts-check
import axios from 'axios';
import LinkHeader from 'http-link-header';
import ready from './ready';
/**
* @param {import('axios').AxiosResponse} response
* @returns {LinkHeader}
*/
export const getLinks = response => {
const value = response.headers.link;
if (!value) {
return { refs: [] };
return new LinkHeader();
}
return LinkHeader.parse(value);
};
/** @type {import('axios').RawAxiosRequestHeaders} */
const csrfHeader = {};
/**
* @returns {void}
*/
const setCSRFHeader = () => {
/** @type {HTMLMetaElement | null} */
const csrfToken = document.querySelector('meta[name=csrf-token]');
if (csrfToken) {
@ -24,6 +35,10 @@ const setCSRFHeader = () => {
ready(setCSRFHeader);
/**
* @param {() => import('immutable').Map} getState
* @returns {import('axios').RawAxiosRequestHeaders}
*/
const authorizationHeaderFromState = getState => {
const accessToken = getState && getState().getIn(['meta', 'access_token'], '');
@ -36,17 +51,25 @@ const authorizationHeaderFromState = getState => {
};
};
export default getState => axios.create({
headers: {
...csrfHeader,
...authorizationHeaderFromState(getState),
},
/**
* @param {() => import('immutable').Map} getState
* @returns {import('axios').AxiosInstance}
*/
export default function api(getState) {
return axios.create({
headers: {
...csrfHeader,
...authorizationHeaderFromState(getState),
},
transformResponse: [function (data) {
try {
return JSON.parse(data);
} catch(Exception) {
return data;
}
}],
});
transformResponse: [
function (data) {
try {
return JSON.parse(data);
} catch {
return data;
}
},
],
});
}

View file

@ -70,6 +70,8 @@ export default class Avatar extends React.PureComponent {
onMouseLeave={this.handleMouseLeave}
style={style}
data-avatar-of={account && `@${account.get('acct')}`}
role='img'
aria-label={account?.get('acct')}
/>
);
}

View file

@ -0,0 +1,51 @@
import React from 'react';
import IconButton from './icon_button';
import PropTypes from 'prop-types';
import { injectIntl, defineMessages } from 'react-intl';
import { bannerSettings } from 'flavours/glitch/settings';
const messages = defineMessages({
dismiss: { id: 'dismissable_banner.dismiss', defaultMessage: 'Dismiss' },
});
export default @injectIntl
class DismissableBanner extends React.PureComponent {
static propTypes = {
id: PropTypes.string.isRequired,
children: PropTypes.node,
intl: PropTypes.object.isRequired,
};
state = {
visible: !bannerSettings.get(this.props.id),
};
handleDismiss = () => {
const { id } = this.props;
this.setState({ visible: false }, () => bannerSettings.set(id, true));
}
render () {
const { visible } = this.state;
if (!visible) {
return null;
}
const { children, intl } = this.props;
return (
<div className='dismissable-banner'>
<div className='dismissable-banner__message'>
{children}
</div>
<div className='dismissable-banner__action'>
<IconButton icon='times' title={intl.formatMessage(messages.dismiss)} onClick={this.handleDismiss} />
</div>
</div>
);
}
}

View file

@ -4,6 +4,7 @@ import { FormattedMessage } from 'react-intl';
import { source_url } from 'flavours/glitch/initial_state';
import { preferencesLink } from 'flavours/glitch/utils/backend_links';
import StackTrace from 'stacktrace-js';
import { Helmet } from 'react-helmet';
export default class ErrorBoundary extends React.PureComponent {
@ -122,6 +123,10 @@ export default class ErrorBoundary extends React.PureComponent {
)}
</ul>
</div>
<Helmet>
<meta name='robots' content='noindex' />
</Helmet>
</div>
);
}

View file

@ -1,7 +1,7 @@
// @ts-check
import React from 'react';
import { Sparklines, SparklinesCurve } from 'react-sparklines';
import { FormattedMessage, injectIntl, defineMessages } from 'react-intl';
import { FormattedMessage } from 'react-intl';
import PropTypes from 'prop-types';
import ImmutablePropTypes from 'react-immutable-proptypes';
import Permalink from './permalink';
@ -9,10 +9,6 @@ import ShortNumber from 'flavours/glitch/components/short_number';
import Skeleton from 'flavours/glitch/components/skeleton';
import classNames from 'classnames';
const messages = defineMessages({
totalVolume: { id: 'hashtag.total_volume', defaultMessage: 'Total volume in the last {days, plural, one {day} other {{days} days}}' },
});
class SilentErrorBoundary extends React.Component {
static propTypes = {
@ -60,7 +56,6 @@ export const ImmutableHashtag = ({ hashtag }) => (
href={hashtag.get('url')}
to={`/tags/${hashtag.get('name')}`}
people={hashtag.getIn(['history', 0, 'accounts']) * 1 + hashtag.getIn(['history', 1, 'accounts']) * 1}
uses={hashtag.getIn(['history', 0, 'uses']) * 1 + hashtag.getIn(['history', 1, 'uses']) * 1}
history={hashtag.get('history').reverse().map((day) => day.get('uses')).toArray()}
/>
);
@ -69,39 +64,52 @@ ImmutableHashtag.propTypes = {
hashtag: ImmutablePropTypes.map.isRequired,
};
const Hashtag = injectIntl(({ name, href, to, people, uses, history, className, intl }) => (
const Hashtag = ({ name, href, to, people, uses, history, className, description, withGraph }) => (
<div className={classNames('trends__item', className)}>
<div className='trends__item__name'>
<Permalink href={href} to={to}>
{name ? <React.Fragment>#<span>{name}</span></React.Fragment> : <Skeleton width={50} />}
</Permalink>
{typeof people !== 'undefined' ? <ShortNumber value={people} renderer={accountsCountRenderer} /> : <Skeleton width={100} />}
{description ? (
<span>{description}</span>
) : (
typeof people !== 'undefined' ? <ShortNumber value={people} renderer={accountsCountRenderer} /> : <Skeleton width={100} />
)}
</div>
<abbr className='trends__item__current' title={intl.formatMessage(messages.totalVolume, { days: 2 })}>
{typeof uses !== 'undefined' ? <ShortNumber value={uses} /> : <Skeleton width={42} height={36} />}
<span className='trends__item__current__asterisk'>*</span>
</abbr>
{typeof uses !== 'undefined' && (
<div className='trends__item__current'>
<ShortNumber value={uses} />
</div>
)}
<div className='trends__item__sparkline'>
<SilentErrorBoundary>
<Sparklines width={50} height={28} data={history ? history : Array.from(Array(7)).map(() => 0)}>
<SparklinesCurve style={{ fill: 'none' }} />
</Sparklines>
</SilentErrorBoundary>
</div>
{withGraph && (
<div className='trends__item__sparkline'>
<SilentErrorBoundary>
<Sparklines width={50} height={28} data={history ? history : Array.from(Array(7)).map(() => 0)}>
<SparklinesCurve style={{ fill: 'none' }} />
</Sparklines>
</SilentErrorBoundary>
</div>
)}
</div>
));
);
Hashtag.propTypes = {
name: PropTypes.string,
href: PropTypes.string,
to: PropTypes.string,
people: PropTypes.number,
description: PropTypes.node,
uses: PropTypes.number,
history: PropTypes.arrayOf(PropTypes.number),
className: PropTypes.string,
withGraph: PropTypes.bool,
};
Hashtag.defaultProps = {
withGraph: true,
};
export default Hashtag;

View file

@ -0,0 +1,33 @@
import React from 'react';
import PropTypes from 'prop-types';
import Blurhash from './blurhash';
import classNames from 'classnames';
export default class Image extends React.PureComponent {
static propTypes = {
src: PropTypes.string,
srcSet: PropTypes.string,
blurhash: PropTypes.string,
className: PropTypes.string,
};
state = {
loaded: false,
};
handleLoad = () => this.setState({ loaded: true });
render () {
const { src, srcSet, blurhash, className } = this.props;
const { loaded } = this.state;
return (
<div className={classNames('image', { loaded }, className)} role='presentation'>
{blurhash && <Blurhash hash={blurhash} className='image__preview' />}
<img src={src} srcSet={srcSet} alt='' onLoad={this.handleLoad} />
</div>
);
}
}

View file

@ -94,7 +94,7 @@ export default class IntersectionObserverArticle extends React.Component {
// When the browser gets a chance, test if we're still not intersecting,
// and if so, set our isHidden to true to trigger an unrender. The point of
// this is to save DOM nodes and avoid using up too much memory.
// See: https://github.com/tootsuite/mastodon/issues/2900
// See: https://github.com/mastodon/mastodon/issues/2900
this.setState((prevState) => ({ isHidden: !prevState.isIntersecting }));
}

View file

@ -1,7 +1,8 @@
import React from 'react';
const Logo = () => (
<svg viewBox='0 0 261 66' className='logo'>
<svg viewBox='0 0 261 66' className='logo' role='img'>
<title>Mastodon</title>
<use xlinkHref='#logo-symbol-wordmark' />
</svg>
);

View file

@ -3,6 +3,7 @@ import PropTypes from 'prop-types';
import { FormattedMessage } from 'react-intl';
import illustration from 'flavours/glitch/images/elephant_ui_disappointed.svg';
import classNames from 'classnames';
import { Helmet } from 'react-helmet';
const MissingIndicator = ({ fullPage }) => (
<div className={classNames('regeneration-indicator', { 'regeneration-indicator--without-header': fullPage })}>
@ -14,6 +15,10 @@ const MissingIndicator = ({ fullPage }) => (
<FormattedMessage id='missing_indicator.label' tagName='strong' defaultMessage='Not found' />
<FormattedMessage id='missing_indicator.sublabel' defaultMessage='This resource could not be found' />
</div>
<Helmet>
<meta name='robots' content='noindex' />
</Helmet>
</div>
);

View file

@ -0,0 +1,30 @@
import React from 'react';
import { Switch, Route, withRouter } from 'react-router-dom';
import { showTrends } from 'flavours/glitch/initial_state';
import Trends from 'flavours/glitch/features/getting_started/containers/trends_container';
import AccountNavigation from 'flavours/glitch/features/account/navigation';
const DefaultNavigation = () => (
<>
{showTrends && (
<>
<div className='flex-spacer' />
<Trends />
</>
)}
</>
);
export default @withRouter
class NavigationPortal extends React.PureComponent {
render () {
return (
<Switch>
<Route path='/@:acct/(tagged/:tagged?)?' component={AccountNavigation} />
<Route component={DefaultNavigation} />
</Switch>
);
}
}

View file

@ -1,19 +1,21 @@
import React from 'react';
import PropTypes from 'prop-types';
import { domain } from 'flavours/glitch/initial_state';
import { fetchServer } from 'flavours/glitch/actions/server';
import React from 'react';
import { FormattedMessage, defineMessages, injectIntl } from 'react-intl';
import { connect } from 'react-redux';
import Account from 'flavours/glitch/containers/account_container';
import { fetchServer } from 'flavours/glitch/actions/server';
import ShortNumber from 'flavours/glitch/components/short_number';
import Skeleton from 'flavours/glitch/components/skeleton';
import { FormattedMessage, injectIntl, defineMessages } from 'react-intl';
import Account from 'flavours/glitch/containers/account_container';
import { domain } from 'flavours/glitch/initial_state';
import Image from 'flavours/glitch/components/image';
import { Link } from 'react-router-dom';
const messages = defineMessages({
aboutActiveUsers: { id: 'server_banner.about_active_users', defaultMessage: 'People using this server during the last 30 days (Monthly Active Users)' },
});
const mapStateToProps = state => ({
server: state.get('server'),
server: state.getIn(['server', 'server']),
});
export default @connect(mapStateToProps)
@ -41,7 +43,7 @@ class ServerBanner extends React.PureComponent {
<FormattedMessage id='server_banner.introduction' defaultMessage='{domain} is part of the decentralized social network powered by {mastodon}.' values={{ domain: <strong>{domain}</strong>, mastodon: <a href='https://joinmastodon.org' target='_blank'>Mastodon</a> }} />
</div>
<img src={server.get('thumbnail')} alt={server.get('title')} className='server-banner__hero' />
<Image blurhash={server.getIn(['thumbnail', 'blurhash'])} src={server.getIn(['thumbnail', 'url'])} className='server-banner__hero' />
<div className='server-banner__description'>
{isLoading ? (
@ -83,7 +85,7 @@ class ServerBanner extends React.PureComponent {
<hr className='spacer' />
<a className='button button--block button-secondary' href='/about/more' target='_blank'><FormattedMessage id='server_banner.learn_more' defaultMessage='Learn more' /></a>
<Link className='button button--block button-secondary' to='/about'><FormattedMessage id='server_banner.learn_more' defaultMessage='Learn more' /></Link>
</div>
);
}

View file

@ -4,8 +4,8 @@ import PropTypes from 'prop-types';
const Skeleton = ({ width, height }) => <span className='skeleton' style={{ width, height }}>&zwnj;</span>;
Skeleton.propTypes = {
width: PropTypes.number,
height: PropTypes.number,
width: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
height: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
};
export default Skeleton;

View file

@ -242,7 +242,7 @@ class StatusActionBar extends ImmutablePureComponent {
}
if (writtenByMe) {
// menu.push({ text: intl.formatMessage(messages.edit), action: this.handleEditClick });
menu.push({ text: intl.formatMessage(messages.edit), action: this.handleEditClick });
menu.push({ text: intl.formatMessage(messages.delete), action: this.handleDeleteClick });
menu.push({ text: intl.formatMessage(messages.redraft), action: this.handleRedraftClick });
} else {

View file

@ -124,6 +124,9 @@ export default class StatusContent extends React.PureComponent {
link.setAttribute('title', link.href);
link.classList.add('unhandled-link');
link.setAttribute('target', '_blank');
link.setAttribute('rel', 'noopener nofollow noreferrer');
try {
if (tagLinks && isLinkMisleading(link)) {
// Add a tag besides the link to display its origin
@ -149,9 +152,6 @@ export default class StatusContent extends React.PureComponent {
if (tagLinks && e instanceof TypeError) link.removeAttribute('href');
}
}
link.setAttribute('target', '_blank');
link.setAttribute('rel', 'noopener noreferrer');
}
}

View file

@ -1,22 +1,25 @@
import React from 'react';
import { Provider } from 'react-redux';
import PropTypes from 'prop-types';
import configureStore from 'flavours/glitch/store/configureStore';
import React from 'react';
import { Helmet } from 'react-helmet';
import { IntlProvider, addLocaleData } from 'react-intl';
import { Provider as ReduxProvider } from 'react-redux';
import { BrowserRouter, Route } from 'react-router-dom';
import { ScrollContext } from 'react-router-scroll-4';
import configureStore from 'flavours/glitch/store/configureStore';
import UI from 'flavours/glitch/features/ui';
import { fetchCustomEmojis } from 'flavours/glitch/actions/custom_emojis';
import { hydrateStore } from 'flavours/glitch/actions/store';
import { connectUserStream } from 'flavours/glitch/actions/streaming';
import { checkDeprecatedLocalSettings } from 'flavours/glitch/actions/local_settings';
import { IntlProvider, addLocaleData } from 'react-intl';
import { getLocale } from 'locales';
import initialState from 'flavours/glitch/initial_state';
import { connectUserStream } from 'flavours/glitch/actions/streaming';
import ErrorBoundary from 'flavours/glitch/components/error_boundary';
import initialState, { title as siteTitle } from 'flavours/glitch/initial_state';
import { getLocale } from 'locales';
const { localeData, messages } = getLocale();
addLocaleData(localeData);
const title = process.env.NODE_ENV === 'production' ? siteTitle : `${siteTitle} (Dev)`;
export const store = configureStore();
const hydrateAction = hydrateStore(initialState);
store.dispatch(hydrateAction);
@ -78,15 +81,17 @@ export default class Mastodon extends React.PureComponent {
return (
<IntlProvider locale={locale} messages={messages}>
<Provider store={store}>
<ReduxProvider store={store}>
<ErrorBoundary>
<BrowserRouter basename='/web'>
<BrowserRouter>
<ScrollContext shouldUpdateScroll={this.shouldUpdateScroll}>
<Route path='/' component={UI} />
</ScrollContext>
</BrowserRouter>
<Helmet defaultTitle={title} titleTemplate={`%s - ${title}`} />
</ErrorBoundary>
</Provider>
</ReduxProvider>
</IntlProvider>
);
}

View file

@ -1,3 +1,4 @@
import 'abortcontroller-polyfill/dist/abortcontroller-polyfill-only';
import 'intersection-observer';
import 'requestidlecallback';
import objectFitImages from 'object-fit-images';

View file

@ -0,0 +1,222 @@
import React from 'react';
import ImmutablePropTypes from 'react-immutable-proptypes';
import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
import { connect } from 'react-redux';
import PropTypes from 'prop-types';
import Column from 'flavours/glitch/components/column';
import LinkFooter from 'flavours/glitch/features/ui/components/link_footer';
import { Helmet } from 'react-helmet';
import { fetchServer, fetchExtendedDescription, fetchDomainBlocks } from 'flavours/glitch/actions/server';
import Account from 'flavours/glitch/containers/account_container';
import Skeleton from 'flavours/glitch/components/skeleton';
import Icon from 'flavours/glitch/components/icon';
import classNames from 'classnames';
import Image from 'flavours/glitch/components/image';
const messages = defineMessages({
title: { id: 'column.about', defaultMessage: 'About' },
rules: { id: 'about.rules', defaultMessage: 'Server rules' },
blocks: { id: 'about.blocks', defaultMessage: 'Moderated servers' },
silenced: { id: 'about.domain_blocks.silenced.title', defaultMessage: 'Limited' },
silencedExplanation: { id: 'about.domain_blocks.silenced.explanation', defaultMessage: 'You will generally not see profiles and content from this server, unless you explicitly look it up or opt into it by following.' },
suspended: { id: 'about.domain_blocks.suspended.title', defaultMessage: 'Suspended' },
suspendedExplanation: { id: 'about.domain_blocks.suspended.explanation', defaultMessage: 'No data from this server will be processed, stored or exchanged, making any interaction or communication with users from this server impossible.' },
});
const severityMessages = {
silence: {
title: messages.silenced,
explanation: messages.silencedExplanation,
},
suspend: {
title: messages.suspended,
explanation: messages.suspendedExplanation,
},
};
const mapStateToProps = state => ({
server: state.getIn(['server', 'server']),
extendedDescription: state.getIn(['server', 'extendedDescription']),
domainBlocks: state.getIn(['server', 'domainBlocks']),
});
class Section extends React.PureComponent {
static propTypes = {
title: PropTypes.string,
children: PropTypes.node,
open: PropTypes.bool,
onOpen: PropTypes.func,
};
state = {
collapsed: !this.props.open,
};
handleClick = () => {
const { onOpen } = this.props;
const { collapsed } = this.state;
this.setState({ collapsed: !collapsed }, () => onOpen && onOpen());
}
render () {
const { title, children } = this.props;
const { collapsed } = this.state;
return (
<div className={classNames('about__section', { active: !collapsed })}>
<div className='about__section__title' role='button' tabIndex='0' onClick={this.handleClick}>
<Icon id={collapsed ? 'chevron-right' : 'chevron-down'} fixedWidth /> {title}
</div>
{!collapsed && (
<div className='about__section__body'>{children}</div>
)}
</div>
);
}
}
export default @connect(mapStateToProps)
@injectIntl
class About extends React.PureComponent {
static propTypes = {
server: ImmutablePropTypes.map,
extendedDescription: ImmutablePropTypes.map,
domainBlocks: ImmutablePropTypes.contains({
isLoading: PropTypes.bool,
isAvailable: PropTypes.bool,
items: ImmutablePropTypes.list,
}),
dispatch: PropTypes.func.isRequired,
intl: PropTypes.object.isRequired,
multiColumn: PropTypes.bool,
};
componentDidMount () {
const { dispatch } = this.props;
dispatch(fetchServer());
dispatch(fetchExtendedDescription());
}
handleDomainBlocksOpen = () => {
const { dispatch } = this.props;
dispatch(fetchDomainBlocks());
}
render () {
const { multiColumn, intl, server, extendedDescription, domainBlocks } = this.props;
const isLoading = server.get('isLoading');
return (
<Column bindToDocument={!multiColumn} label={intl.formatMessage(messages.title)}>
<div className='scrollable about'>
<div className='about__header'>
<Image blurhash={server.getIn(['thumbnail', 'blurhash'])} src={server.getIn(['thumbnail', 'url'])} srcSet={server.getIn(['thumbnail', 'versions'])?.map((value, key) => `${value} ${key.replace('@', '')}`).join(', ')} className='about__header__hero' />
<h1>{isLoading ? <Skeleton width='10ch' /> : server.get('domain')}</h1>
<p><FormattedMessage id='about.powered_by' defaultMessage='Decentralized social media powered by {mastodon}' values={{ mastodon: <a href='https://joinmastodon.org' className='about__mail' target='_blank'>Mastodon</a> }} /></p>
</div>
<div className='about__meta'>
<div className='about__meta__column'>
<h4><FormattedMessage id='server_banner.administered_by' defaultMessage='Administered by:' /></h4>
<Account id={server.getIn(['contact', 'account', 'id'])} />
</div>
<hr className='about__meta__divider' />
<div className='about__meta__column'>
<h4><FormattedMessage id='about.contact' defaultMessage='Contact:' /></h4>
{isLoading ? <Skeleton width='10ch' /> : <a className='about__mail' href={`mailto:${server.getIn(['contact', 'email'])}`}>{server.getIn(['contact', 'email'])}</a>}
</div>
</div>
<Section open title={intl.formatMessage(messages.title)}>
{extendedDescription.get('isLoading') ? (
<>
<Skeleton width='100%' />
<br />
<Skeleton width='100%' />
<br />
<Skeleton width='100%' />
<br />
<Skeleton width='70%' />
</>
) : (extendedDescription.get('content')?.length > 0 ? (
<div
className='prose'
dangerouslySetInnerHTML={{ __html: extendedDescription.get('content') }}
/>
) : (
<p><FormattedMessage id='about.not_available' defaultMessage='This information has not been made available on this server.' /></p>
))}
</Section>
<Section title={intl.formatMessage(messages.rules)}>
{!isLoading && (server.get('rules').isEmpty() ? (
<p><FormattedMessage id='about.not_available' defaultMessage='This information has not been made available on this server.' /></p>
) : (
<ol className='rules-list'>
{server.get('rules').map(rule => (
<li key={rule.get('id')}>
<span className='rules-list__text'>{rule.get('text')}</span>
</li>
))}
</ol>
))}
</Section>
<Section title={intl.formatMessage(messages.blocks)} onOpen={this.handleDomainBlocksOpen}>
{domainBlocks.get('isLoading') ? (
<>
<Skeleton width='100%' />
<br />
<Skeleton width='70%' />
</>
) : (domainBlocks.get('isAvailable') ? (
<>
<p><FormattedMessage id='about.domain_blocks.preamble' defaultMessage='Mastodon generally allows you to view content from and interact with users from any other server in the fediverse. These are the exceptions that have been made on this particular server.' /></p>
<table className='about__domain-blocks'>
<thead>
<tr>
<th><FormattedMessage id='about.domain_blocks.domain' defaultMessage='Domain' /></th>
<th><FormattedMessage id='about.domain_blocks.severity' defaultMessage='Severity' /></th>
<th><FormattedMessage id='about.domain_blocks.comment' defaultMessage='Reason' /></th>
</tr>
</thead>
<tbody>
{domainBlocks.get('items').map(block => (
<tr key={block.get('domain')}>
<td><span title={`SHA-256: ${block.get('digest')}`}>{block.get('domain')}</span></td>
<td><span title={intl.formatMessage(severityMessages[block.get('severity')].explanation)}>{intl.formatMessage(severityMessages[block.get('severity')].title)}</span></td>
<td>{block.get('comment')}</td>
</tr>
))}
</tbody>
</table>
</>
) : (
<p><FormattedMessage id='about.not_available' defaultMessage='This information has not been made available on this server.' /></p>
))}
</Section>
<LinkFooter />
</div>
<Helmet>
<title>{intl.formatMessage(messages.title)}</title>
<meta name='robots' content='all' />
</Helmet>
</Column>
);
}
}

View file

@ -0,0 +1,53 @@
import React from 'react';
import PropTypes from 'prop-types';
import ImmutablePropTypes from 'react-immutable-proptypes';
import ImmutablePureComponent from 'react-immutable-pure-component';
import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
import Hashtag from 'flavours/glitch/components/hashtag';
const messages = defineMessages({
lastStatusAt: { id: 'account.featured_tags.last_status_at', defaultMessage: 'Last post on {date}' },
empty: { id: 'account.featured_tags.last_status_never', defaultMessage: 'No posts' },
});
export default @injectIntl
class FeaturedTags extends ImmutablePureComponent {
static contextTypes = {
router: PropTypes.object,
};
static propTypes = {
account: ImmutablePropTypes.map,
featuredTags: ImmutablePropTypes.list,
tagged: PropTypes.string,
intl: PropTypes.object.isRequired,
};
render () {
const { account, featuredTags, intl } = this.props;
if (!account || account.get('suspended') || featuredTags.isEmpty()) {
return null;
}
return (
<div className='getting-started__trends'>
<h4><FormattedMessage id='account.featured_tags.title' defaultMessage="{name}'s featured hashtags" values={{ name: <bdi dangerouslySetInnerHTML={{ __html: account.get('display_name_html') }} /> }} /></h4>
{featuredTags.take(3).map(featuredTag => (
<Hashtag
key={featuredTag.get('name')}
name={featuredTag.get('name')}
href={featuredTag.get('url')}
to={`/@${account.get('acct')}/tagged/${featuredTag.get('name')}`}
uses={featuredTag.get('statuses_count')}
withGraph={false}
description={((featuredTag.get('statuses_count') * 1) > 0) ? intl.formatMessage(messages.lastStatusAt, { date: intl.formatDate(featuredTag.get('last_status_at'), { month: 'short', day: '2-digit' }) }) : intl.formatMessage(messages.empty)}
/>
))}
</div>
);
}
}

View file

@ -3,7 +3,7 @@ import ImmutablePropTypes from 'react-immutable-proptypes';
import PropTypes from 'prop-types';
import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
import ImmutablePureComponent from 'react-immutable-pure-component';
import { autoPlayGif, me, title, domain } from 'flavours/glitch/initial_state';
import { autoPlayGif, me, domain } from 'flavours/glitch/initial_state';
import { preferencesLink, profileLink, accountAdminLink } from 'flavours/glitch/utils/backend_links';
import classNames from 'classnames';
import Icon from 'flavours/glitch/components/icon';
@ -19,7 +19,7 @@ import { Helmet } from 'react-helmet';
const messages = defineMessages({
unfollow: { id: 'account.unfollow', defaultMessage: 'Unfollow' },
follow: { id: 'account.follow', defaultMessage: 'Follow' },
cancel_follow_request: { id: 'account.cancel_follow_request', defaultMessage: 'Cancel follow request' },
cancel_follow_request: { id: 'account.cancel_follow_request', defaultMessage: 'Withdraw follow request' },
requested: { id: 'account.requested', defaultMessage: 'Awaiting approval. Click to cancel follow request' },
unblock: { id: 'account.unblock', defaultMessage: 'Unblock @{name}' },
edit_profile: { id: 'account.edit_profile', defaultMessage: 'Edit profile' },
@ -273,7 +273,9 @@ class Header extends ImmutablePureComponent {
const content = { __html: account.get('note_emojified') };
const displayNameHtml = { __html: account.get('display_name_html') };
const fields = account.get('fields');
const acct = account.get('acct').indexOf('@') === -1 && domain ? `${account.get('acct')}@${domain}` : account.get('acct');
const isLocal = account.get('acct').indexOf('@') === -1;
const acct = isLocal && domain ? `${account.get('acct')}@${domain}` : account.get('acct');
const isIndexable = !account.get('noindex');
let badge;
@ -352,7 +354,8 @@ class Header extends ImmutablePureComponent {
</div>
<Helmet>
<title>{titleFromAccount(account)} - {title}</title>
<title>{titleFromAccount(account)}</title>
<meta name='robots' content={(isLocal && isIndexable) ? 'all' : 'noindex'} />
</Helmet>
</div>
);

View file

@ -0,0 +1,15 @@
import { connect } from 'react-redux';
import FeaturedTags from '../components/featured_tags';
import { makeGetAccount } from 'flavours/glitch/selectors';
import { List as ImmutableList } from 'immutable';
const mapStateToProps = () => {
const getAccount = makeGetAccount();
return (state, { accountId }) => ({
account: getAccount(state, accountId),
featuredTags: state.getIn(['user_lists', 'featured_tags', accountId, 'items'], ImmutableList()),
});
};
export default connect(mapStateToProps)(FeaturedTags);

View file

@ -0,0 +1,52 @@
import React from 'react';
import PropTypes from 'prop-types';
import { connect } from 'react-redux';
import FeaturedTags from 'flavours/glitch/features/account/containers/featured_tags_container';
import { normalizeForLookup } from 'flavours/glitch/reducers/accounts_map';
const mapStateToProps = (state, { match: { params: { acct } } }) => {
const accountId = state.getIn(['accounts_map', normalizeForLookup(acct)]);
if (!accountId) {
return {
isLoading: true,
};
}
return {
accountId,
isLoading: false,
};
};
export default @connect(mapStateToProps)
class AccountNavigation extends React.PureComponent {
static propTypes = {
match: PropTypes.shape({
params: PropTypes.shape({
acct: PropTypes.string,
tagged: PropTypes.string,
}).isRequired,
}).isRequired,
accountId: PropTypes.string,
isLoading: PropTypes.bool,
};
render () {
const { accountId, isLoading, match: { params: { tagged } } } = this.props;
if (isLoading) {
return null;
}
return (
<>
<div className='flex-spacer' />
<FeaturedTags accountId={accountId} tagged={tagged} />
</>
);
}
}

View file

@ -15,9 +15,10 @@ import ScrollContainer from 'flavours/glitch/containers/scroll_container';
import LoadMore from 'flavours/glitch/components/load_more';
import MissingIndicator from 'flavours/glitch/components/missing_indicator';
import { openModal } from 'flavours/glitch/actions/modal';
import { normalizeForLookup } from 'flavours/glitch/reducers/accounts_map';
const mapStateToProps = (state, { params: { acct, id } }) => {
const accountId = id || state.getIn(['accounts_map', acct]);
const accountId = id || state.getIn(['accounts_map', normalizeForLookup(acct)]);
if (!accountId) {
return {

View file

@ -24,6 +24,7 @@ import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
import { unfollowModal } from 'flavours/glitch/initial_state';
const messages = defineMessages({
cancelFollowRequestConfirm: { id: 'confirmations.cancel_follow_request.confirm', defaultMessage: 'Withdraw request' },
unfollowConfirm: { id: 'confirmations.unfollow.confirm', defaultMessage: 'Unfollow' },
blockDomainConfirm: { id: 'confirmations.domain_block.confirm', defaultMessage: 'Hide entire domain' },
});
@ -43,7 +44,7 @@ const makeMapStateToProps = () => {
const mapDispatchToProps = (dispatch, { intl }) => ({
onFollow (account) {
if (account.getIn(['relationship', 'following']) || account.getIn(['relationship', 'requested'])) {
if (account.getIn(['relationship', 'following'])) {
if (unfollowModal) {
dispatch(openModal('CONFIRM', {
message: <FormattedMessage id='confirmations.unfollow.message' defaultMessage='Are you sure you want to unfollow {name}?' values={{ name: <strong>@{account.get('acct')}</strong> }} />,
@ -53,6 +54,14 @@ const mapDispatchToProps = (dispatch, { intl }) => ({
} else {
dispatch(unfollowAccount(account.get('id')));
}
} else if (account.getIn(['relationship', 'requested'])) {
if (unfollowModal) {
dispatch(openModal('CONFIRM', {
message: <FormattedMessage id='confirmations.cancel_follow_request.message' defaultMessage='Are you sure you want to withdraw your request to follow {name}?' values={{ name: <strong>@{account.get('acct')}</strong> }} />,
confirm: intl.formatMessage(messages.cancelFollowRequestConfirm),
onConfirm: () => dispatch(unfollowAccount(account.get('id'))),
}));
}
} else {
dispatch(followAccount(account.get('id')));
}

View file

@ -17,19 +17,22 @@ import MissingIndicator from 'flavours/glitch/components/missing_indicator';
import TimelineHint from 'flavours/glitch/components/timeline_hint';
import LimitedAccountHint from './components/limited_account_hint';
import { getAccountHidden } from 'flavours/glitch/selectors';
import { normalizeForLookup } from 'flavours/glitch/reducers/accounts_map';
import { fetchFeaturedTags } from '../../actions/featured_tags';
const emptyList = ImmutableList();
const mapStateToProps = (state, { params: { acct, id }, withReplies = false }) => {
const accountId = id || state.getIn(['accounts_map', acct]);
const mapStateToProps = (state, { params: { acct, id, tagged }, withReplies = false }) => {
const accountId = id || state.getIn(['accounts_map', normalizeForLookup(acct)]);
if (!accountId) {
return {
isLoading: true,
statusIds: emptyList,
};
}
const path = withReplies ? `${accountId}:with_replies` : accountId;
const path = withReplies ? `${accountId}:with_replies` : `${accountId}${tagged ? `:${tagged}` : ''}`;
return {
accountId,
@ -37,7 +40,7 @@ const mapStateToProps = (state, { params: { acct, id }, withReplies = false }) =
remoteUrl: state.getIn(['accounts', accountId, 'url']),
isAccount: !!state.getIn(['accounts', accountId]),
statusIds: state.getIn(['timelines', `account:${path}`, 'items'], ImmutableList()),
featuredStatusIds: withReplies ? ImmutableList() : state.getIn(['timelines', `account:${accountId}:pinned`, 'items'], ImmutableList()),
featuredStatusIds: withReplies ? ImmutableList() : state.getIn(['timelines', `account:${accountId}:pinned${tagged ? `:${tagged}` : ''}`, 'items'], ImmutableList()),
isLoading: state.getIn(['timelines', `account:${path}`, 'isLoading']),
hasMore: state.getIn(['timelines', `account:${path}`, 'hasMore']),
suspended: state.getIn(['accounts', accountId, 'suspended'], false),
@ -60,6 +63,7 @@ class AccountTimeline extends ImmutablePureComponent {
params: PropTypes.shape({
acct: PropTypes.string,
id: PropTypes.string,
tagged: PropTypes.string,
}).isRequired,
accountId: PropTypes.string,
dispatch: PropTypes.func.isRequired,
@ -77,14 +81,16 @@ class AccountTimeline extends ImmutablePureComponent {
};
_load () {
const { accountId, withReplies, dispatch } = this.props;
const { accountId, withReplies, params: { tagged }, dispatch } = this.props;
dispatch(fetchAccount(accountId));
if (!withReplies) {
dispatch(expandAccountFeaturedTimeline(accountId));
dispatch(expandAccountFeaturedTimeline(accountId, { tagged }));
}
dispatch(expandAccountTimeline(accountId, { withReplies }));
dispatch(fetchFeaturedTags(accountId));
dispatch(expandAccountTimeline(accountId, { withReplies, tagged }));
}
componentDidMount () {
@ -98,12 +104,17 @@ class AccountTimeline extends ImmutablePureComponent {
}
componentDidUpdate (prevProps) {
const { params: { acct }, accountId, dispatch } = this.props;
const { params: { acct, tagged }, accountId, withReplies, dispatch } = this.props;
if (prevProps.accountId !== accountId && accountId) {
this._load();
} else if (prevProps.params.acct !== acct) {
dispatch(lookupAccount(acct));
} else if (prevProps.params.tagged !== tagged) {
if (!withReplies) {
dispatch(expandAccountFeaturedTimeline(accountId, { tagged }));
}
dispatch(expandAccountTimeline(accountId, { withReplies, tagged }));
}
}
@ -126,7 +137,7 @@ class AccountTimeline extends ImmutablePureComponent {
}
handleLoadMore = maxId => {
this.props.dispatch(expandAccountTimeline(this.props.accountId, { maxId, withReplies: this.props.withReplies }));
this.props.dispatch(expandAccountTimeline(this.props.accountId, { maxId, withReplies: this.props.withReplies, tagged: this.props.params.tagged }));
}
setRef = c => {
@ -136,7 +147,13 @@ class AccountTimeline extends ImmutablePureComponent {
render () {
const { accountId, statusIds, featuredStatusIds, isLoading, hasMore, suspended, isAccount, hidden, multiColumn, remote, remoteUrl } = this.props;
if (!isAccount) {
if (isLoading && statusIds.isEmpty()) {
return (
<Column>
<LoadingIndicator />
</Column>
);
} else if (!isLoading && !isAccount) {
return (
<Column>
<ColumnBackButton multiColumn={multiColumn} />
@ -145,14 +162,6 @@ class AccountTimeline extends ImmutablePureComponent {
);
}
if (!statusIds && isLoading) {
return (
<Column>
<LoadingIndicator />
</Column>
);
}
let emptyMessage;
const forceEmptyState = suspended || hidden;
@ -174,7 +183,7 @@ class AccountTimeline extends ImmutablePureComponent {
<ProfileColumnHeader onClick={this.handleHeaderClick} multiColumn={multiColumn} />
<StatusList
prepend={<HeaderContainer accountId={this.props.accountId} hideTabs={forceEmptyState} />}
prepend={<HeaderContainer accountId={this.props.accountId} hideTabs={forceEmptyState} tagged={this.props.params.tagged} />}
alwaysPrepend
append={remoteMessage}
scrollKey='account_timeline'

View file

@ -1,15 +1,16 @@
import React from 'react';
import { connect } from 'react-redux';
import PropTypes from 'prop-types';
import ImmutablePropTypes from 'react-immutable-proptypes';
import { debounce } from 'lodash';
import { fetchBookmarkedStatuses, expandBookmarkedStatuses } from 'flavours/glitch/actions/bookmarks';
import Column from 'flavours/glitch/features/ui/components/column';
import ColumnHeader from 'flavours/glitch/components/column_header';
import { addColumn, removeColumn, moveColumn } from 'flavours/glitch/actions/columns';
import StatusList from 'flavours/glitch/components/status_list';
import PropTypes from 'prop-types';
import React from 'react';
import { Helmet } from 'react-helmet';
import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
import ImmutablePropTypes from 'react-immutable-proptypes';
import ImmutablePureComponent from 'react-immutable-pure-component';
import { connect } from 'react-redux';
import { fetchBookmarkedStatuses, expandBookmarkedStatuses } from 'flavours/glitch/actions/bookmarks';
import { addColumn, removeColumn, moveColumn } from 'flavours/glitch/actions/columns';
import ColumnHeader from 'flavours/glitch/components/column_header';
import StatusList from 'flavours/glitch/components/status_list';
import Column from 'flavours/glitch/features/ui/components/column';
const messages = defineMessages({
heading: { id: 'column.bookmarks', defaultMessage: 'Bookmarks' },
@ -95,6 +96,11 @@ class Bookmarks extends ImmutablePureComponent {
emptyMessage={emptyMessage}
bindToDocument={!multiColumn}
/>
<Helmet>
<title>{intl.formatMessage(messages.heading)}</title>
<meta name='robots' content='noindex' />
</Helmet>
</Column>
);
}

View file

@ -0,0 +1,75 @@
import React from 'react';
import { connect } from 'react-redux';
import { FormattedMessage } from 'react-intl';
import ImmutablePureComponent from 'react-immutable-pure-component';
import { domain } from 'flavours/glitch/initial_state';
import { fetchServer } from 'flavours/glitch/actions/server';
const mapStateToProps = state => ({
message: state.getIn(['server', 'server', 'registrations', 'message']),
});
export default @connect(mapStateToProps)
class ClosedRegistrationsModal extends ImmutablePureComponent {
componentDidMount () {
const { dispatch } = this.props;
dispatch(fetchServer());
}
render () {
let closedRegistrationsMessage;
if (this.props.message) {
closedRegistrationsMessage = (
<p
className='prose'
dangerouslySetInnerHTML={{ __html: this.props.message }}
/>
);
} else {
closedRegistrationsMessage = (
<p className='prose'>
<FormattedMessage
id='closed_registrations_modal.description'
defaultMessage='Creating an account on {domain} is currently not possible, but please keep in mind that you do not need an account specifically on {domain} to use Mastodon.'
values={{ domain: <strong>{domain}</strong> }}
/>
</p>
);
}
return (
<div className='modal-root__modal interaction-modal'>
<div className='interaction-modal__lead'>
<h3><FormattedMessage id='closed_registrations_modal.title' defaultMessage='Signing up on Mastodon' /></h3>
<p>
<FormattedMessage
id='closed_registrations_modal.preamble'
defaultMessage='Mastodon is decentralized, so no matter where you create your account, you will be able to follow and interact with anyone on this server. You can even self-host it!'
/>
</p>
</div>
<div className='interaction-modal__choices'>
<div className='interaction-modal__choices__choice'>
<h3><FormattedMessage id='interaction_modal.on_this_server' defaultMessage='On this server' /></h3>
{closedRegistrationsMessage}
</div>
<div className='interaction-modal__choices__choice'>
<h3><FormattedMessage id='interaction_modal.on_another_server' defaultMessage='On a different server' /></h3>
<p className='prose'>
<FormattedMessage
id='closed_registrations.other_server_instructions'
defaultMessage='Since Mastodon is decentralized, you can create an account on another server and still interact with this one.'
/>
</p>
<a href='https://joinmastodon.org/servers' className='button button--block'><FormattedMessage id='closed_registrations_modal.find_another_server' defaultMessage='Find another server' /></a>
</div>
</div>
</div>
);
}
};

View file

@ -10,7 +10,8 @@ import { addColumn, removeColumn, moveColumn } from 'flavours/glitch/actions/col
import ColumnSettingsContainer from './containers/column_settings_container';
import { connectCommunityStream } from 'flavours/glitch/actions/streaming';
import { Helmet } from 'react-helmet';
import { title } from 'flavours/glitch/initial_state';
import { domain } from 'flavours/glitch/initial_state';
import DismissableBanner from 'flavours/glitch/components/dismissable_banner';
const messages = defineMessages({
title: { id: 'column.community', defaultMessage: 'Local timeline' },
@ -138,6 +139,10 @@ class CommunityTimeline extends React.PureComponent {
<ColumnSettingsContainer columnId={columnId} />
</ColumnHeader>
<DismissableBanner id='community_timeline'>
<FormattedMessage id='dismissable_banner.community_timeline' defaultMessage='These are the most recent public posts from people whose accounts are hosted by {domain}.' values={{ domain }} />
</DismissableBanner>
<StatusListContainer
trackScroll={!pinned}
scrollKey={`community_timeline-${columnId}`}
@ -149,7 +154,8 @@ class CommunityTimeline extends React.PureComponent {
/>
<Helmet>
<title>{intl.formatMessage(messages.title)} - {title}</title>
<title>{intl.formatMessage(messages.title)}</title>
<meta name='robots' content='noindex' />
</Helmet>
</Column>
);

View file

@ -21,6 +21,7 @@ import Motion from '../../ui/util/optional_motion';
const messages = defineMessages({
placeholder: { id: 'search.placeholder', defaultMessage: 'Search' },
placeholderSignedIn: { id: 'search.search_or_paste', defaultMessage: 'Search or paste URL' },
});
class SearchPopout extends React.PureComponent {
@ -62,6 +63,7 @@ class Search extends React.PureComponent {
static contextTypes = {
router: PropTypes.object.isRequired,
identity: PropTypes.object.isRequired,
};
static propTypes = {
@ -137,6 +139,7 @@ class Search extends React.PureComponent {
render () {
const { intl, value, submitted } = this.props;
const { expanded } = this.state;
const { signedIn } = this.context.identity;
const hasValue = value.length > 0 || submitted;
return (
@ -147,7 +150,7 @@ class Search extends React.PureComponent {
ref={this.setRef}
className='search__input'
type='text'
placeholder={intl.formatMessage(messages.placeholder)}
placeholder={intl.formatMessage(signedIn ? messages.placeholderSignedIn : messages.placeholder)}
value={value || ''}
onChange={this.handleChange}
onKeyUp={this.handleKeyUp}

View file

@ -4,7 +4,6 @@ import UploadProgressContainer from '../containers/upload_progress_container';
import ImmutablePureComponent from 'react-immutable-pure-component';
import UploadContainer from '../containers/upload_container';
import SensitiveButtonContainer from '../containers/sensitive_button_container';
import { FormattedMessage } from 'react-intl';
export default class UploadForm extends ImmutablePureComponent {
static propTypes = {
@ -16,7 +15,7 @@ export default class UploadForm extends ImmutablePureComponent {
return (
<div className='composer--upload_form'>
<UploadProgressContainer icon='upload' message={<FormattedMessage id='upload_progress.label' defaultMessage='Uploading…' />} />
<UploadProgressContainer />
{mediaIds.size > 0 && (
<div className='content'>

View file

@ -3,26 +3,34 @@ import PropTypes from 'prop-types';
import Motion from '../../ui/util/optional_motion';
import spring from 'react-motion/lib/spring';
import Icon from 'flavours/glitch/components/icon';
import { FormattedMessage } from 'react-intl';
export default class UploadProgress extends React.PureComponent {
static propTypes = {
active: PropTypes.bool,
progress: PropTypes.number,
icon: PropTypes.string.isRequired,
message: PropTypes.node.isRequired,
isProcessing: PropTypes.bool,
};
render () {
const { active, progress, icon, message } = this.props;
const { active, progress, isProcessing } = this.props;
if (!active) {
return null;
}
let message;
if (isProcessing) {
message = <FormattedMessage id='upload_progress.processing' defaultMessage='Processing…' />;
} else {
message = <FormattedMessage id='upload_progress.label' defaultMessage='Uploading…' />;
}
return (
<div className='composer--upload_form--progress'>
<Icon id={icon} />
<Icon id='upload' />
<div className='message'>
{message}

Some files were not shown because too many files have changed in this diff Show more