@tracearr/translations 2.2.4-beta.3 → 2.3.0-beta.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (252) hide show
  1. package/README.md +1 -1
  2. package/dist/config.d.ts +1164 -64
  3. package/dist/config.d.ts.map +1 -1
  4. package/dist/config.mobile.d.ts +1164 -64
  5. package/dist/config.mobile.d.ts.map +1 -1
  6. package/dist/locales/af-ZA/common.json +281 -280
  7. package/dist/locales/af-ZA/notifications.json +238 -218
  8. package/dist/locales/af-ZA/pages.json +1726 -1646
  9. package/dist/locales/af-ZA/settings.json +888 -440
  10. package/dist/locales/ar-SA/common.json +281 -280
  11. package/dist/locales/ar-SA/notifications.json +242 -222
  12. package/dist/locales/ar-SA/pages.json +1684 -1604
  13. package/dist/locales/ar-SA/settings.json +889 -441
  14. package/dist/locales/ca-ES/common.json +281 -280
  15. package/dist/locales/ca-ES/notifications.json +238 -218
  16. package/dist/locales/ca-ES/pages.json +1682 -1602
  17. package/dist/locales/ca-ES/settings.json +888 -440
  18. package/dist/locales/cs-CZ/common.json +281 -280
  19. package/dist/locales/cs-CZ/notifications.json +242 -222
  20. package/dist/locales/cs-CZ/pages.json +1688 -1608
  21. package/dist/locales/cs-CZ/settings.json +889 -441
  22. package/dist/locales/da-DK/common.json +281 -280
  23. package/dist/locales/da-DK/notifications.json +242 -222
  24. package/dist/locales/da-DK/pages.json +1684 -1604
  25. package/dist/locales/da-DK/settings.json +889 -441
  26. package/dist/locales/de-DE/common.json +281 -280
  27. package/dist/locales/de-DE/notifications.json +242 -222
  28. package/dist/locales/de-DE/pages.json +1690 -1610
  29. package/dist/locales/de-DE/settings.json +889 -441
  30. package/dist/locales/el-GR/common.json +281 -280
  31. package/dist/locales/el-GR/notifications.json +242 -222
  32. package/dist/locales/el-GR/pages.json +1684 -1604
  33. package/dist/locales/el-GR/settings.json +889 -441
  34. package/dist/locales/en/notifications.json +26 -6
  35. package/dist/locales/en/pages.json +94 -12
  36. package/dist/locales/en/settings.json +474 -26
  37. package/dist/locales/en-US/common.json +281 -280
  38. package/dist/locales/en-US/notifications.json +242 -222
  39. package/dist/locales/en-US/pages.json +1774 -1694
  40. package/dist/locales/en-US/settings.json +898 -450
  41. package/dist/locales/es-ES/common.json +281 -280
  42. package/dist/locales/es-ES/notifications.json +242 -222
  43. package/dist/locales/es-ES/pages.json +1689 -1609
  44. package/dist/locales/es-ES/settings.json +889 -441
  45. package/dist/locales/fi-FI/common.json +281 -280
  46. package/dist/locales/fi-FI/notifications.json +242 -222
  47. package/dist/locales/fi-FI/pages.json +1684 -1604
  48. package/dist/locales/fi-FI/settings.json +889 -441
  49. package/dist/locales/fr-FR/notifications.json +242 -222
  50. package/dist/locales/fr-FR/pages.json +1698 -1618
  51. package/dist/locales/fr-FR/settings.json +898 -450
  52. package/dist/locales/he-IL/common.json +281 -280
  53. package/dist/locales/he-IL/notifications.json +238 -218
  54. package/dist/locales/he-IL/pages.json +1726 -1646
  55. package/dist/locales/he-IL/settings.json +888 -440
  56. package/dist/locales/hu-HU/common.json +281 -280
  57. package/dist/locales/hu-HU/notifications.json +238 -218
  58. package/dist/locales/hu-HU/pages.json +1726 -1646
  59. package/dist/locales/hu-HU/settings.json +888 -440
  60. package/dist/locales/it-IT/common.json +281 -280
  61. package/dist/locales/it-IT/notifications.json +242 -222
  62. package/dist/locales/it-IT/pages.json +1684 -1604
  63. package/dist/locales/it-IT/settings.json +889 -441
  64. package/dist/locales/ja-JP/common.json +281 -280
  65. package/dist/locales/ja-JP/notifications.json +242 -222
  66. package/dist/locales/ja-JP/pages.json +1684 -1604
  67. package/dist/locales/ja-JP/settings.json +889 -441
  68. package/dist/locales/ko-KR/common.json +281 -281
  69. package/dist/locales/ko-KR/notifications.json +242 -222
  70. package/dist/locales/ko-KR/pages.json +1746 -1666
  71. package/dist/locales/ko-KR/settings.json +898 -450
  72. package/dist/locales/nl-NL/common.json +281 -280
  73. package/dist/locales/nl-NL/notifications.json +242 -222
  74. package/dist/locales/nl-NL/pages.json +1699 -1619
  75. package/dist/locales/nl-NL/settings.json +891 -443
  76. package/dist/locales/no-NO/common.json +281 -280
  77. package/dist/locales/no-NO/notifications.json +242 -222
  78. package/dist/locales/no-NO/pages.json +1684 -1604
  79. package/dist/locales/no-NO/settings.json +889 -441
  80. package/dist/locales/pl-PL/common.json +281 -280
  81. package/dist/locales/pl-PL/notifications.json +242 -222
  82. package/dist/locales/pl-PL/pages.json +1684 -1604
  83. package/dist/locales/pl-PL/settings.json +889 -441
  84. package/dist/locales/pt-BR/common.json +281 -280
  85. package/dist/locales/pt-BR/notifications.json +242 -222
  86. package/dist/locales/pt-BR/pages.json +1725 -1645
  87. package/dist/locales/pt-BR/settings.json +889 -441
  88. package/dist/locales/pt-PT/common.json +281 -280
  89. package/dist/locales/pt-PT/notifications.json +242 -222
  90. package/dist/locales/pt-PT/pages.json +1684 -1604
  91. package/dist/locales/pt-PT/settings.json +889 -441
  92. package/dist/locales/ro-RO/common.json +281 -280
  93. package/dist/locales/ro-RO/notifications.json +242 -222
  94. package/dist/locales/ro-RO/pages.json +1684 -1604
  95. package/dist/locales/ro-RO/settings.json +889 -441
  96. package/dist/locales/ru-RU/common.json +281 -280
  97. package/dist/locales/ru-RU/notifications.json +242 -222
  98. package/dist/locales/ru-RU/pages.json +1684 -1604
  99. package/dist/locales/ru-RU/settings.json +889 -441
  100. package/dist/locales/sr-SP/common.json +281 -280
  101. package/dist/locales/sr-SP/notifications.json +238 -218
  102. package/dist/locales/sr-SP/pages.json +1726 -1646
  103. package/dist/locales/sr-SP/settings.json +888 -440
  104. package/dist/locales/sv-SE/common.json +281 -280
  105. package/dist/locales/sv-SE/notifications.json +242 -222
  106. package/dist/locales/sv-SE/pages.json +1684 -1604
  107. package/dist/locales/sv-SE/settings.json +889 -441
  108. package/dist/locales/tr-TR/common.json +281 -280
  109. package/dist/locales/tr-TR/notifications.json +238 -218
  110. package/dist/locales/tr-TR/pages.json +1726 -1646
  111. package/dist/locales/tr-TR/settings.json +888 -440
  112. package/dist/locales/uk-UA/common.json +13 -12
  113. package/dist/locales/uk-UA/nav.json +17 -23
  114. package/dist/locales/uk-UA/notifications.json +242 -222
  115. package/dist/locales/uk-UA/pages.json +121 -41
  116. package/dist/locales/uk-UA/settings.json +889 -441
  117. package/dist/locales/vi-VN/common.json +281 -280
  118. package/dist/locales/vi-VN/notifications.json +238 -218
  119. package/dist/locales/vi-VN/pages.json +1726 -1646
  120. package/dist/locales/vi-VN/settings.json +888 -440
  121. package/dist/locales/zh-CN/common.json +281 -280
  122. package/dist/locales/zh-CN/notifications.json +242 -222
  123. package/dist/locales/zh-CN/pages.json +1695 -1615
  124. package/dist/locales/zh-CN/settings.json +898 -450
  125. package/dist/locales/zh-TW/common.json +281 -280
  126. package/dist/locales/zh-TW/notifications.json +242 -222
  127. package/dist/locales/zh-TW/pages.json +1804 -1724
  128. package/dist/locales/zh-TW/settings.json +888 -440
  129. package/package.json +1 -1
  130. package/src/locales/af-ZA/common.json +281 -280
  131. package/src/locales/af-ZA/notifications.json +238 -218
  132. package/src/locales/af-ZA/pages.json +1726 -1646
  133. package/src/locales/af-ZA/settings.json +888 -440
  134. package/src/locales/ar-SA/common.json +281 -280
  135. package/src/locales/ar-SA/notifications.json +242 -222
  136. package/src/locales/ar-SA/pages.json +1684 -1604
  137. package/src/locales/ar-SA/settings.json +889 -441
  138. package/src/locales/ca-ES/common.json +281 -280
  139. package/src/locales/ca-ES/notifications.json +238 -218
  140. package/src/locales/ca-ES/pages.json +1682 -1602
  141. package/src/locales/ca-ES/settings.json +888 -440
  142. package/src/locales/cs-CZ/common.json +281 -280
  143. package/src/locales/cs-CZ/notifications.json +242 -222
  144. package/src/locales/cs-CZ/pages.json +1688 -1608
  145. package/src/locales/cs-CZ/settings.json +889 -441
  146. package/src/locales/da-DK/common.json +281 -280
  147. package/src/locales/da-DK/notifications.json +242 -222
  148. package/src/locales/da-DK/pages.json +1684 -1604
  149. package/src/locales/da-DK/settings.json +889 -441
  150. package/src/locales/de-DE/common.json +281 -280
  151. package/src/locales/de-DE/notifications.json +242 -222
  152. package/src/locales/de-DE/pages.json +1690 -1610
  153. package/src/locales/de-DE/settings.json +889 -441
  154. package/src/locales/el-GR/common.json +281 -280
  155. package/src/locales/el-GR/notifications.json +242 -222
  156. package/src/locales/el-GR/pages.json +1684 -1604
  157. package/src/locales/el-GR/settings.json +889 -441
  158. package/src/locales/en/notifications.json +26 -6
  159. package/src/locales/en/pages.json +94 -12
  160. package/src/locales/en/settings.json +474 -26
  161. package/src/locales/en-US/common.json +281 -280
  162. package/src/locales/en-US/notifications.json +242 -222
  163. package/src/locales/en-US/pages.json +1774 -1694
  164. package/src/locales/en-US/settings.json +898 -450
  165. package/src/locales/es-ES/common.json +281 -280
  166. package/src/locales/es-ES/notifications.json +242 -222
  167. package/src/locales/es-ES/pages.json +1689 -1609
  168. package/src/locales/es-ES/settings.json +889 -441
  169. package/src/locales/fi-FI/common.json +281 -280
  170. package/src/locales/fi-FI/notifications.json +242 -222
  171. package/src/locales/fi-FI/pages.json +1684 -1604
  172. package/src/locales/fi-FI/settings.json +889 -441
  173. package/src/locales/fr-FR/notifications.json +242 -222
  174. package/src/locales/fr-FR/pages.json +1698 -1618
  175. package/src/locales/fr-FR/settings.json +898 -450
  176. package/src/locales/he-IL/common.json +281 -280
  177. package/src/locales/he-IL/notifications.json +238 -218
  178. package/src/locales/he-IL/pages.json +1726 -1646
  179. package/src/locales/he-IL/settings.json +888 -440
  180. package/src/locales/hu-HU/common.json +281 -280
  181. package/src/locales/hu-HU/notifications.json +238 -218
  182. package/src/locales/hu-HU/pages.json +1726 -1646
  183. package/src/locales/hu-HU/settings.json +888 -440
  184. package/src/locales/it-IT/common.json +281 -280
  185. package/src/locales/it-IT/notifications.json +242 -222
  186. package/src/locales/it-IT/pages.json +1684 -1604
  187. package/src/locales/it-IT/settings.json +889 -441
  188. package/src/locales/ja-JP/common.json +281 -280
  189. package/src/locales/ja-JP/notifications.json +242 -222
  190. package/src/locales/ja-JP/pages.json +1684 -1604
  191. package/src/locales/ja-JP/settings.json +889 -441
  192. package/src/locales/ko-KR/common.json +281 -281
  193. package/src/locales/ko-KR/notifications.json +242 -222
  194. package/src/locales/ko-KR/pages.json +1746 -1666
  195. package/src/locales/ko-KR/settings.json +898 -450
  196. package/src/locales/nl-NL/common.json +281 -280
  197. package/src/locales/nl-NL/notifications.json +242 -222
  198. package/src/locales/nl-NL/pages.json +1699 -1619
  199. package/src/locales/nl-NL/settings.json +891 -443
  200. package/src/locales/no-NO/common.json +281 -280
  201. package/src/locales/no-NO/notifications.json +242 -222
  202. package/src/locales/no-NO/pages.json +1684 -1604
  203. package/src/locales/no-NO/settings.json +889 -441
  204. package/src/locales/pl-PL/common.json +281 -280
  205. package/src/locales/pl-PL/notifications.json +242 -222
  206. package/src/locales/pl-PL/pages.json +1684 -1604
  207. package/src/locales/pl-PL/settings.json +889 -441
  208. package/src/locales/pt-BR/common.json +281 -280
  209. package/src/locales/pt-BR/notifications.json +242 -222
  210. package/src/locales/pt-BR/pages.json +1725 -1645
  211. package/src/locales/pt-BR/settings.json +889 -441
  212. package/src/locales/pt-PT/common.json +281 -280
  213. package/src/locales/pt-PT/notifications.json +242 -222
  214. package/src/locales/pt-PT/pages.json +1684 -1604
  215. package/src/locales/pt-PT/settings.json +889 -441
  216. package/src/locales/ro-RO/common.json +281 -280
  217. package/src/locales/ro-RO/notifications.json +242 -222
  218. package/src/locales/ro-RO/pages.json +1684 -1604
  219. package/src/locales/ro-RO/settings.json +889 -441
  220. package/src/locales/ru-RU/common.json +281 -280
  221. package/src/locales/ru-RU/notifications.json +242 -222
  222. package/src/locales/ru-RU/pages.json +1684 -1604
  223. package/src/locales/ru-RU/settings.json +889 -441
  224. package/src/locales/sr-SP/common.json +281 -280
  225. package/src/locales/sr-SP/notifications.json +238 -218
  226. package/src/locales/sr-SP/pages.json +1726 -1646
  227. package/src/locales/sr-SP/settings.json +888 -440
  228. package/src/locales/sv-SE/common.json +281 -280
  229. package/src/locales/sv-SE/notifications.json +242 -222
  230. package/src/locales/sv-SE/pages.json +1684 -1604
  231. package/src/locales/sv-SE/settings.json +889 -441
  232. package/src/locales/tr-TR/common.json +281 -280
  233. package/src/locales/tr-TR/notifications.json +238 -218
  234. package/src/locales/tr-TR/pages.json +1726 -1646
  235. package/src/locales/tr-TR/settings.json +888 -440
  236. package/src/locales/uk-UA/common.json +13 -12
  237. package/src/locales/uk-UA/nav.json +17 -23
  238. package/src/locales/uk-UA/notifications.json +242 -222
  239. package/src/locales/uk-UA/pages.json +121 -41
  240. package/src/locales/uk-UA/settings.json +889 -441
  241. package/src/locales/vi-VN/common.json +281 -280
  242. package/src/locales/vi-VN/notifications.json +238 -218
  243. package/src/locales/vi-VN/pages.json +1726 -1646
  244. package/src/locales/vi-VN/settings.json +888 -440
  245. package/src/locales/zh-CN/common.json +281 -280
  246. package/src/locales/zh-CN/notifications.json +242 -222
  247. package/src/locales/zh-CN/pages.json +1695 -1615
  248. package/src/locales/zh-CN/settings.json +898 -450
  249. package/src/locales/zh-TW/common.json +281 -280
  250. package/src/locales/zh-TW/notifications.json +242 -222
  251. package/src/locales/zh-TW/pages.json +1804 -1724
  252. package/src/locales/zh-TW/settings.json +888 -440
@@ -1,859 +1,673 @@
1
1
  {
2
- "login": {
3
- "title": "Tracearr",
4
- "tagline": "Tracearr - Stream access management",
5
- "createAccountHeading": "Create your account to get started",
6
- "signInHeading": "Sign in to your account",
7
- "createAccountDescription": "Create an account to manage your media servers",
8
- "signInDescription": "Sign in to access your dashboard",
9
- "selectPlexServer": "Select your Plex server",
10
- "waitingForPlex": "Waiting for Plex authorization...",
11
- "completeInPopup": "Complete sign-in in the popup window",
12
- "reopenPlexLogin": "Reopen Plex Login",
13
- "continueWith": "Continue with {{provider}}",
14
- "usernameOrEmail": "Username or Email",
15
- "identifierPlaceholder": "Username or email address",
16
- "username": "Username",
17
- "usernamePlaceholder": "yourusername",
18
- "emailPlaceholder": "your@email.com",
19
- "displayNamePlaceholder": "Choose a display name",
20
- "passwordPlaceholder": "At least 8 characters",
21
- "yourPasswordPlaceholder": "Your password",
22
- "setupNote": "After creating your account, you'll add your Plex or Jellyfin servers from Settings.",
23
- "localDisabledHint": "Local sign-in is disabled for this instance. Ask an admin to run `enable-local-login` from the Tracearr CLI to re-enable it.",
24
- "oidcError": "Single sign-on failed. Please try again or use another sign-in method.",
25
- "accountCreated": "Account created successfully!",
26
- "connectedTo": "Connected to {{name}}",
27
- "plexAuthFailed": "Plex authentication failed",
28
- "plexStartFailed": "Failed to start Plex login",
29
- "serverConnectFailed": "Failed to connect to server",
30
- "signupFailed": "Signup failed",
31
- "createAccountFailed": "Failed to create account",
32
- "loginFailed": "Login failed",
33
- "invalidCredentials": "Invalid email or password",
34
- "claimCodeRequired": "First-time setup requires a claim code",
35
- "enterClaimCode": "Enter Claim Code",
36
- "claimCodeDescription": "Check your server logs for the claim code to proceed with setup",
37
- "claimCodeLabel": "Claim Code",
38
- "claimCodeHint": "The claim code is printed in the server logs when the container starts",
39
- "validateClaimCode": "Validate Claim Code",
40
- "claimCodeSecurityNote": "This security measure ensures only authorized users can complete first-time setup"
41
- },
42
- "dashboard": {
43
- "alerts": "Alerts",
44
- "plays": "Plays",
45
- "watchTime": "Watch Time",
46
- "activeUsers": "Active Users",
47
- "nowPlaying": "Now Playing",
48
- "streamLocations": "Stream Locations",
49
- "serverResources": "Server Resources",
50
- "bandwidth": "Bandwidth",
51
- "noActiveStreams": "No active streams",
52
- "streamsAppearHere": "Active streams will appear here when users start watching"
53
- },
54
- "users": {
55
- "title": "Users",
56
- "showRemoved": "Show removed",
57
- "noUsersFound": "No users found.",
58
- "searchPlaceholder": "Search users...",
59
- "selectAllUsers": "Select all {{count}} users",
60
- "serversColumn": "Servers",
61
- "resetTrustScore": "Reset Trust Score",
62
- "resetTrustScoreTitle_one": "Reset Trust Score for {{count}} User",
63
- "resetTrustScoreTitle_other": "Reset Trust Score for {{count}} Users",
64
- "resetTrustScoreConfirm": "Are you sure you want to reset the trust score to 100? This action cannot be undone.",
65
- "mergeUsers": "Merge users",
66
- "mergeDialogTitle": "Merge users",
67
- "mergeDialogDescription": "Every server account, session, and violation from the duplicate moves to the primary. The duplicate identity is deleted.",
68
- "mergePickPrimary": "Choose the primary identity",
69
- "mergePrimaryBadge": "Primary",
70
- "mergePrimaryForced": "This account can log in, so it must stay the primary.",
71
- "mergeSameServerWarningTitle": "This action is irreversible",
72
- "mergeSameServerDialogDescription": "This merge permanently combines both accounts on the same server. It cannot be undone.",
73
- "mergeSameServerWarning": "Both identities already have an account on the same server. Merging will permanently combine their session history, violations, and trust score into a single account on that server. This cannot be undone, and splitting the account afterward will not restore the original two accounts.",
74
- "mergeSameServerAcknowledge": "I understand the same-server history combine cannot be undone",
75
- "mergeSameServerFallbackName": "this server",
76
- "mergeServerAccountRemoved": "Removed",
77
- "mergeConfirm": "Merge",
78
- "mergeSelectTwo": "Select exactly two users to merge",
79
- "mergeSameIdentity": "These accounts already belong to the same user",
80
- "mergeSelectAllActive": "Clear the select-all selection and pick exactly two users to merge",
81
- "suggestionsTitle": "Possible duplicate users",
82
- "suggestionsDescription": "These identities look like the same person across servers. Review and merge them if they match.",
83
- "suggestionsReview": "Review",
84
- "suggestionsMatchEmail": "Same email",
85
- "suggestionsMatchUsername": "Same username",
86
- "suggestionsError": "Could not load merge suggestions",
87
- "filterHasAccessTo": "Has access to",
88
- "filterHasAccessToPlaceholder": "Any server",
89
- "filterHasAccessToHint": "Shows people with an active account on every server selected."
90
- },
91
- "userDetail": {
92
- "backToUsers": "Back to Users",
93
- "userNotFound": "User not found",
94
- "userInfo": "User Info",
95
- "statistics": "Statistics",
96
- "sessions": "Sessions",
97
- "violations": "Violations",
98
- "terminationHistory": "Termination History",
99
- "noViolationsFound": "No violations for this user.",
100
- "noTerminationsFound": "No stream terminations for this user.",
101
- "byRule": "By / Rule",
102
- "manual": "Manual",
103
- "unknownRule": "Unknown rule",
104
- "adjustTrustScore": "Adjust Trust Score",
105
- "linkedAccounts": "Linked accounts",
106
- "splitAccount": "Split into separate user",
107
- "splitConfirmTitle": "Split server account",
108
- "splitConfirmDescription": "Detach this server account into its own user. Its watch history and violations move with it.",
109
- "splitConfirmLoading": "Splitting...",
110
- "acrossAllServers": "Across all linked accounts:",
111
- "overallTrust": "Overall Trust",
112
- "serverScope": "Server",
113
- "allServers": "All servers",
114
- "title": "User Details"
115
- },
116
- "history": {
117
- "title": "History",
118
- "description": "Browse all streaming sessions with powerful filtering",
119
- "loadingMore": "Loading more...",
120
- "scrollForMore": "Scroll for more",
121
- "showingAllResults": "Showing all {{total}} results",
122
- "deleteSession_one": "Delete {{count}} Session",
123
- "deleteSession_other": "Delete {{count}} Sessions",
124
- "deleteSessionsConfirm": "Are you sure you want to delete? This action cannot be undone."
125
- },
126
- "library": {
127
- "title": "Library",
128
- "description": "Top movies and shows on your server",
129
- "topMovies": "Top Movies",
130
- "topShows": "Top TV Shows",
131
- "noMoviePlays": "No movie plays in this period",
132
- "noShowPlays": "No TV show plays in this period",
133
- "overview": {
134
- "description": "Library health and growth metrics",
135
- "lastUpdated": "Last updated:",
136
- "totalItems": "Total Items",
137
- "shows": "shows",
138
- "added": "Added",
139
- "libraryGrowth": "Library Growth",
140
- "failedToLoad": "Failed to load library statistics",
141
- "failedToLoadDesc": "Could not fetch library data. Please try again.",
142
- "thisPeriod": "this period",
143
- "thisWeek": "this week",
144
- "thisMonth": "this month",
145
- "thisYear": "this year",
146
- "serversNeedSync": "These servers need to sync:"
147
- },
148
- "quality": {
149
- "title": "Quality",
150
- "description": "Resolution and codec distribution",
151
- "qualityEvolution": "Quality Evolution",
152
- "all": "All",
153
- "failedToLoad": "Failed to load quality data",
154
- "failedToLoadDesc": "Could not fetch quality data. Please try again."
155
- },
156
- "storage": {
157
- "title": "Storage",
158
- "description": "Storage usage, predictions, and optimization",
159
- "totalStorage": "Total Storage",
160
- "growthRate": "Growth Rate",
161
- "duplicates": "Duplicates",
162
- "groups": "groups",
163
- "recoverable": "recoverable",
164
- "staleContent": "Stale Content",
165
- "staleContentDesc": "Content that may be candidates for removal",
166
- "items": "items",
167
- "unused": "unused",
168
- "storageTrend": "Storage Trend",
169
- "confidence": "Confidence",
170
- "confidenceHigh": "High",
171
- "confidenceMedium": "Medium",
172
- "confidenceLow": "Low",
173
- "zeroGrowth": "0 GB/mo",
174
- "predictions": "Predictions",
175
- "contentROI": "Content ROI",
176
- "contentROIDesc": "Watch value per storage cost",
177
- "avgHoursPerGB": "avg hours/GB",
178
- "insufficientData": "Insufficient data",
179
- "of": "of",
180
- "days": "days",
181
- "failedToLoad": "Failed to load storage data",
182
- "failedToLoadDesc": "Could not fetch storage data. Please try again.",
183
- "duplicatesTitle": "Duplicates",
184
- "duplicatesSubtitle": "Titles stored as more than one physical file, across servers, libraries, and versions",
185
- "growthPreChangeover": "based on pre-update history",
186
- "loadingDuplicates": "Loading duplicates...",
187
- "duplicatesFailed": "Failed to load duplicates",
188
- "noDuplicatesTitle": "No duplicates found",
189
- "noDuplicatesDesc": "No titles with more than one physical file detected.",
190
- "colTitle": "Title",
191
- "colMatchType": "Match Type",
192
- "colCopies": "Copies",
193
- "colRecoverable": "Recoverable Space",
194
- "sameServer": "Same server",
195
- "mirror": "Mirror"
196
- },
197
- "watch": {
198
- "title": "Watch Analytics",
199
- "description": "Viewing behavior and content engagement",
200
- "watched": "Watched",
201
- "percentWatched": "% watched",
202
- "totalWatchTime": "Total Watch Time",
203
- "avgPerItem": "avg per item",
204
- "completed": "Completed",
205
- "peakHour": "Peak Hour",
206
- "viewingHours": "Viewing Hours",
207
- "peak": "Peak:",
208
- "monthlyTrends": "Monthly Trends",
209
- "busiest": "Busiest:",
210
- "quietest": "Quietest:",
211
- "bingeHighlights": "Binge Highlights",
212
- "bingeHighlightsDesc": "Shows with the most intensive viewing patterns",
213
- "bingeSessions": "",
214
- "noData": "No watch data yet",
215
- "noDataDesc": "Watch analytics will appear here once content has been played. Check back after some viewing activity.",
216
- "failedToLoad": "Failed to load watch analytics",
217
- "failedToLoadDesc": "Could not fetch watch data."
218
- },
219
- "emptyState": {
220
- "checkingStatus": "Checking library status...",
221
- "backfillAvailable": {
222
- "title": "Historical data available",
223
- "bodyWithDays": "Your library has {{days}} days of history. Generate snapshots to see trends in charts.",
224
- "bodyGeneric": "Generate historical snapshots to see library trends over time.",
225
- "syncRunningTitle": "Library sync in progress...",
226
- "syncRunningBody": "Historical data generation will start automatically once the sync completes."
227
- },
228
- "generateHistory": "Generate History",
229
- "starting": "Starting...",
230
- "syncInProgress": {
231
- "title": "Library sync in progress...",
232
- "body": "Library statistics will appear once the sync completes. This may take a few minutes depending on library size."
233
- },
234
- "notSynced": {
235
- "title": "Library not synced yet",
236
- "body": "Library statistics will appear here once the library has been synced. This typically happens automatically every hour."
237
- },
238
- "noMedia": {
239
- "title": "No movies or shows yet",
240
- "body": "This library is synced but doesn't have any movies or shows in it yet."
241
- },
242
- "syncNow": "Sync Now",
243
- "syncing": "Syncing...",
244
- "notSyncedShort": "Not synced yet",
245
- "backfillRunning": {
246
- "title": "Generating historical data...",
247
- "fallbackBody": "Creating snapshots from library history. This may take a few minutes.",
248
- "progress": "{{processed}} of {{total}} libraries",
249
- "snapshotsSuffix": " ({{count}} snapshots)"
250
- },
251
- "multiServer": {
252
- "title": "Some libraries need attention",
253
- "body": "Sync the servers below to see combined library statistics.",
254
- "needsBackfillIntro": "These servers are synced but have no historical data yet:"
255
- },
256
- "toast": {
257
- "noServerSelected": "No server selected",
258
- "syncStartedTitle": "Library sync started",
259
- "syncStartedDesc": "This may take a few minutes depending on library size.",
260
- "syncFailedTitle": "Failed to start sync",
261
- "genericRetry": "Please try again.",
262
- "backfillStartedTitle": "Backfill started",
263
- "backfillStartedDesc": "Historical snapshots are being generated.",
264
- "backfillFailedTitle": "Failed to start backfill",
265
- "backfillCompleteTitle": "Backfill complete",
266
- "backfillErrorTitle": "Backfill failed"
267
- }
268
- },
269
- "versionsBackfill": {
270
- "banner": "File version data is still being collected for this server. Run a library sync to finish.",
271
- "action": "Sync now",
272
- "syncFailed": "Sync failed to start on {{count}} server(s). Check your permissions and server status.",
273
- "syncStarted": "Library sync started."
274
- }
275
- },
276
2
  "activity": {
277
- "title": "Activity",
278
- "description": "Play trends, patterns, and streaming behavior",
279
- "playsOverTime": "Plays Over Time",
3
+ "activityByDayOfWeek": "Activity by Day of Week",
4
+ "activityByHourOfDay": "Activity by Hour of Day",
280
5
  "concurrentStreams": "Concurrent Streams",
6
+ "description": "Play trends, patterns, and streaming behavior",
281
7
  "engagementBreakdown": "Engagement Breakdown",
282
8
  "howUsersEngage": "How users engage with content",
9
+ "platforms": "Platforms",
10
+ "playsOverTime": "Plays Over Time",
283
11
  "playsVsSessions": "Plays vs Sessions",
284
12
  "playsVsSessionsDesc": "Full completions only — counts a play when total watch time covers a content's entire runtime",
285
- "activityByDayOfWeek": "Activity by Day of Week",
286
- "activityByHourOfDay": "Activity by Hour of Day",
287
- "platforms": "Platforms",
288
- "streamQuality": "Stream Quality"
13
+ "streamQuality": "Stream Quality",
14
+ "title": "Activity"
289
15
  },
290
- "violations": {
291
- "title": "Violations",
292
- "tryAdjustingFilters": "Try adjusting your filters",
293
- "selectAllViolations": "Select all {{count}} violations matching filters",
294
- "dismissViolation": "Dismiss Violation",
295
- "dismissViolationConfirm": "Are you sure you want to dismiss this violation? This will remove it from the violation log permanently.",
296
- "dismissViolation_one": "Dismiss {{count}} Violation",
297
- "dismissViolation_other": "Dismiss {{count}} Violations",
298
- "dismissViolationsConfirm": "Are you sure you want to dismiss? This will remove them from the violation log permanently and restore associated trust scores.",
299
- "noViolationsFound": "No violations found",
300
- "noViolationsRecorded": "No violations have been recorded yet.",
301
- "allSeverities": "All Severities",
302
- "allStatuses": "All Statuses",
303
- "allRules": "All rules",
304
- "filterPeople": "People",
305
- "allPeople": "All people",
306
- "peopleSelectedCount": "{{count}} people",
307
- "personFilterPlaceholder": "Filter by person",
308
- "personFilterEmpty": "No matching people found",
309
- "personFilterError": "Failed to load people",
310
- "filterByPerson": "Filter violations by this person",
311
- "detail": {
312
- "notFound": "Violation not found",
313
- "violationDetails": "Violation Details",
314
- "userInfo": "User",
315
- "sessions": "Sessions",
316
- "noSessions": "No sessions associated with this violation",
317
- "trigger": "Trigger",
318
- "map": "Session Locations",
319
- "actions": "Actions Taken",
320
- "timestamps": "Timestamps",
321
- "created": "Created",
322
- "acknowledged": "Acknowledged",
323
- "detected": "Detected",
324
- "inactivity": "Inactivity Details",
325
- "daysInactive": "Days Inactive",
326
- "threshold": "Threshold",
327
- "lastActivity": "Last Activity",
328
- "neverActive": "Never active",
329
- "conditionEvidence": "Condition Evidence",
330
- "conditionGroup": "Condition Group {{index}}",
331
- "matched": "{{matched}}/{{total}} matched",
332
- "actual": "Actual",
333
- "relatedSessions": "{{count}} related session",
334
- "relatedSessions_one": "{{count}} related session",
335
- "relatedSessions_other": "{{count}} related sessions"
336
- }
16
+ "apiDocs": {
17
+ "apiKeyAutoLoaded": "API key auto-loaded",
18
+ "backToSettings": "Back to Settings",
19
+ "noApiKey": "No API key generated - create one in Settings to test endpoints",
20
+ "specLoadError": "Failed to load the API specification. Check your API key and try again.",
21
+ "versionSwitcherLabel": "API documentation version",
22
+ "versionV1": "API v1",
23
+ "versionV2": "API v2"
337
24
  },
338
25
  "automations": {
339
26
  "actions": {
340
- "send": {
341
- "label": "Send Notification",
342
- "description": "Send to one or more destinations",
343
- "fields": {
344
- "cooldown_minutes": {
345
- "description": "Minimum time between notifications"
346
- }
347
- },
348
- "ran": "Sent a notification"
349
- },
350
- "trust": {
351
- "label": "Trust Score",
352
- "description": "Adjust, set, or reset the trust score",
353
- "fields": {
354
- "mode": {
355
- "label": "Mode"
356
- },
357
- "amount": {
358
- "label": "Amount",
359
- "description": "Positive to increase, negative to decrease"
360
- },
361
- "value": {
362
- "label": "Value"
363
- }
364
- },
365
- "ran": "Changed the trust score"
366
- },
367
27
  "kill_stream": {
368
- "label": "Kill Stream",
369
28
  "description": "Terminate the active stream",
370
29
  "fields": {
371
30
  "cooldown_minutes": {
372
31
  "description": "Minimum time between terminations for the same user"
373
32
  },
374
33
  "delay_seconds": {
375
- "label": "Sustain window",
376
- "description": "Waits this many seconds, then kills the stream only if the automation still matches. 0 kills right after a final re-check."
377
- },
378
- "target": {
379
- "description": "Which sessions to terminate"
34
+ "description": "Waits this many seconds, then kills the stream only if the automation still matches. 0 kills right after a final re-check.",
35
+ "label": "Sustain window"
380
36
  },
381
37
  "message": {
382
38
  "placeholder": "Optional message"
39
+ },
40
+ "target": {
41
+ "description": "Which sessions to terminate"
383
42
  }
384
43
  },
44
+ "label": "Kill Stream",
385
45
  "ran": "Stopped the stream"
386
46
  },
387
47
  "message_client": {
388
- "label": "Message Client",
389
48
  "description": "Send a message to the media player",
390
- "hint": "Jellyfin and Emby only. Plex only supports messages when killing a stream.",
391
49
  "fields": {
392
- "target": {
393
- "description": "Which sessions to message"
394
- },
395
50
  "message": {
396
51
  "placeholder": "Message to display…"
52
+ },
53
+ "target": {
54
+ "description": "Which sessions to message"
397
55
  }
398
56
  },
57
+ "hint": "Jellyfin and Emby only. Plex only supports messages when killing a stream.",
58
+ "label": "Message Client",
399
59
  "ran": "Put a message on the player"
60
+ },
61
+ "send": {
62
+ "description": "Send to one or more destinations",
63
+ "fields": {
64
+ "cooldown_minutes": {
65
+ "description": "Minimum time between notifications"
66
+ }
67
+ },
68
+ "label": "Send Notification",
69
+ "ran": "Sent a notification"
70
+ },
71
+ "trust": {
72
+ "description": "Adjust, set, or reset the trust score",
73
+ "fields": {
74
+ "amount": {
75
+ "description": "Positive to increase, negative to decrease",
76
+ "label": "Amount"
77
+ },
78
+ "mode": {
79
+ "label": "Mode"
80
+ },
81
+ "value": {
82
+ "label": "Value"
83
+ }
84
+ },
85
+ "label": "Trust Score",
86
+ "ran": "Changed the trust score"
400
87
  }
401
88
  },
402
89
  "activity": {
403
- "title": "Activity",
90
+ "branch": {
91
+ "else": "Took the second branch",
92
+ "then": "Took the first branch"
93
+ },
404
94
  "description": "What this automation did, newest first. Runs are kept for {{days}} days.",
405
- "outcome": "Outcome",
406
- "who": "Who",
407
- "where": "Where",
408
- "playing": "Playing",
409
- "from": "From",
410
- "summary": "Summary",
411
- "started": "Started",
95
+ "empty": "No runs yet",
96
+ "emptyDescription": "Runs are listed here once a trigger matches.",
97
+ "emptyRan": "Nothing has matched yet",
98
+ "emptyRanDescription_one": "{{count}} check ran and did not match.",
99
+ "emptyRanDescription_other": "{{count}} checks ran and did not match.",
412
100
  "finished": "Finished",
101
+ "from": "From",
102
+ "group": "Group {{number}}",
103
+ "item": "Item",
413
104
  "noSummary": "No notes",
105
+ "openInEditor": "Open in the builder with this run",
106
+ "outcome": "Outcome",
414
107
  "outcomes": {
415
108
  "completed": "Ran",
416
- "stopped_by_condition": "No match",
417
- "error": "Failed"
109
+ "error": "Failed",
110
+ "stopped_by_condition": "No match"
418
111
  },
419
- "empty": "No runs yet",
420
- "emptyDescription": "Runs are listed here once a trigger matches.",
421
- "runTitle": "Run",
112
+ "playing": "Playing",
113
+ "recordedViolation": "Recorded a violation",
422
114
  "runLoading": "Loading the run",
423
- "triggeredBy": "Triggered by {{trigger}}",
424
- "unknownStep": "Unrecognized step",
115
+ "runTitle": "Run",
116
+ "started": "Started",
117
+ "summary": "Summary",
425
118
  "tabs": {
426
119
  "all": "All",
427
120
  "completed": "Ran",
428
- "stopped_by_condition": "No match",
429
- "error": "Failed"
430
- },
431
- "group": "Group {{number}}",
432
- "branch": {
433
- "then": "Took the first branch",
434
- "else": "Took the second branch"
121
+ "error": "Failed",
122
+ "stopped_by_condition": "No match"
435
123
  },
436
- "whyBranch": "What it read",
437
- "openInEditor": "Open in the builder with this run",
438
124
  "tabsLabel": "Filter by outcome",
439
- "emptyRan": "Nothing has matched yet",
440
- "emptyRanDescription_one": "{{count}} check ran and did not match.",
441
- "emptyRanDescription_other": "{{count}} checks ran and did not match.",
442
- "item": "Item",
443
- "recordedViolation": "Recorded a violation"
125
+ "title": "Activity",
126
+ "triggeredBy": "Triggered by {{trigger}}",
127
+ "unknownStep": "Unrecognized step",
128
+ "where": "Where",
129
+ "who": "Who",
130
+ "whyBranch": "What it read"
444
131
  },
445
132
  "allKinds": "All kinds",
446
- "allStatuses": "All statuses",
447
133
  "allSeverities": "All severities",
134
+ "allStatuses": "All statuses",
448
135
  "bind": {
449
- "nameHelper": "The name in the automations list.",
450
- "namePlaceholder": "A name for this automation",
136
+ "accountLabel": "Which account",
451
137
  "activeLabel": "Turn it on now",
138
+ "anyServer": "Any server",
452
139
  "back": "Back",
453
- "submit": "Use this",
454
- "submitting": "Setting it up…",
140
+ "created": "{{name}} is set up and running.",
141
+ "createdOff": "{{name}} was created and is off. Turn it on from the list.",
455
142
  "customize": "Open in the builder",
143
+ "destinationsLabel": "Send to",
456
144
  "doors": {
457
145
  "helper": "Use this keeps the steps as they are; the answers above can change later. Open in the builder makes every step editable and ends the link to the ready-made automation."
458
146
  },
459
- "anyServer": "Any server",
460
- "serverHelper": "Any server means all of them.",
461
- "serverLabel": "Which server",
462
- "accountLabel": "Which account",
463
- "personLabel": "Which person",
464
- "destinationsLabel": "Send to",
465
- "required": "Pick at least one.",
147
+ "failed": "Couldn't set that up. Try again.",
148
+ "helper": {
149
+ "clientMessage": "Shown on the player while it keeps playing.",
150
+ "killMessage": "Shown on the player when the stream stops."
151
+ },
152
+ "nameHelper": "The name in the automations list.",
153
+ "namePlaceholder": "A name for this automation",
466
154
  "needs": {
467
155
  "title": "What it needs"
468
156
  },
469
- "helper": {
470
- "killMessage": "Shown on the player when the stream stops.",
471
- "clientMessage": "Shown on the player while it keeps playing."
472
- },
473
157
  "noInputs": "Nothing to fill in.",
474
- "failed": "Couldn't set that up. Try again.",
475
- "created": "{{name}} is set up and running.",
476
- "createdOff": "{{name}} was created and is off. Turn it on from the list."
158
+ "personLabel": "Which person",
159
+ "required": "Pick at least one.",
160
+ "serverHelper": "Any server means all of them.",
161
+ "serverLabel": "Which server",
162
+ "submit": "Use this",
163
+ "submitting": "Setting it up…"
477
164
  },
478
165
  "builder": {
479
- "destinationDisabled": "Disabled destination",
480
- "noDestinations": "No destinations yet. Add one to send notifications.",
481
- "newDestination": "New destination",
482
- "errors": {
483
- "sendNeedsDestination": "Pick at least one destination",
484
- "nameRequired": "Automation name is required",
485
- "scopeIncomplete": "Pick a target for the selected scope",
486
- "triggerRequired": "Add what starts this, or switch one back on",
487
- "policyNeedsSubject": "A policy needs a stream or account trigger: violations are about a person",
488
- "fieldUnavailable": "This check is not available for every trigger here",
489
- "operatorInvalid": "This comparison does not fit the condition",
490
- "valueInvalid": "This value does not fit the condition",
491
- "actionUnavailable": "These triggers do not supply what this action needs",
492
- "variableUnavailable": "The message names something not every trigger here supplies",
493
- "minutesRange": "Between {{min}} and {{max}} minutes",
494
- "daysRange": "Between {{min}} and {{max}} days",
495
- "measureInvalid": "Pick how the minutes are counted",
496
- "fieldNotAvailableFor": "Not available for: {{triggers}}",
497
- "trustAmountRange": "Trust changes by between -100 and 100 points",
498
- "trustValueRange": "Trust score is between 0 and 100",
499
- "messageRequired": "Type the message to show",
500
- "tooLong": "At most {{max}} characters"
501
- },
502
- "recordAs": {
503
- "label": "When this runs, record it as",
504
- "policy": "A violation",
505
- "policyDescription": "Listed in Violations; can be acknowledged.",
506
- "notification": "An alert",
507
- "notificationDescription": "Recorded in Activity; never a violation."
166
+ "actions": {
167
+ "add": "Add action",
168
+ "addBranch": "Add action",
169
+ "branchElse": "Otherwise…",
170
+ "branchElseEmpty": "Nothing. The automation carries on.",
171
+ "branchName": "this branch",
172
+ "branchThen": "then",
173
+ "collapseBranch": "Hide this branch's steps",
174
+ "confirmRemoveDescription": "Stops happening on save.",
175
+ "confirmRemoveTitle": "Remove this action?",
176
+ "emptyAction": "Choose what happens",
177
+ "emptyDescription": "Send a notification, stop the stream, change a trust score, or run steps only when an extra check passes.",
178
+ "emptyTitle": "What should happen?",
179
+ "expandBranch": "Show this branch's steps",
180
+ "helper": "These run in order, top to bottom.",
181
+ "ifAddCheck": "Add another check",
182
+ "ifNothing": "nothing yet",
183
+ "ifTitle": "If…",
184
+ "menu": "More for {{name}}",
185
+ "moveDown": "Move {{name}} down",
186
+ "moveUp": "Move {{name}} up",
187
+ "policyNote": "A branch does not decide whether this is flagged; the And only if… section does.",
188
+ "sectionTitle": "Do this…"
508
189
  },
509
- "severityLabel": "Severity",
510
190
  "activeLabel": "Active",
511
- "saving": "Saving…",
512
- "selectPlaceholder": "Select…",
513
- "searchPlaceholder": "Search…",
514
- "noMatches": "No matches",
515
191
  "clearSelection": "Clear selection",
516
- "selectedCount": "{{count}} selected",
517
- "scope": {
518
- "label": "Scope",
519
- "global": "Global",
520
- "server": "Specific server",
521
- "account": "Specific account",
522
- "person": "Person (all their servers)",
523
- "serverLabel": "Server",
524
- "serverPlaceholder": "Select server",
525
- "accountLabel": "Account",
526
- "accountPlaceholder": "Select account",
527
- "personLabel": "Person",
528
- "personPlaceholder": "Select person",
529
- "personHelper": "Matches this person on every server they have an account on.",
530
- "noServers": "No servers connected yet.",
531
- "enforceAcrossServers": "Enforce across servers",
532
- "enforceAcrossServersDescription": "Acts on the person's sessions on any of their servers, not only the one that triggered it. Off by default."
533
- },
534
192
  "conditions": {
193
+ "addAnother": "Add another condition",
194
+ "addFirst": "Add a condition",
535
195
  "addGroup": "Add AND condition group",
536
- "fieldPlaceholder": "Select field",
537
- "windowPrefix": "in",
538
- "windowUnit": "hrs",
539
- "uniqueDevices": "Unique devices",
540
- "uniqueDevicesHint": "Counts only sessions from different physical devices.",
541
- "uniqueIps": "Unique IPs",
542
- "uniqueIpsHint": "Counts only sessions from different IP addresses, so same-household streams are not counted.",
543
- "allDeviceTypes": "All device types",
544
- "deviceTypesHint": "Counts only streams from the selected device types. Empty means every device.",
545
- "yes": "Yes",
546
- "no": "No",
547
- "recentlySeen": "Recently seen",
548
- "allCountries": "All countries",
549
- "sectionTitle": "Only when…",
550
- "optional": "optional",
551
- "helper": "Checks that must pass first. Empty means it runs every time.",
552
- "emptyLine": "No extra checks. This runs every time.",
553
196
  "all": "all of these",
554
- "any": "any of these",
197
+ "allCountries": "All countries",
198
+ "allDeviceTypes": "All device types",
555
199
  "allHint": "and: every check has to pass",
200
+ "any": "any of these",
556
201
  "anyHint": "or: any one check is enough",
557
- "matchLabel": "How these conditions combine",
202
+ "canNeverPass": "This can never pass. The trigger already fires at {{threshold}}.",
203
+ "deviceTypesHint": "Counts only streams from the selected device types. Empty means every device.",
204
+ "emptyLine": "No extra checks. This runs every time.",
558
205
  "fieldLabel": "Condition",
206
+ "fieldPlaceholder": "Select field",
207
+ "groupSeparator": "and also",
208
+ "helper": "Checks that must pass first. Empty means it runs every time.",
209
+ "matchLabel": "How these conditions combine",
210
+ "no": "No",
211
+ "noFields": "No checks are available for these triggers. Add a stream or account trigger first.",
559
212
  "operatorLabel": "Comparison",
213
+ "optional": "optional",
214
+ "recentlySeen": "Recently seen",
215
+ "removeGroup": "Remove this set of checks",
216
+ "sectionTitle": "Only when…",
217
+ "uniqueDevices": "Unique devices",
218
+ "uniqueDevicesHint": "Counts only sessions from different physical devices.",
219
+ "uniqueIps": "Unique IPs",
220
+ "uniqueIpsHint": "Counts only sessions from different IP addresses, so same-household streams are not counted.",
560
221
  "valueLabel": "Value",
561
- "canNeverPass": "This can never pass. The trigger already fires at {{threshold}}.",
562
- "noFields": "No checks are available for these triggers. Add a stream or account trigger first.",
563
- "groupSeparator": "and also",
564
- "addAnother": "Add another condition",
565
- "addFirst": "Add a condition",
566
- "removeGroup": "Remove this set of checks"
222
+ "windowPrefix": "in",
223
+ "windowUnit": "hrs",
224
+ "yes": "Yes"
567
225
  },
568
- "actions": {
569
- "add": "Add action",
570
- "sectionTitle": "Do this…",
571
- "ifTitle": "If…",
572
- "helper": "These run in order, top to bottom.",
573
- "emptyTitle": "What should happen?",
574
- "emptyDescription": "Send a notification, stop the stream, change a trust score, or run steps only when an extra check passes.",
575
- "emptyAction": "Choose what happens",
576
- "moveUp": "Move {{name}} up",
577
- "moveDown": "Move {{name}} down",
578
- "menu": "More for {{name}}",
579
- "branchName": "this branch",
580
- "confirmRemoveTitle": "Remove this action?",
581
- "confirmRemoveDescription": "Stops happening on save.",
582
- "policyNote": "A branch does not decide whether this is flagged; the And only if… section does.",
583
- "branchThen": "then",
584
- "branchElse": "Otherwise…",
585
- "branchElseEmpty": "Nothing. The automation carries on.",
586
- "ifNothing": "nothing yet",
587
- "ifAddCheck": "Add another check",
588
- "addBranch": "Add action",
589
- "expandBranch": "Show this branch's steps",
590
- "collapseBranch": "Hide this branch's steps"
226
+ "destinationDisabled": "Disabled destination",
227
+ "errors": {
228
+ "actionUnavailable": "These triggers do not supply what this action needs",
229
+ "daysRange": "Between {{min}} and {{max}} days",
230
+ "fieldNotAvailableFor": "Not available for: {{triggers}}",
231
+ "fieldUnavailable": "This check is not available for every trigger here",
232
+ "measureInvalid": "Pick how the minutes are counted",
233
+ "messageRequired": "Type the message to show",
234
+ "minutesRange": "Between {{min}} and {{max}} minutes",
235
+ "nameRequired": "Automation name is required",
236
+ "operatorInvalid": "This comparison does not fit the condition",
237
+ "policyNeedsSubject": "A policy needs a stream or account trigger: violations are about a person",
238
+ "scopeIncomplete": "Pick a target for the selected scope",
239
+ "sendNeedsDestination": "Pick at least one destination",
240
+ "tooLong": "At most {{max}} characters",
241
+ "triggerRequired": "Add what starts this, or switch one back on",
242
+ "trustAmountRange": "Trust changes by between -100 and 100 points",
243
+ "trustValueRange": "Trust score is between 0 and 100",
244
+ "valueInvalid": "This value does not fit the condition",
245
+ "variableUnavailable": "The message names something not every trigger here supplies"
591
246
  },
592
- "when": {
593
- "title": "When…",
594
- "helper": "Any one of these starts it. At least one is required.",
595
- "emptyTitle": "What should start this?",
596
- "emptyDescription": "A stream starting, a server going down, an account going quiet.",
597
- "emptyAction": "Choose what starts it",
598
- "add": "Add trigger",
599
- "or": "or"
247
+ "footer": {
248
+ "problems_one": "{{count}} problem",
249
+ "problems_other": "{{count}} problems",
250
+ "ready": "Ready to save",
251
+ "remaining_one": "{{count}} left to finish",
252
+ "remaining_other": "{{count}} left to finish",
253
+ "search": "to search"
600
254
  },
601
255
  "heldFor": {
602
- "prefix": "A stream has been paused for",
603
- "minutesLabel": "Minutes",
604
- "unit": "minutes",
605
- "measureLabel": "Counted",
606
256
  "current": "this time",
607
- "total": "in total"
257
+ "measureLabel": "Counted",
258
+ "minutesLabel": "Minutes",
259
+ "prefix": "A stream has been paused for",
260
+ "total": "in total",
261
+ "unit": "minutes"
608
262
  },
609
263
  "inactiveFor": {
610
- "prefix": "An account has been inactive for",
611
264
  "daysLabel": "Days",
265
+ "prefix": "An account has been inactive for",
612
266
  "unit": "days"
613
267
  },
614
- "rows": {
615
- "toggle": "Include {{name}}",
616
- "remove": "Remove {{name}}",
617
- "skipped": "Skipped",
618
- "toggleHint": "skip",
619
- "removeHint": "remove",
620
- "expandHint": "open",
621
- "moveHint": "reorder"
622
- },
623
- "picker": {
624
- "searchPlaceholder": "Search or describe what should happen",
625
- "empty": "Nothing matches that.",
626
- "navigate": "move",
627
- "select": "pick",
628
- "close": "close"
629
- },
630
- "sentence": {
631
- "label": "What this automation does",
632
- "placeholderTrigger": "something happens",
633
- "placeholderAction": "do something"
634
- },
635
- "footer": {
636
- "problems_one": "{{count}} problem",
637
- "problems_other": "{{count}} problems",
638
- "remaining_one": "{{count}} left to finish",
639
- "remaining_other": "{{count}} left to finish",
640
- "ready": "Ready to save",
641
- "search": "to search"
642
- },
643
268
  "leave": {
644
- "title": "Leave without saving?",
645
- "confirm": "Leave"
269
+ "confirm": "Leave",
270
+ "title": "Leave without saving?"
646
271
  },
647
272
  "liveCheck": {
648
- "title": "Right now on the servers",
273
+ "actual": "now {{value}}",
274
+ "backToLive": "Back to what's playing now",
649
275
  "checking": "Checking against the sessions playing now…",
650
276
  "empty": "Nothing is playing right now; nothing to check against.",
277
+ "expand": "Show what matched for {{name}}",
651
278
  "failed": "Could not reach the servers to check.",
652
279
  "footnote": "Cooldowns and already-handled sessions aren't simulated.",
653
- "expand": "Show what matched for {{name}}",
654
- "passed": "Passed",
655
280
  "notPassed": "Did not pass",
656
- "actual": "now {{value}}",
657
- "unfinished": "Shows what this would do once the automation is complete.",
281
+ "passed": "Passed",
658
282
  "paused": "Paused while this saves",
659
- "sampleTitle": "What this would do to that run",
660
283
  "sampleGone": "That session is no longer on record; nothing to check against.",
661
- "backToLive": "Back to what's playing now"
662
- }
663
- },
664
- "categories": {
665
- "session_behavior": "Session Behavior",
666
- "stream_quality": "Stream Quality",
667
- "user_attributes": "User Attributes",
668
- "device_client": "Device & Client",
669
- "network_location": "Network & Location",
670
- "scope": "Scope",
671
- "media": "Media"
672
- },
673
- "createAutomation": "Create Automation",
674
- "customAutomation": "Custom automation",
675
- "deleteAutomationConfirm": "Are you sure you want to delete this automation? This action cannot be undone.",
676
- "deleteAutomation_one": "Delete {{count}} Automation",
677
- "deleteAutomation_other": "Delete {{count}} Automations",
678
- "deleteAutomationsConfirm": "Are you sure you want to delete? This action cannot be undone.",
679
- "describe": {
680
- "more_one": "+{{count}} more",
681
- "more_other": "+{{count}} more",
682
- "noValues": "(none)",
683
- "includesSameDevice": "includes same device",
684
- "uniqueIps": "unique IPs",
685
- "deviceTypesOnly": "{{types}} only",
686
- "when": "When {{text}}",
687
- "or": "or {{text}}",
688
- "nothing": "nothing yet",
689
- "onlyWhen": "only when",
690
- "andAlso": "and also",
691
- "allOf": "all of:",
692
- "anyOf": "any of:",
693
- "joinAll": "and",
694
- "joinAny": "or",
695
- "then": "then {{text}}",
696
- "otherwise": "Otherwise",
697
- "appliesTo": "Applies to {{name}}",
698
- "duration": {
699
- "minutes_one": "{{count}} minute",
700
- "minutes_other": "{{count}} minutes",
701
- "days_one": "{{count}} day",
702
- "days_other": "{{count}} days"
284
+ "sampleTitle": "What this would do to that run",
285
+ "title": "Right now on the servers",
286
+ "unfinished": "Shows what this would do once the automation is complete."
703
287
  },
704
- "triggers": {
705
- "sessionStarted": "a stream starts",
706
- "sessionFirstSeen": "",
707
- "sessionStopped": "a stream stops",
708
- "sessionTranscodeChanged": "transcoding starts or stops",
709
- "sessionPaused": "a stream is paused",
710
- "sessionHeldFor": "a stream has been paused for {{duration}}",
711
- "sessionHeldForTotal": "a stream has been paused for {{duration}} in total",
712
- "accountInactiveFor": "an account has been inactive for {{duration}}",
713
- "accountNewDevice": "an account plays from a new device",
714
- "accountTrustChanged": "an account's trust score changes",
715
- "mediaAdded": "media is added",
716
- "mediaUpgraded": "media is upgraded",
717
- "serverDown": "a server goes down",
718
- "serverUp": "a server comes back up",
719
- "pluginUpdateAvailable": "a plugin update is available",
720
- "serverUpdateAvailable": "a server update is available",
721
- "tracearrUpdateAvailable": "a Tracearr update is available"
288
+ "newDestination": "New destination",
289
+ "noAlertRecipientsTooltip": "",
290
+ "noDestinations": "No destinations yet. Add one to send notifications.",
291
+ "noMatches": "No matches",
292
+ "picker": {
293
+ "close": "close",
294
+ "empty": "Nothing matches that.",
295
+ "navigate": "move",
296
+ "searchPlaceholder": "Search or describe what should happen",
297
+ "select": "pick"
722
298
  },
723
- "operators": {
724
- "eq": "is",
725
- "neq": "is not",
726
- "gt": "is above",
727
- "gte": "is at least",
728
- "lt": "is below",
729
- "lte": "is at most",
730
- "in": "is one of",
731
- "not_in": "is not one of",
732
- "contains": "contains",
733
- "not_contains": "does not contain"
299
+ "recordAs": {
300
+ "label": "When this runs, record it as",
301
+ "notification": "An alert",
302
+ "notificationDescription": "Recorded in Activity; never a violation.",
303
+ "policy": "A violation",
304
+ "policyDescription": "Listed in Violations; can be acknowledged."
734
305
  },
735
- "fields": {
736
- "concurrent_streams": "the stream count",
737
- "active_session_distance_km": "the distance between streams",
738
- "travel_speed_kmh": "the travel speed",
739
- "unique_ips_in_window": "the number of IP addresses",
740
- "unique_devices_in_window": "the number of devices",
741
- "inactive_days": "the time since the last stream",
742
- "current_pause_minutes": "the current pause",
743
- "total_pause_minutes": "the total pause time",
744
- "source_resolution": "the source resolution",
745
- "output_resolution": "the output resolution",
746
- "is_transcoding": "the transcoding",
747
- "is_transcode_downgrade": "the downgrade",
748
- "source_bitrate_mbps": "the source bitrate",
749
- "user_id": "the user",
750
- "trust_score": "the trust score",
751
- "account_age_days": "the account age",
752
- "device_type": "the device type",
753
- "client_name": "the player",
754
- "platform": "the platform",
755
- "is_local_network": "the local network",
756
- "country": "the country",
757
- "ip_in_range": "the IP address",
758
- "server_id": "the server",
759
- "media_type": "the media type",
760
- "library_item_type": "the item type",
761
- "library_name": "the library",
762
- "resolution_after": "the resolution",
763
- "dynamic_range_after": "the dynamic range",
764
- "video_codec_after": "the video codec",
765
- "audio_channels_after": "the audio channels",
766
- "file_size_after": "the file size"
306
+ "rows": {
307
+ "expandHint": "open",
308
+ "moveHint": "reorder",
309
+ "remove": "Remove {{name}}",
310
+ "removeHint": "remove",
311
+ "skipped": "Skipped",
312
+ "toggle": "Include {{name}}",
313
+ "toggleHint": "skip"
767
314
  },
768
- "states": {
769
- "is_local_network": {
770
- "yes": "the user is on the local network",
771
- "no": "the user is not on the local network"
772
- },
773
- "is_transcode_downgrade": {
774
- "yes": "the stream is downgraded",
775
- "no": "the stream is not downgraded"
776
- },
777
- "is_transcoding": {
778
- "video": {
779
- "yes": "the stream is transcoding video",
780
- "no": "the stream is not transcoding video"
781
- },
782
- "audio": {
783
- "yes": "the stream is transcoding audio",
784
- "no": "the stream is not transcoding audio"
785
- },
786
- "video_or_audio": {
787
- "yes": "the stream is transcoding",
788
- "no": "the stream is not transcoding"
789
- },
790
- "neither": {
791
- "yes": "the stream is not transcoding",
792
- "no": "the stream is transcoding"
793
- }
315
+ "saving": "Saving…",
316
+ "scope": {
317
+ "account": "Specific account",
318
+ "accountLabel": "Account",
319
+ "accountPlaceholder": "Select account",
320
+ "enforceAcrossServers": "Enforce across servers",
321
+ "enforceAcrossServersDescription": "Acts on the person's sessions on any of their servers, not only the one that triggered it. Off by default.",
322
+ "global": "Global",
323
+ "label": "Scope",
324
+ "noServers": "No servers connected yet.",
325
+ "person": "Person (all their servers)",
326
+ "personHelper": "Matches this person on every server they have an account on.",
327
+ "personLabel": "Person",
328
+ "personPlaceholder": "Select person",
329
+ "server": "Specific server",
330
+ "serverLabel": "Server",
331
+ "serverPlaceholder": "Select server"
332
+ },
333
+ "searchPlaceholder": "Search…",
334
+ "selectPlaceholder": "Select…",
335
+ "selectedCount": "{{count}} selected",
336
+ "sentence": {
337
+ "label": "What this automation does",
338
+ "placeholderAction": "do something",
339
+ "placeholderTrigger": "something happens"
340
+ },
341
+ "severityLabel": "Severity",
342
+ "when": {
343
+ "add": "Add trigger",
344
+ "emptyAction": "Choose what starts it",
345
+ "emptyDescription": "A stream starting, a server going down, an account going quiet.",
346
+ "emptyTitle": "What should start this?",
347
+ "helper": "Any one of these starts it. At least one is required.",
348
+ "or": "or",
349
+ "title": "When…"
350
+ }
351
+ },
352
+ "catalog": {
353
+ "actions": {
354
+ "if": {
355
+ "description": "Run one set of steps when a condition holds and another when it does not.",
356
+ "label": "Branch on a condition",
357
+ "synonyms": "if, else, otherwise, branch, split, condition"
358
+ },
359
+ "kill_stream": {
360
+ "synonyms": "stop, terminate, cut, end playback"
361
+ },
362
+ "message_client": {
363
+ "synonyms": "warn, tell, notice, on screen"
364
+ },
365
+ "send": {
366
+ "synonyms": "notify, alert, discord, email, webhook, push"
367
+ },
368
+ "trust": {
369
+ "synonyms": "score, reputation, penalise, reward"
370
+ }
371
+ },
372
+ "groups": {
373
+ "accounts": "Accounts",
374
+ "control": "Control flow",
375
+ "library": "Library",
376
+ "notifications": "",
377
+ "notify": "Notify",
378
+ "policy": "Policy",
379
+ "servers": "Servers",
380
+ "sessions": "Sessions",
381
+ "updates": "Updates"
382
+ },
383
+ "suggested": "Suggested",
384
+ "triggers": {
385
+ "accountInactiveFor": {
386
+ "description": "An account has watched nothing for the set number of days.",
387
+ "label": "An account goes quiet",
388
+ "synonyms": "inactive, dormant, unused, stale, cleanup"
389
+ },
390
+ "accountNewDevice": {
391
+ "description": "An account streams from a device for the first time.",
392
+ "synonyms": "device, new, unknown, unrecognized, phone, login, sharing"
393
+ },
394
+ "accountTrustChanged": {
395
+ "description": "An account's trust score changes, whether an automation or an owner moved it.",
396
+ "synonyms": "trust, score, reputation, penalty, adjusted"
397
+ },
398
+ "mediaAdded": {
399
+ "description": "A library item shows up on a server for the first time.",
400
+ "synonyms": "new, added, library, movie, episode, import"
401
+ },
402
+ "mediaUpgraded": {
403
+ "description": "A library item that was already there changes quality.",
404
+ "synonyms": "upgrade, quality, replaced, remux, 4k, resolution"
405
+ },
406
+ "newsletterFailed": {
407
+ "description": "",
408
+ "synonyms": ""
409
+ },
410
+ "newsletterSent": {
411
+ "description": "",
412
+ "synonyms": ""
413
+ },
414
+ "pluginUpdateAvailable": {
415
+ "description": "The Tracearr plugin on a server has a newer release.",
416
+ "synonyms": "plugin, upgrade, version, release"
417
+ },
418
+ "serverDown": {
419
+ "description": "A media server stops answering.",
420
+ "synonyms": "unreachable, offline, outage, down"
421
+ },
422
+ "serverUp": {
423
+ "description": "A media server answers again.",
424
+ "synonyms": "online, recovered, restored, back"
425
+ },
426
+ "serverUpdateAvailable": {
427
+ "description": "A media server has a newer release.",
428
+ "synonyms": "upgrade, version, release, patch"
429
+ },
430
+ "sessionFirstSeen": {
431
+ "description": "",
432
+ "synonyms": ""
433
+ },
434
+ "sessionHeldFor": {
435
+ "description": "A stream has been paused longer than the set number of minutes.",
436
+ "label": "A stream sits paused",
437
+ "synonyms": "pause, idle, abandoned, stuck, afk"
438
+ },
439
+ "sessionPaused": {
440
+ "description": "The moment a stream is paused.",
441
+ "synonyms": "pause, hold, idle"
442
+ },
443
+ "sessionStarted": {
444
+ "description": "",
445
+ "synonyms": "play, watch, begin, start, viewing"
446
+ },
447
+ "sessionStopped": {
448
+ "description": "Playback ends, however it ended.",
449
+ "synonyms": "end, finish, quit, close"
450
+ },
451
+ "sessionTranscodeChanged": {
452
+ "description": "The server switches a stream between direct play and transcoding.",
453
+ "synonyms": "transcode, convert, direct play, cpu"
454
+ },
455
+ "tracearrUpdateAvailable": {
456
+ "description": "Tracearr itself has a newer release.",
457
+ "synonyms": "upgrade, version, release, self"
794
458
  }
459
+ }
460
+ },
461
+ "categories": {
462
+ "device_client": "Device & Client",
463
+ "media": "Media",
464
+ "network_location": "Network & Location",
465
+ "scope": "Scope",
466
+ "session_behavior": "Session Behavior",
467
+ "stream_quality": "Stream Quality",
468
+ "user_attributes": "User Attributes"
469
+ },
470
+ "configFields": {
471
+ "cooldown_minutes": {
472
+ "label": "Cooldown"
795
473
  },
474
+ "message": {
475
+ "label": "Message"
476
+ },
477
+ "target": {
478
+ "label": "Target"
479
+ }
480
+ },
481
+ "cooldownInvalid": "Enter a whole number of minutes, 0 or more, or leave it empty.",
482
+ "cooldownLabel": "At most once every",
483
+ "createAutomation": "Create Automation",
484
+ "customAutomation": "Custom automation",
485
+ "deleteAutomationConfirm": "Are you sure you want to delete this automation? This action cannot be undone.",
486
+ "deleteAutomation_one": "Delete {{count}} Automation",
487
+ "deleteAutomation_other": "Delete {{count}} Automations",
488
+ "deleteAutomationsConfirm": "Are you sure you want to delete? This action cannot be undone.",
489
+ "describe": {
796
490
  "actions": {
797
- "if": "if",
798
- "flagIt": "Flag it",
799
491
  "doNothing": "do nothing",
800
- "send": "send to {{destinations}}",
801
- "sendAnywhere": "send a notification",
492
+ "flagIt": "Flag it",
493
+ "if": "if",
802
494
  "kill_stream": "stop the stream",
803
495
  "message_client": "message the player",
804
- "trustUp": "raise trust by {{amount}}",
805
- "trustDown": "drop trust by {{amount}}",
496
+ "send": "send to {{destinations}}",
497
+ "sendAnywhere": "send a notification",
806
498
  "trustAdjust": "adjust trust by {{amount}}",
499
+ "trustDown": "drop trust by {{amount}}",
500
+ "trustReset": "reset trust",
807
501
  "trustSet": "set trust to {{value}}",
808
- "trustReset": "reset trust"
502
+ "trustUp": "raise trust by {{amount}}"
503
+ },
504
+ "allOf": "all of:",
505
+ "andAlso": "and also",
506
+ "anyOf": "any of:",
507
+ "appliesTo": "Applies to {{name}}",
508
+ "deviceTypesOnly": "{{types}} only",
509
+ "duration": {
510
+ "days_one": "{{count}} day",
511
+ "days_other": "{{count}} days",
512
+ "minutes_one": "{{count}} minute",
513
+ "minutes_other": "{{count}} minutes"
514
+ },
515
+ "fields": {
516
+ "account_age_days": "the account age",
517
+ "active_session_distance_km": "the distance between streams",
518
+ "audio_channels_after": "the audio channels",
519
+ "client_name": "the player",
520
+ "concurrent_streams": "the stream count",
521
+ "country": "the country",
522
+ "current_pause_minutes": "the current pause",
523
+ "device_type": "the device type",
524
+ "dynamic_range_after": "the dynamic range",
525
+ "file_size_after": "the file size",
526
+ "inactive_days": "the time since the last stream",
527
+ "ip_in_range": "the IP address",
528
+ "is_local_network": "the local network",
529
+ "is_transcode_downgrade": "the downgrade",
530
+ "is_transcoding": "the transcoding",
531
+ "library_item_type": "the item type",
532
+ "library_name": "the library",
533
+ "media_type": "the media type",
534
+ "output_resolution": "the output resolution",
535
+ "platform": "the platform",
536
+ "resolution_after": "the resolution",
537
+ "server_id": "the server",
538
+ "source_bitrate_mbps": "the source bitrate",
539
+ "source_resolution": "the source resolution",
540
+ "total_pause_minutes": "the total pause time",
541
+ "travel_speed_kmh": "the travel speed",
542
+ "trust_score": "the trust score",
543
+ "unique_devices_in_window": "the number of devices",
544
+ "unique_ips_in_window": "the number of IP addresses",
545
+ "user_id": "the user",
546
+ "video_codec_after": "the video codec"
547
+ },
548
+ "includesSameDevice": "includes same device",
549
+ "joinAll": "and",
550
+ "joinAny": "or",
551
+ "more_one": "+{{count}} more",
552
+ "more_other": "+{{count}} more",
553
+ "noValues": "(none)",
554
+ "nothing": "nothing yet",
555
+ "onlyWhen": "only when",
556
+ "operators": {
557
+ "contains": "contains",
558
+ "eq": "is",
559
+ "gt": "is above",
560
+ "gte": "is at least",
561
+ "in": "is one of",
562
+ "lt": "is below",
563
+ "lte": "is at most",
564
+ "neq": "is not",
565
+ "not_contains": "does not contain",
566
+ "not_in": "is not one of"
809
567
  },
568
+ "or": "or {{text}}",
569
+ "otherwise": "Otherwise",
570
+ "sameDeviceInput": "same device: {{input}}",
810
571
  "scope": {
811
- "server": "one server",
812
572
  "account": "one account",
813
- "person": "one person"
573
+ "person": "one person",
574
+ "server": "one server"
814
575
  },
815
- "sameDeviceInput": "same device: {{input}}",
816
- "uniqueIpsInput": "unique IPs: {{input}}",
817
- "unbound": {
818
- "server": "a chosen server",
819
- "account": "a chosen account",
820
- "person": "a chosen person",
821
- "destinations": "a chosen destination",
822
- "field_value": "a chosen value",
823
- "select": "a chosen option",
824
- "number": "a chosen number",
825
- "duration": "a chosen length of time",
826
- "text": "a chosen message",
827
- "boolean": "a chosen setting",
828
- "listed": "those chosen"
829
- }
830
- },
831
- "description": "Automations watch your servers and act when their conditions match",
832
- "detail": {
833
- "notFound": "Automation not found",
834
- "title": "Automation",
835
- "unsaved": "Unsaved changes",
836
- "runsLine_one": "1 run · last run {{when}}",
837
- "runsLine_other": "{{count}} runs · last run {{when}}",
838
- "noRuns": "No runs yet"
839
- },
576
+ "states": {
577
+ "is_local_network": {
578
+ "no": "the user is not on the local network",
579
+ "yes": "the user is on the local network"
580
+ },
581
+ "is_transcode_downgrade": {
582
+ "no": "the stream is not downgraded",
583
+ "yes": "the stream is downgraded"
584
+ },
585
+ "is_transcoding": {
586
+ "audio": {
587
+ "no": "the stream is not transcoding audio",
588
+ "yes": "the stream is transcoding audio"
589
+ },
590
+ "neither": {
591
+ "no": "the stream is transcoding",
592
+ "yes": "the stream is not transcoding"
593
+ },
594
+ "video": {
595
+ "no": "the stream is not transcoding video",
596
+ "yes": "the stream is transcoding video"
597
+ },
598
+ "video_or_audio": {
599
+ "no": "the stream is not transcoding",
600
+ "yes": "the stream is transcoding"
601
+ }
602
+ }
603
+ },
604
+ "then": "then {{text}}",
605
+ "triggers": {
606
+ "accountInactiveFor": "an account has been inactive for {{duration}}",
607
+ "accountNewDevice": "an account plays from a new device",
608
+ "accountTrustChanged": "an account's trust score changes",
609
+ "mediaAdded": "media is added",
610
+ "mediaUpgraded": "media is upgraded",
611
+ "newsletterFailed": "",
612
+ "newsletterSent": "",
613
+ "pluginUpdateAvailable": "a plugin update is available",
614
+ "serverDown": "a server goes down",
615
+ "serverUp": "a server comes back up",
616
+ "serverUpdateAvailable": "a server update is available",
617
+ "sessionFirstSeen": "",
618
+ "sessionHeldFor": "a stream has been paused for {{duration}}",
619
+ "sessionHeldForTotal": "a stream has been paused for {{duration}} in total",
620
+ "sessionPaused": "a stream is paused",
621
+ "sessionStarted": "a stream starts",
622
+ "sessionStopped": "a stream stops",
623
+ "sessionTranscodeChanged": "transcoding starts or stops",
624
+ "tracearrUpdateAvailable": "a Tracearr update is available"
625
+ },
626
+ "unbound": {
627
+ "account": "a chosen account",
628
+ "boolean": "a chosen setting",
629
+ "destinations": "a chosen destination",
630
+ "duration": "a chosen length of time",
631
+ "field_value": "a chosen value",
632
+ "listed": "those chosen",
633
+ "number": "a chosen number",
634
+ "person": "a chosen person",
635
+ "select": "a chosen option",
636
+ "server": "a chosen server",
637
+ "text": "a chosen message"
638
+ },
639
+ "uniqueIps": "unique IPs",
640
+ "uniqueIpsInput": "unique IPs: {{input}}",
641
+ "when": "When {{text}}"
642
+ },
643
+ "description": "Automations watch your servers and act when their conditions match",
644
+ "descriptionLabel": "Description",
645
+ "descriptionPlaceholder": "What this is for",
646
+ "detail": {
647
+ "noRuns": "No runs yet",
648
+ "notFound": "Automation not found",
649
+ "runsLine_one": "1 run · last run {{when}}",
650
+ "runsLine_other": "{{count}} runs · last run {{when}}",
651
+ "title": "Automation",
652
+ "unsaved": "Unsaved changes"
653
+ },
840
654
  "disable": "Disable",
841
655
  "editAutomation": "Edit Automation",
842
656
  "effects": {
843
- "title": "What this will do",
657
+ "allServers": "Runs on every server unless one is chosen.",
658
+ "everyServer": "Runs on every server.",
844
659
  "kill": "Can stop a stream that is playing.",
845
- "trust": "Changes trust scores.",
846
660
  "message": "Puts a message on a player.",
847
- "violation": "Records a violation against the matched person.",
661
+ "oneServer": "Runs on {{server}} only.",
848
662
  "tellsOnly": "Only notifies. Never stops a stream or changes an account.",
849
- "allServers": "Runs on every server unless one is chosen.",
850
- "everyServer": "Runs on every server.",
851
- "oneServer": "Runs on {{server}} only."
663
+ "title": "What this will do",
664
+ "trust": "Changes trust scores.",
665
+ "violation": "Records a violation against the matched person."
852
666
  },
853
- "emptyTitle": "No automations yet",
854
667
  "emptyDescription": "Ready-made automations. Pick one and fill in the blanks.",
855
668
  "emptySeeAll": "See all {{count}}",
856
669
  "emptySeeAllLoading": "See all",
670
+ "emptyTitle": "No automations yet",
857
671
  "enable": "Enable",
858
672
  "evaluations": {
859
673
  "disclosure": "Matches that did not start a run ({{total}})",
@@ -865,349 +679,345 @@
865
679
  }
866
680
  },
867
681
  "export": {
868
- "title": "Share this automation",
869
- "description": "A code another Tracearr can paste in.",
682
+ "authorHelper": "Shown on the gallery page and carried in the code. Optional.",
683
+ "authorInCode": "The code includes the author name.",
684
+ "authorLabel": "Author",
685
+ "authorPlaceholder": "Name",
870
686
  "carries": "The code carries the steps only. Destinations, servers and accounts are not included; the receiving side fills in its own.",
871
687
  "copyCode": "Copy the share code",
872
688
  "copyJson": "Copy the JSON",
873
- "authorLabel": "Author",
874
- "authorPlaceholder": "Name",
875
- "authorHelper": "Shown on the gallery page and carried in the code. Optional.",
876
- "save": "Save as ready-made",
877
- "saved": "{{name}} saved as a ready-made automation.",
878
- "saveFailed": "Could not save it.",
689
+ "description": "A code another Tracearr can paste in.",
879
690
  "failed": "Couldn't make a code for this one.",
880
- "saveHelper": "Adds it to this server's list of ready-made automations.",
881
- "authorInCode": "The code includes the author name.",
882
- "groupLabel": "Section",
883
- "groupHelper": "Which part of the gallery it is listed under.",
884
691
  "gallery": {
885
- "trigger": "Put this in the community gallery",
886
- "body": "The gallery at docs.tracearr.com/templates lists shared automations. Adding one is a pull request to Tracearr/automation-templates with the JSON below. Tracearr never reads the gallery."
692
+ "body": "The gallery at docs.tracearr.com/templates lists shared automations. Adding one is a pull request to Tracearr/automation-templates with the JSON below. Tracearr never reads the gallery.",
693
+ "trigger": "Put this in the community gallery"
887
694
  },
888
- "openRepository": "Open the repository"
695
+ "groupHelper": "Which part of the gallery it is listed under.",
696
+ "groupLabel": "Section",
697
+ "openRepository": "Open the repository",
698
+ "save": "Save as ready-made",
699
+ "saveFailed": "Could not save it.",
700
+ "saveHelper": "Adds it to this server's list of ready-made automations.",
701
+ "saved": "{{name}} saved as a ready-made automation.",
702
+ "title": "Share this automation"
889
703
  },
890
704
  "fields": {
891
- "concurrent_streams": {
892
- "label": "Concurrent Streams",
893
- "description": "Number of active streams from the same user"
705
+ "account_age_days": {
706
+ "description": "Days since account creation",
707
+ "label": "Account Age"
894
708
  },
895
709
  "active_session_distance_km": {
896
- "label": "Distance Between Sessions",
897
- "description": "Distance between simultaneous sessions"
710
+ "description": "Distance between simultaneous sessions",
711
+ "label": "Distance Between Sessions"
898
712
  },
899
- "travel_speed_kmh": {
900
- "label": "Travel Speed",
901
- "description": "Calculated travel speed between locations"
713
+ "audio_channels_after": {
714
+ "description": "Audio channel count the item ends up with",
715
+ "label": "Audio Channels"
902
716
  },
903
- "unique_ips_in_window": {
904
- "label": "Unique IPs in Window",
905
- "description": "Number of unique IP addresses in the time window"
717
+ "client_name": {
718
+ "description": "Media player application",
719
+ "label": "Client/Player",
720
+ "placeholder": "e.g., Plex for iOS"
906
721
  },
907
- "unique_devices_in_window": {
908
- "label": "Unique Devices in Window",
909
- "description": "Number of unique devices in the time window"
722
+ "concurrent_streams": {
723
+ "description": "Number of active streams from the same user",
724
+ "label": "Concurrent Streams"
910
725
  },
911
- "inactive_days": {
912
- "label": "Days Inactive",
913
- "description": "Days since last activity"
726
+ "country": {
727
+ "description": "Geographic country",
728
+ "label": "Country",
729
+ "placeholder": "Select countries…"
914
730
  },
915
731
  "current_pause_minutes": {
916
- "label": "Current Pause Duration",
917
- "description": "How long the session has been continuously paused"
918
- },
919
- "total_pause_minutes": {
920
- "label": "Total Pause Duration",
921
- "description": "Total accumulated pause time across all pause/resume cycles"
732
+ "description": "How long the session has been continuously paused",
733
+ "label": "Current Pause Duration"
922
734
  },
923
- "source_resolution": {
924
- "label": "Source Resolution",
925
- "description": "Original media resolution"
735
+ "device_type": {
736
+ "description": "Type of device used",
737
+ "label": "Device Type"
926
738
  },
927
- "output_resolution": {
928
- "label": "Output Resolution",
929
- "description": "Transcoded or delivered resolution"
739
+ "dynamic_range_after": {
740
+ "description": "HDR format the item ends up with",
741
+ "label": "Dynamic Range"
930
742
  },
931
- "is_transcoding": {
932
- "label": "Is Transcoding",
933
- "description": "Whether video or audio streams are being transcoded"
743
+ "file_size_after": {
744
+ "description": "Size the item ends up at, across every copy",
745
+ "label": "File Size"
934
746
  },
935
- "is_transcode_downgrade": {
936
- "label": "Transcode Downgrade",
937
- "description": "Output resolution is lower than source"
747
+ "inactive_days": {
748
+ "description": "Days since last activity",
749
+ "label": "Days Inactive"
938
750
  },
939
- "source_bitrate_mbps": {
940
- "label": "Source Bitrate",
941
- "description": "Original media bitrate"
751
+ "ip_in_range": {
752
+ "description": "IP address in a CIDR range, IPv4 or IPv6",
753
+ "label": "IP Range",
754
+ "placeholder": "e.g., 192.168.1.0/24 or 2001:db8:abcd:7800::/64"
942
755
  },
943
- "user_id": {
944
- "label": "User",
945
- "description": "Specific users by account",
946
- "placeholder": "Select users…"
756
+ "is_local_network": {
757
+ "description": "Streaming from the local network",
758
+ "label": "Local Network"
947
759
  },
948
- "trust_score": {
949
- "label": "Trust Score",
950
- "description": "The user's trust score, from 0 to 100"
760
+ "is_transcode_downgrade": {
761
+ "description": "Output resolution is lower than source",
762
+ "label": "Transcode Downgrade"
951
763
  },
952
- "account_age_days": {
953
- "label": "Account Age",
954
- "description": "Days since account creation"
764
+ "is_transcoding": {
765
+ "description": "Whether video or audio streams are being transcoded",
766
+ "label": "Is Transcoding"
955
767
  },
956
- "device_type": {
957
- "label": "Device Type",
958
- "description": "Type of device used"
768
+ "library_item_type": {
769
+ "description": "What kind of library item it is",
770
+ "label": "Item Type"
959
771
  },
960
- "client_name": {
961
- "label": "Client/Player",
962
- "description": "Media player application",
963
- "placeholder": "e.g., Plex for iOS"
772
+ "library_name": {
773
+ "description": "Name of the library it landed in",
774
+ "label": "Library",
775
+ "placeholder": "Movies"
964
776
  },
965
- "platform": {
966
- "label": "Platform/OS",
967
- "description": "Operating system"
777
+ "media_type": {
778
+ "description": "Type of content",
779
+ "label": "Media Type"
968
780
  },
969
- "is_local_network": {
970
- "label": "Local Network",
971
- "description": "Streaming from the local network"
781
+ "output_resolution": {
782
+ "description": "Transcoded or delivered resolution",
783
+ "label": "Output Resolution"
972
784
  },
973
- "country": {
974
- "label": "Country",
975
- "description": "Geographic country",
976
- "placeholder": "Select countries…"
785
+ "platform": {
786
+ "description": "Operating system",
787
+ "label": "Platform/OS"
977
788
  },
978
- "ip_in_range": {
979
- "label": "IP Range",
980
- "description": "IP address in a CIDR range, IPv4 or IPv6",
981
- "placeholder": "e.g., 192.168.1.0/24 or 2001:db8:abcd:7800::/64"
789
+ "resolution_after": {
790
+ "description": "Resolution the item ends up at",
791
+ "label": "Resolution"
982
792
  },
983
793
  "server_id": {
984
- "label": "Server",
985
794
  "description": "Specific media server",
795
+ "label": "Server",
986
796
  "placeholder": "Select servers…"
987
797
  },
988
- "media_type": {
989
- "label": "Media Type",
990
- "description": "Type of content"
798
+ "source_bitrate_mbps": {
799
+ "description": "Original media bitrate",
800
+ "label": "Source Bitrate"
991
801
  },
992
- "library_item_type": {
993
- "label": "Item Type",
994
- "description": "What kind of library item it is"
802
+ "source_resolution": {
803
+ "description": "Original media resolution",
804
+ "label": "Source Resolution"
995
805
  },
996
- "library_name": {
997
- "label": "Library",
998
- "description": "Name of the library it landed in",
999
- "placeholder": "Movies"
806
+ "total_pause_minutes": {
807
+ "description": "Total accumulated pause time across all pause/resume cycles",
808
+ "label": "Total Pause Duration"
1000
809
  },
1001
- "resolution_after": {
1002
- "label": "Resolution",
1003
- "description": "Resolution the item ends up at"
810
+ "travel_speed_kmh": {
811
+ "description": "Calculated travel speed between locations",
812
+ "label": "Travel Speed"
1004
813
  },
1005
- "dynamic_range_after": {
1006
- "label": "Dynamic Range",
1007
- "description": "HDR format the item ends up with"
814
+ "trust_score": {
815
+ "description": "The user's trust score, from 0 to 100",
816
+ "label": "Trust Score"
1008
817
  },
1009
- "video_codec_after": {
1010
- "label": "Video Codec",
1011
- "description": "Video codec the item ends up with"
818
+ "unique_devices_in_window": {
819
+ "description": "Number of unique devices in the time window",
820
+ "label": "Unique Devices in Window"
1012
821
  },
1013
- "audio_channels_after": {
1014
- "label": "Audio Channels",
1015
- "description": "Audio channel count the item ends up with"
822
+ "unique_ips_in_window": {
823
+ "description": "Number of unique IP addresses in the time window",
824
+ "label": "Unique IPs in Window"
1016
825
  },
1017
- "file_size_after": {
1018
- "label": "File Size",
1019
- "description": "Size the item ends up at, across every copy"
826
+ "user_id": {
827
+ "description": "Specific users by account",
828
+ "label": "User",
829
+ "placeholder": "Select users…"
830
+ },
831
+ "video_codec_after": {
832
+ "description": "Video codec the item ends up with",
833
+ "label": "Video Codec"
1020
834
  }
1021
835
  },
836
+ "filters": {
837
+ "allSources": "Anywhere",
838
+ "allTriggers": "All triggers",
839
+ "source": "Where it came from",
840
+ "sources": {
841
+ "builtin": "Built-in",
842
+ "import": "Imported",
843
+ "local": "Saved here",
844
+ "own": "Built in the builder"
845
+ },
846
+ "trigger": "What starts it"
847
+ },
1022
848
  "gallery": {
1023
- "title": "New automation",
849
+ "builtin": "Built-in",
1024
850
  "description": "Ready-made automations. Pick one and fill in the blanks.",
1025
- "searchPlaceholder": "Search",
1026
- "noMatches": "Nothing matches “{{query}}”.",
1027
- "noMatchesHint": "Try a word from the outcome: discord, offline, paused.",
851
+ "failed": "Couldn't load the ready-made automations.",
1028
852
  "group": {
853
+ "housekeeping": "Housekeeping",
1029
854
  "notifications": "Notifications",
1030
- "server_health": "Server health",
855
+ "other": "Other ways to start",
1031
856
  "policies": "Limits and rules",
1032
- "housekeeping": "Housekeeping",
1033
- "other": "Other ways to start"
857
+ "server_health": "Server health"
858
+ },
859
+ "hint": {
860
+ "close": "close",
861
+ "move": "move",
862
+ "use": "use"
1034
863
  },
1035
- "builtin": "Built-in",
1036
864
  "kind": {
1037
- "policy": "A violation",
1038
- "notification": "An alert"
865
+ "notification": "An alert",
866
+ "policy": "A violation"
1039
867
  },
868
+ "loading": "Loading…",
869
+ "missing": "That ready-made automation is not on this server.",
870
+ "noMatches": "Nothing matches “{{query}}”.",
871
+ "noMatchesHint": "Try a word from the outcome: discord, offline, paused.",
1040
872
  "paste": {
1041
- "title": "Paste a share code",
1042
- "description": "Paste a code and review what it does before adding it."
873
+ "description": "Paste a code and review what it does before adding it.",
874
+ "title": "Paste a share code"
1043
875
  },
1044
- "scratch": {
1045
- "title": "Start from scratch",
1046
- "description": "Build it step by step."
1047
- },
1048
- "failed": "Couldn't load the ready-made automations.",
1049
876
  "retry": "Try again",
1050
- "missing": "That ready-made automation is not on this server.",
1051
- "hint": {
1052
- "move": "move",
1053
- "use": "use",
1054
- "close": "close"
877
+ "scratch": {
878
+ "description": "Build it step by step.",
879
+ "title": "Start from scratch"
1055
880
  },
1056
- "loading": "Loading…"
881
+ "searchPlaceholder": "Search",
882
+ "title": "New automation"
1057
883
  },
1058
884
  "import": {
1059
- "title": "Paste a share code",
1060
- "description": "Paste the code. Everything is in the code; Tracearr fetches nothing.",
1061
- "reviewDescription": "What the code does, and what to fill in.",
1062
- "placeholder": "tracearr1.…",
1063
- "formatHint": "A code starts with tracearr1.",
885
+ "adding": "Adding it…",
886
+ "builtinMatch": "This is {{name}}, one of the automations Tracearr ships.",
1064
887
  "check": "Check it",
1065
888
  "checking": "Reading it…",
1066
- "valid": "Tracearr can read this code.",
1067
- "madeBy": "Author: {{author}}, as written in the code",
1068
889
  "codeShort": "Code {{fingerprint}}",
1069
- "paused": {
1070
- "label": "Start paused",
1071
- "helper": "Turn it on from the list after review."
1072
- },
1073
- "submit": "Add it",
1074
- "adding": "Adding it…",
1075
- "existing": "Already saved as {{name}}.",
1076
- "existingUse": "Use it",
1077
890
  "collision": {
1078
- "title": "A different automation named {{name}} already exists.",
1079
891
  "add": "Keep both",
1080
- "replace": "Replace mine"
892
+ "replace": "Replace mine",
893
+ "title": "A different automation named {{name}} already exists."
1081
894
  },
1082
- "raw": "Show the JSON",
895
+ "description": "Paste the code. Everything is in the code; Tracearr fetches nothing.",
1083
896
  "errors": {
1084
897
  "notACode": "That doesn't look like a Tracearr share code.",
1085
898
  "notACodeHint": "A code starts with tracearr1. The JSON works too.",
899
+ "rejected": "Tracearr couldn't read this one.",
900
+ "rejectedHint": "It may come from a different tool or have been edited by hand.",
1086
901
  "tooBig": "That's too big to be a Tracearr automation.",
1087
902
  "tooBigHint": "Codes are a few thousand characters at most.",
1088
- "truncated": "This code looks cut off.",
1089
- "truncatedHint": "Copy the whole code and paste it again; some chat apps split long codes across lines.",
1090
- "tooNew": "This needs Tracearr {{required}} or newer.",
1091
- "tooNewHint": "This server runs {{current}}. Update Tracearr, then paste again.",
1092
903
  "tooMany": "That's a lot of codes in one minute.",
1093
904
  "tooManyHint": "Wait a moment, then check it again.",
1094
- "rejected": "Tracearr couldn't read this one.",
1095
- "rejectedHint": "It may come from a different tool or have been edited by hand."
905
+ "tooNew": "This needs Tracearr {{required}} or newer.",
906
+ "tooNewHint": "This server runs {{current}}. Update Tracearr, then paste again.",
907
+ "truncated": "This code looks cut off.",
908
+ "truncatedHint": "Copy the whole code and paste it again; some chat apps split long codes across lines."
1096
909
  },
910
+ "existing": "Already saved as {{name}}.",
911
+ "existingUse": "Use it",
912
+ "formatHint": "A code starts with tracearr1.",
913
+ "madeBy": "Author: {{author}}, as written in the code",
914
+ "paused": {
915
+ "helper": "Turn it on from the list after review.",
916
+ "label": "Start paused"
917
+ },
918
+ "placeholder": "tracearr1.…",
919
+ "raw": "Show the JSON",
920
+ "reviewDescription": "What the code does, and what to fill in.",
1097
921
  "source": "Shared automations are listed at docs.tracearr.com/templates.",
1098
- "validCaveat": "Nothing in a code says who wrote it or whether it is safe. The steps are below.",
1099
- "builtinMatch": "This is {{name}}, one of the automations Tracearr ships."
922
+ "submit": "Add it",
923
+ "title": "Paste a share code",
924
+ "valid": "Tracearr can read this code.",
925
+ "validCaveat": "Nothing in a code says who wrote it or whether it is safe. The steps are below."
1100
926
  },
1101
927
  "kind": {
1102
- "policy": "Violation",
1103
- "notification": "Alert"
928
+ "notification": "Alert",
929
+ "policy": "Violation"
1104
930
  },
1105
931
  "kindColumn": "Kind",
1106
932
  "name": "Automation Name",
1107
- "newAutomation": "New automation",
1108
- "namePlaceholder": "A name for this automation",
1109
933
  "nameInvalid": "Give it a name.",
1110
- "descriptionLabel": "Description",
1111
- "descriptionPlaceholder": "What this is for",
1112
- "thisAutomation": "This automation",
1113
- "cooldownLabel": "At most once every",
1114
- "cooldownInvalid": "Enter a whole number of minutes, 0 or more, or leave it empty.",
1115
- "retentionLabel": "Keep runs for",
1116
- "retentionPlaceholder": "{{days}}",
1117
- "retentionInvalid": "Enter a whole number of days, at least 1, or leave it empty.",
934
+ "namePlaceholder": "A name for this automation",
935
+ "newAutomation": "New automation",
1118
936
  "noAutomationsFound": "No automations found",
937
+ "openGallery": "Open the gallery",
1119
938
  "operators": {
939
+ "contains": "contains",
1120
940
  "eq": "equals",
1121
- "neq": "not equals",
1122
941
  "gt": "greater than",
1123
942
  "gte": "at least",
943
+ "in": "is one of",
1124
944
  "lt": "less than",
1125
945
  "lte": "at most",
1126
- "in": "is one of",
1127
- "not_in": "is not one of",
1128
- "contains": "contains",
1129
- "not_contains": "does not contain"
946
+ "neq": "not equals",
947
+ "not_contains": "does not contain",
948
+ "not_in": "is not one of"
1130
949
  },
1131
950
  "options": {
1132
- "4K": "4K (2160p)",
1133
951
  "1080p": "1080p",
1134
- "720p": "720p",
952
+ "1440p": "1440p",
1135
953
  "480p": "480p",
954
+ "4K": "4K (2160p)",
955
+ "720p": "720p",
956
+ "8K": "8K",
1136
957
  "SD": "SD",
1137
- "unknown": "Unknown",
1138
- "mobile": "Mobile",
1139
- "tablet": "Tablet",
1140
- "tv": "TV",
1141
- "desktop": "Desktop",
1142
- "browser": "Browser",
1143
- "ios": "iOS",
1144
958
  "android": "Android",
1145
- "windows": "Windows",
1146
- "macos": "macOS",
1147
- "linux": "Linux",
1148
- "tvos": "tvOS",
1149
959
  "androidtv": "Android TV",
1150
- "roku": "Roku",
1151
- "webos": "webOS",
1152
- "tizen": "Tizen",
1153
- "movie": "Movie",
1154
- "episode": "TV Episode",
1155
- "track": "Music",
1156
- "photo": "Photo",
1157
- "live": "Live TV",
1158
- "trailer": "Trailer",
1159
- "video": "Video",
1160
960
  "audio": "Audio",
1161
- "video_or_audio": "Video or Audio",
1162
- "neither": "Neither (Direct Play)",
1163
- "8K": "8K",
1164
- "1440p": "1440p",
1165
- "sdr": "SDR",
961
+ "browser": "Browser",
962
+ "desktop": "Desktop",
963
+ "dolby vision": "Dolby Vision",
964
+ "episode": "TV Episode",
1166
965
  "hdr": "HDR",
1167
966
  "hdr10": "HDR10",
1168
967
  "hdr10+": "HDR10+",
1169
968
  "hlg": "HLG",
1170
- "dolby vision": "Dolby Vision",
969
+ "ios": "iOS",
1171
970
  "libraryItemType": {
971
+ "album": "Album",
972
+ "artist": "Artist",
973
+ "episode": "Episode",
1172
974
  "movie": "Movie",
1173
- "show": "Show",
975
+ "photo": "Photo",
1174
976
  "season": "Season",
1175
- "episode": "Episode",
1176
- "artist": "Artist",
1177
- "album": "Album",
1178
- "track": "Track",
1179
- "photo": "Photo"
1180
- }
977
+ "show": "Show",
978
+ "track": "Track"
979
+ },
980
+ "linux": "Linux",
981
+ "live": "Live TV",
982
+ "macos": "macOS",
983
+ "mobile": "Mobile",
984
+ "movie": "Movie",
985
+ "neither": "Neither (Direct Play)",
986
+ "photo": "Photo",
987
+ "roku": "Roku",
988
+ "sdr": "SDR",
989
+ "tablet": "Tablet",
990
+ "tizen": "Tizen",
991
+ "track": "Music",
992
+ "trailer": "Trailer",
993
+ "tv": "TV",
994
+ "tvos": "tvOS",
995
+ "unknown": "Unknown",
996
+ "video": "Video",
997
+ "video_or_audio": "Video or Audio",
998
+ "webos": "webOS",
999
+ "windows": "Windows"
1181
1000
  },
1182
1001
  "provenance": {
1183
1002
  "builtin": "Built-in · {{name}} {{version}}",
1003
+ "customized": "Customized from {{name}}",
1004
+ "customizedFromRemoved": "Customized from a ready-made automation that has since been removed",
1184
1005
  "imported": "Imported from a share code on {{date}} · {{name}} {{version}}",
1185
1006
  "importedBy": "Imported from a share code by {{author}} on {{date}} · {{name}} {{version}}",
1186
- "saved": "Saved here from {{name}} on {{date}} · {{version}}",
1187
- "customized": "Customized from {{name}}",
1188
- "customizedFromRemoved": "Customized from a ready-made automation that has since been removed"
1007
+ "saved": "Saved here from {{name}} on {{date}} · {{version}}"
1189
1008
  },
1190
1009
  "recordsOnly": "Records runs only",
1010
+ "retentionInvalid": "Enter a whole number of days, at least 1, or leave it empty.",
1011
+ "retentionLabel": "Keep runs for",
1012
+ "retentionPlaceholder": "{{days}}",
1191
1013
  "scope": {
1192
- "global": "Global",
1193
- "person": "Person",
1194
1014
  "account": "Account",
1195
- "crossServer": "Cross-server"
1015
+ "crossServer": "Cross-server",
1016
+ "global": "Global",
1017
+ "person": "Person"
1196
1018
  },
1197
1019
  "searchPlaceholder": "Search automations…",
1198
1020
  "sessionTargets": {
1199
- "triggering": {
1200
- "label": "Triggering session",
1201
- "tooltip": "Only the session that triggered this automation"
1202
- },
1203
- "oldest": {
1204
- "label": "Oldest session",
1205
- "tooltip": "The user's longest-running active session"
1206
- },
1207
- "newest": {
1208
- "label": "Newest session",
1209
- "tooltip": "The user's most recently started session"
1210
- },
1211
1021
  "all_except_one": {
1212
1022
  "label": "All except one (keep oldest)",
1213
1023
  "tooltip": "All sessions except the oldest, bringing the user down to one stream"
@@ -1215,854 +1025,1124 @@
1215
1025
  "all_user": {
1216
1026
  "label": "All user sessions",
1217
1027
  "tooltip": "Every active session for this user"
1218
- }
1219
- },
1220
- "configFields": {
1221
- "cooldown_minutes": {
1222
- "label": "Cooldown"
1223
1028
  },
1224
- "target": {
1225
- "label": "Target"
1226
- },
1227
- "message": {
1228
- "label": "Message"
1229
- }
1230
- },
1231
- "trustModes": {
1232
- "adjust": {
1233
- "label": "Adjust by amount"
1029
+ "newest": {
1030
+ "label": "Newest session",
1031
+ "tooltip": "The user's most recently started session"
1234
1032
  },
1235
- "set": {
1236
- "label": "Set to value"
1033
+ "oldest": {
1034
+ "label": "Oldest session",
1035
+ "tooltip": "The user's longest-running active session"
1237
1036
  },
1238
- "reset": {
1239
- "label": "Reset to default (100)"
1037
+ "triggering": {
1038
+ "label": "Triggering session",
1039
+ "tooltip": "Only the session that triggered this automation"
1240
1040
  }
1241
1041
  },
1242
1042
  "severity": {
1043
+ "high": "High",
1243
1044
  "low": "Low",
1244
- "warning": "Warning",
1245
- "high": "High"
1045
+ "warning": "Warning"
1246
1046
  },
1247
1047
  "template": {
1248
- "version": "v{{version}}",
1249
- "updateAvailable": "An update is available",
1250
- "updatedTitle": "The ready-made automation is now on v{{version}}",
1251
- "updatedBody": "Review the answers below, then update.",
1252
- "before": "Now",
1253
1048
  "after": "After the update",
1254
- "review": "Review and update",
1255
- "save": "Save changes",
1049
+ "before": "Now",
1256
1050
  "customize": "Customize",
1257
- "customizeTitle": "Open this in the builder?",
1258
1051
  "customizeConfirm": "Opening it in the builder makes this automation independent: every step is editable, and it no longer receives updates from the ready-made one. This cannot be undone.",
1259
1052
  "customizeConfirmAction": "Customize it",
1260
- "customizeFirst": "This automation follows a ready-made one. Open it in the builder first.",
1261
1053
  "customizeFailed": "Could not open it in the builder.",
1262
- "upgradeFailed": "Couldn't update that. Try again.",
1054
+ "customizeFirst": "This automation follows a ready-made one. Open it in the builder first.",
1055
+ "customizeTitle": "Open this in the builder?",
1056
+ "doorsHelper": "The steps come from the ready-made automation and are fixed. Open in the builder makes every step editable and ends the link.",
1263
1057
  "gone": "The ready-made automation this was built from is no longer on this server.",
1264
- "doorsHelper": "The steps come from the ready-made automation and are fixed. Open in the builder makes every step editable and ends the link."
1058
+ "review": "Review and update",
1059
+ "save": "Save changes",
1060
+ "updateAvailable": "An update is available",
1061
+ "updatedBody": "Review the answers below, then update.",
1062
+ "updatedTitle": "The ready-made automation is now on v{{version}}",
1063
+ "upgradeFailed": "Couldn't update that. Try again.",
1064
+ "version": "v{{version}}"
1265
1065
  },
1266
1066
  "templates": {
1267
1067
  "account-inactivity": {
1268
- "name": "Inactive account",
1269
1068
  "description": "Raise a violation when an account goes unused for the days you allow.",
1270
- "keywords": "idle dormant unused stale cleanup inactive account"
1069
+ "keywords": "idle dormant unused stale cleanup inactive account",
1070
+ "name": "Inactive account"
1271
1071
  },
1272
1072
  "concurrent-streams": {
1273
- "name": "Too many streams at once",
1274
1073
  "description": "Raise a violation when an account plays more streams at once than you allow.",
1275
- "keywords": "limit cap concurrent simultaneous sharing too many streams"
1074
+ "keywords": "limit cap concurrent simultaneous sharing too many streams",
1075
+ "name": "Too many streams at once"
1276
1076
  },
1277
1077
  "device-velocity": {
1278
- "name": "Many IPs in a window",
1279
1078
  "description": "Raise a violation when an account streams from more IP addresses in a window than you allow.",
1280
- "keywords": "ip addresses vpn sharing devices window"
1079
+ "keywords": "ip addresses vpn sharing devices window",
1080
+ "name": "Many IPs in a window"
1281
1081
  },
1282
1082
  "geo-restriction": {
1283
- "name": "Blocked countries",
1284
1083
  "description": "Raise a violation when a stream comes from a country you block.",
1285
- "keywords": "country geo vpn abroad region block travel"
1084
+ "keywords": "country geo vpn abroad region block travel",
1085
+ "name": "Blocked countries"
1286
1086
  },
1287
1087
  "impossible-travel": {
1288
- "name": "Impossible travel",
1289
1088
  "description": "Raise a violation when two sessions sit further apart than anyone could travel between them.",
1290
- "keywords": "vpn travel speed distance location sharing"
1089
+ "keywords": "vpn travel speed distance location sharing",
1090
+ "name": "Impossible travel"
1291
1091
  },
1292
1092
  "kill-paused-streams": {
1293
- "name": "Stop paused streams",
1294
1093
  "description": "Stop a stream that has sat paused past the minutes you allow.",
1295
- "keywords": "pause idle afk stop kill terminate reclaim"
1094
+ "keywords": "pause idle afk stop kill terminate reclaim",
1095
+ "name": "Stop paused streams"
1296
1096
  },
1297
1097
  "media-added": {
1298
- "name": "New media added",
1299
1098
  "description": "Tell a destination when a library item shows up for the first time.",
1300
- "keywords": "new library movie episode added import notify discord email webhook"
1099
+ "keywords": "new library movie episode added import notify discord email webhook",
1100
+ "name": "New media added"
1301
1101
  },
1302
1102
  "media-upgraded": {
1303
- "name": "Media upgraded",
1304
1103
  "description": "Tell a destination when a library item changes quality.",
1305
- "keywords": "upgrade quality remux 4k resolution replaced notify discord email webhook"
1104
+ "keywords": "upgrade quality remux 4k resolution replaced notify discord email webhook",
1105
+ "name": "Media upgraded"
1306
1106
  },
1307
1107
  "new-device": {
1308
- "name": "New device",
1309
1108
  "description": "Tell a destination the first time an account streams from a device you have not seen.",
1310
- "keywords": "device new unknown unrecognized phone login sharing notify discord email webhook"
1109
+ "keywords": "device new unknown unrecognized phone login sharing notify discord email webhook",
1110
+ "name": "New device"
1111
+ },
1112
+ "newsletter-failed": {
1113
+ "description": "",
1114
+ "keywords": "",
1115
+ "name": ""
1311
1116
  },
1312
1117
  "no-4k-transcodes": {
1313
- "name": "No 4K transcodes",
1314
1118
  "description": "Stop a stream that transcodes 4K source video.",
1315
- "keywords": "4k transcode quality cpu bandwidth stop"
1119
+ "keywords": "4k transcode quality cpu bandwidth stop",
1120
+ "name": "No 4K transcodes"
1316
1121
  },
1317
1122
  "paused-too-long": {
1318
- "name": "Paused too long",
1319
1123
  "description": "Tell a destination when a stream sits paused past the minutes you allow.",
1320
- "keywords": "pause idle afk stuck abandoned notify discord email webhook"
1124
+ "keywords": "pause idle afk stuck abandoned notify discord email webhook",
1125
+ "name": "Paused too long"
1321
1126
  },
1322
1127
  "plugin-update": {
1323
- "name": "Tracearr plugin update",
1324
1128
  "description": "Tell a destination when a server has a newer Tracearr plugin to install.",
1325
- "keywords": "plugin update upgrade version release notify discord email webhook"
1129
+ "keywords": "plugin update upgrade version release notify discord email webhook",
1130
+ "name": "Tracearr plugin update"
1326
1131
  },
1327
1132
  "server-down": {
1328
- "name": "Server down",
1329
1133
  "description": "Tell a destination when a media server stops answering.",
1330
- "keywords": "offline outage unreachable down notify discord email webhook"
1134
+ "keywords": "offline outage unreachable down notify discord email webhook",
1135
+ "name": "Server down"
1331
1136
  },
1332
1137
  "server-up": {
1333
- "name": "Server back up",
1334
1138
  "description": "Tell a destination when a media server answers again.",
1335
- "keywords": "online recovered restored back up notify discord email webhook"
1139
+ "keywords": "online recovered restored back up notify discord email webhook",
1140
+ "name": "Server back up"
1336
1141
  },
1337
1142
  "server-update": {
1338
- "name": "Media server update",
1339
1143
  "description": "Tell a destination when a media server has an update available.",
1340
- "keywords": "update upgrade version release plex jellyfin emby notify discord"
1144
+ "keywords": "update upgrade version release plex jellyfin emby notify discord",
1145
+ "name": "Media server update"
1341
1146
  },
1342
1147
  "simultaneous-locations": {
1343
- "name": "Two places at once",
1344
1148
  "description": "Raise a violation when one account streams from two distant places at the same time.",
1345
- "keywords": "distance location sharing vpn two places at once"
1149
+ "keywords": "distance location sharing vpn two places at once",
1150
+ "name": "Two places at once"
1346
1151
  },
1347
1152
  "stream-ended": {
1348
- "name": "Stream ended",
1349
1153
  "description": "Tell a destination every time a stream stops.",
1350
- "keywords": "stop end finish playback notify discord email webhook"
1154
+ "keywords": "stop end finish playback notify discord email webhook",
1155
+ "name": "Stream ended"
1351
1156
  },
1352
1157
  "stream-started": {
1353
- "name": "Stream started",
1354
1158
  "description": "Tell a destination every time a stream starts.",
1355
- "keywords": "play watch begin start viewing notify discord email webhook"
1159
+ "keywords": "play watch begin start viewing notify discord email webhook",
1160
+ "name": "Stream started"
1356
1161
  },
1357
1162
  "tracearr-update": {
1358
- "name": "Tracearr update",
1359
1163
  "description": "Tell a destination when a new Tracearr release is out.",
1360
- "keywords": "update upgrade version release tracearr notify discord email webhook"
1164
+ "keywords": "update upgrade version release tracearr notify discord email webhook",
1165
+ "name": "Tracearr update"
1361
1166
  },
1362
1167
  "transcode-started": {
1363
- "name": "Stream is transcoding",
1364
1168
  "description": "Tell a destination when a stream transcodes video or audio.",
1365
- "keywords": "transcode convert cpu direct play quality notify discord email webhook"
1169
+ "keywords": "transcode convert cpu direct play quality notify discord email webhook",
1170
+ "name": "Stream is transcoding"
1366
1171
  },
1367
1172
  "trust-score-changed": {
1368
- "name": "Trust score changed",
1369
1173
  "description": "Tell a destination when an account's trust score changes.",
1370
- "keywords": "trust score reputation penalty adjusted notify discord email webhook"
1174
+ "keywords": "trust score reputation penalty adjusted notify discord email webhook",
1175
+ "name": "Trust score changed"
1371
1176
  }
1372
1177
  },
1178
+ "thisAutomation": "This automation",
1373
1179
  "title": "Automations",
1374
1180
  "toggleAutomation": "Turn {{name}} on or off",
1181
+ "trustModes": {
1182
+ "adjust": {
1183
+ "label": "Adjust by amount"
1184
+ },
1185
+ "reset": {
1186
+ "label": "Reset to default (100)"
1187
+ },
1188
+ "set": {
1189
+ "label": "Set to value"
1190
+ }
1191
+ },
1375
1192
  "tryAdjustingFilters": "Try adjusting your filters.",
1376
1193
  "units": {
1194
+ "days": "days",
1195
+ "gb": "GB",
1196
+ "hours": "hours",
1377
1197
  "km": "km",
1378
1198
  "kmh": "km/h",
1379
1199
  "mbps": "Mbps",
1380
- "days": "days",
1381
1200
  "minutes": "minutes",
1382
- "hours": "hours",
1383
- "gb": "GB",
1384
1201
  "seconds": "seconds"
1385
1202
  },
1386
- "updateAutomation": "Update Automation",
1387
- "catalog": {
1388
- "groups": {
1389
- "sessions": "Sessions",
1390
- "accounts": "Accounts",
1391
- "library": "Library",
1392
- "servers": "Servers",
1393
- "updates": "Updates",
1394
- "notify": "Notify",
1395
- "policy": "Policy",
1396
- "control": "Control flow"
1397
- },
1398
- "suggested": "Suggested",
1399
- "triggers": {
1400
- "sessionStarted": {
1401
- "description": "",
1402
- "synonyms": "play, watch, begin, start, viewing"
1403
- },
1404
- "sessionFirstSeen": {
1405
- "description": "",
1406
- "synonyms": ""
1407
- },
1408
- "sessionStopped": {
1409
- "description": "Playback ends, however it ended.",
1410
- "synonyms": "end, finish, quit, close"
1411
- },
1412
- "sessionTranscodeChanged": {
1413
- "description": "The server switches a stream between direct play and transcoding.",
1414
- "synonyms": "transcode, convert, direct play, cpu"
1415
- },
1416
- "sessionPaused": {
1417
- "description": "The moment a stream is paused.",
1418
- "synonyms": "pause, hold, idle"
1419
- },
1420
- "sessionHeldFor": {
1421
- "label": "A stream sits paused",
1422
- "description": "A stream has been paused longer than the set number of minutes.",
1423
- "synonyms": "pause, idle, abandoned, stuck, afk"
1424
- },
1425
- "accountInactiveFor": {
1426
- "label": "An account goes quiet",
1427
- "description": "An account has watched nothing for the set number of days.",
1428
- "synonyms": "inactive, dormant, unused, stale, cleanup"
1429
- },
1430
- "accountNewDevice": {
1431
- "description": "An account streams from a device for the first time.",
1432
- "synonyms": "device, new, unknown, unrecognized, phone, login, sharing"
1433
- },
1434
- "accountTrustChanged": {
1435
- "description": "An account's trust score changes, whether an automation or an owner moved it.",
1436
- "synonyms": "trust, score, reputation, penalty, adjusted"
1437
- },
1438
- "mediaAdded": {
1439
- "description": "A library item shows up on a server for the first time.",
1440
- "synonyms": "new, added, library, movie, episode, import"
1441
- },
1442
- "mediaUpgraded": {
1443
- "description": "A library item that was already there changes quality.",
1444
- "synonyms": "upgrade, quality, replaced, remux, 4k, resolution"
1445
- },
1446
- "serverDown": {
1447
- "description": "A media server stops answering.",
1448
- "synonyms": "unreachable, offline, outage, down"
1449
- },
1450
- "serverUp": {
1451
- "description": "A media server answers again.",
1452
- "synonyms": "online, recovered, restored, back"
1453
- },
1454
- "pluginUpdateAvailable": {
1455
- "description": "The Tracearr plugin on a server has a newer release.",
1456
- "synonyms": "plugin, upgrade, version, release"
1457
- },
1458
- "serverUpdateAvailable": {
1459
- "description": "A media server has a newer release.",
1460
- "synonyms": "upgrade, version, release, patch"
1461
- },
1462
- "tracearrUpdateAvailable": {
1463
- "description": "Tracearr itself has a newer release.",
1464
- "synonyms": "upgrade, version, release, self"
1465
- }
1466
- },
1467
- "actions": {
1468
- "send": {
1469
- "synonyms": "notify, alert, discord, email, webhook, push"
1470
- },
1471
- "trust": {
1472
- "synonyms": "score, reputation, penalise, reward"
1473
- },
1474
- "kill_stream": {
1475
- "synonyms": "stop, terminate, cut, end playback"
1476
- },
1477
- "message_client": {
1478
- "synonyms": "warn, tell, notice, on screen"
1479
- },
1480
- "if": {
1481
- "label": "Branch on a condition",
1482
- "description": "Run one set of steps when a condition holds and another when it does not.",
1483
- "synonyms": "if, else, otherwise, branch, split, condition"
1484
- }
1485
- }
1486
- },
1487
- "filters": {
1488
- "source": "Where it came from",
1489
- "allSources": "Anywhere",
1490
- "sources": {
1491
- "builtin": "Built-in",
1492
- "import": "Imported",
1493
- "local": "Saved here",
1494
- "own": "Built in the builder"
1495
- },
1496
- "trigger": "What starts it",
1497
- "allTriggers": "All triggers"
1498
- },
1499
- "openGallery": "Open the gallery"
1500
- },
1501
- "terminateStream": {
1502
- "title": "Terminate Stream",
1503
- "stopMedia": "Stop \"{{mediaTitle}}\" for @{{username}}?",
1504
- "messageLabel": "Message to user (optional)",
1505
- "messagePlaceholder": "e.g., Please don't share your account",
1506
- "messageHint": "This message will be shown to them during playback",
1507
- "terminating": "Terminating...",
1508
- "killStream": "Kill Stream"
1509
- },
1510
- "notFound": {
1511
- "title": "404",
1512
- "heading": "Page Not Found",
1513
- "description": "The page you're looking for doesn't exist or has been moved."
1514
- },
1515
- "settings": {
1516
- "plex": {
1517
- "noServersFound": "No Plex servers found",
1518
- "noServersFoundHint": "Make sure you own at least one Plex server",
1519
- "noReachableConnections": "No reachable connections",
1520
- "local": "Local",
1521
- "remote": "Remote",
1522
- "custom": "Custom",
1523
- "secure": "Secure",
1524
- "mayNotConnect": "May not connect",
1525
- "recommended": "Recommended",
1526
- "customUrl": "Custom URL",
1527
- "connectionError": {
1528
- "timeout": "Timed out",
1529
- "dns": "DNS error",
1530
- "refused": "Connection refused",
1531
- "unreachable": "Host unreachable",
1532
- "reset": "Connection reset",
1533
- "tls": "TLS error",
1534
- "http": "HTTP {{status}}",
1535
- "unknown": "Connection failed"
1536
- },
1537
- "connectionsReachable": "{{reachable}} of {{total}} connections reachable",
1538
- "connectionsAvailable": "{{count}} connections available",
1539
- "hideFiltered": "Hide filtered",
1540
- "showAll": "Show all",
1541
- "moreConnections": "+{{count}} more connections",
1542
- "connectingTo": "Connecting to {{name}}...",
1543
- "noAccountsLinked": "No Plex Accounts Linked",
1544
- "noAccountsLinkedHint": "Link a Plex account to add Plex servers to Tracearr.",
1545
- "linkPlexAccount": "Link Plex Account",
1546
- "linkAnotherAccount": "Link Another Plex Account",
1547
- "linking": "Linking...",
1548
- "accountsLinked_one": "{{count}} Plex account linked",
1549
- "accountsLinked_other": "{{count}} Plex accounts linked",
1550
- "noAccountsLinkedShort": "No Plex accounts linked",
1551
- "loginEnabled": "Login Enabled",
1552
- "serversConnected_one": "{{count}} server connected",
1553
- "serversConnected_other": "{{count}} servers connected",
1554
- "unlinkAccount": "Unlink this Plex account",
1555
- "reauthorizeAccount": "Reauthorize this Plex account",
1556
- "deleteServersFirst": "Delete connected servers first to unlink this account",
1557
- "linkedAccounts": "Linked Plex Accounts",
1558
- "linkedAccountsDesc": "",
1559
- "noAccountsYet": "No Plex accounts linked yet.",
1560
- "unlinkPlexAccount": "Unlink Plex Account",
1561
- "unlinkConfirm": "Are you sure you want to unlink this Plex account? You won't be able to add servers from this account until you link it again."
1562
- },
1563
- "destinations": {
1564
- "add": "Add destination",
1565
- "builtinNote": "Built in",
1566
- "clearSecret": "Clear",
1567
- "delete": "Delete",
1568
- "deleteConfirm": "Delete {{name}}? Rules that send to it will be blocked until they are updated.",
1569
- "description": "Where notifications go. Add as many as you like, and automations can send to any of them.",
1570
- "empty": "No destinations yet.",
1571
- "fields": {
1572
- "webhookUrl": "Webhook URL",
1573
- "url": "URL",
1574
- "serverUrl": "Server URL",
1575
- "apiUrl": "API URL",
1576
- "topic": "Topic",
1577
- "authToken": "Auth token",
1578
- "userKey": "User key",
1579
- "apiToken": "API token"
1580
- },
1581
- "hints": {
1582
- "authTokenOptional": "Optional for public topics"
1583
- },
1584
- "ownerOnly": "Only the owner can manage notification destinations.",
1585
- "pushNote": "Delivered to paired mobile devices; each device filters in its own notification settings.",
1586
- "receiveViolations": "Receive violations",
1587
- "receiveViolationsHint": "",
1588
- "reencrypt": "Re-enter this destination's secret",
1589
- "secretSet": "Set (leave blank to keep)",
1590
- "test": "Test",
1591
- "testHint": "Save first to test",
1592
- "testNeedsForm": "Fill in the required fields to test",
1593
- "title": "Notification destinations",
1594
- "types": {
1595
- "discord": "Discord",
1596
- "jsonWebhook": "Webhook (JSON)",
1597
- "ntfy": "ntfy",
1598
- "gotify": "Gotify",
1599
- "apprise": "Apprise",
1600
- "pushover": "Pushover",
1601
- "push": "Mobile push",
1602
- "webToast": "Browser toasts"
1603
- },
1604
- "usedBy": "Used by {{count}} rule",
1605
- "usedBy_other": "Used by {{count}} rules",
1606
- "webToastNote": "Toasts in this browser."
1607
- },
1608
- "jobs": {
1609
- "runNow": "Run Now",
1610
- "running": "Running...",
1611
- "lastRun": "Last run",
1612
- "nextRun": "Next run",
1613
- "schedule": "Schedule"
1614
- },
1615
- "mobile": {
1616
- "editDisplayName": "Edit Display Name",
1617
- "editDisplayNameDesc": "Change how this device appears in your device list",
1618
- "displayName": "Display Name",
1619
- "displayNamePlaceholder": "e.g., My iPhone",
1620
- "updating": "Updating..."
1621
- }
1203
+ "updateAutomation": "Update Automation"
1622
1204
  },
1623
- "maintenance": {
1624
- "startingTitle": "Tracearr is starting up...",
1625
- "interruptionTitle": "Service interruption",
1626
- "startingDescription": "The server is waiting for backend services to become available. This page will automatically refresh when everything is ready.",
1627
- "interruptionDescription": "One or more backend services have become unavailable. This page will automatically refresh when connectivity is restored.",
1628
- "unreachable": "Can't reach the Tracearr server right now. Live updates are paused and will resume on their own.",
1629
- "restoreTitle": "Restoring from backup...",
1630
- "restoreFailed": "Restore failed",
1631
- "restorePhase": {
1632
- "validating": "Validating backup",
1633
- "creating_restore_point": "Creating restore point",
1634
- "shutting_down": "Shutting down services",
1635
- "restoring_database": "Restoring database",
1636
- "running_migrations": "Running migrations",
1637
- "rebuilding_aggregates": "Rebuilding aggregates",
1638
- "restarting": "Restarting services",
1639
- "complete": "Restore complete"
1640
- },
1641
- "initStep": {
1642
- "migrations": "Applying database migrations",
1643
- "timescale": "Preparing TimescaleDB (this can take a while after an upgrade)",
1644
- "services": "Starting services"
1645
- },
1646
- "doNotRestart": "Do not restart or stop the server while this runs. Interrupting it can leave the database half-upgraded."
1205
+ "dashboard": {
1206
+ "activeUsers": "Active Users",
1207
+ "alerts": "Alerts",
1208
+ "bandwidth": "Bandwidth",
1209
+ "noActiveStreams": "No active streams",
1210
+ "nowPlaying": "Now Playing",
1211
+ "plays": "Plays",
1212
+ "serverResources": "Server Resources",
1213
+ "streamLocations": "Stream Locations",
1214
+ "streamsAppearHere": "Active streams will appear here when users start watching",
1215
+ "watchTime": "Watch Time"
1647
1216
  },
1648
- "map": {
1649
- "allUsers": "All users",
1650
- "allTypes": "All types",
1651
- "heatmap": "Heatmap",
1652
- "circles": "Circles",
1653
- "streams": "streams",
1654
- "locations": "locations",
1655
- "allActivity": "All activity",
1656
- "basemapMissing": "",
1657
- "webglUnavailable": "",
1658
- "webglHint": "",
1659
- "basemapShadowed": "",
1660
- "badMounts": ""
1217
+ "debug": {
1218
+ "clearAutomations": "Delete all automations and runs",
1219
+ "clearAutomationsConfirm": "Delete every automation and all of their runs?",
1220
+ "clearLibraryCache": "Clear Library Cache",
1221
+ "clearMobileDevices": "Clear Mobile Devices",
1222
+ "clearQueryCache": "Clear Query Cache",
1223
+ "clearServers": "Clear Servers",
1224
+ "clearSessions": "Clear Sessions",
1225
+ "clearStuckJobs": "Clear Stuck Jobs",
1226
+ "clearTerminationLogs": "Clear Termination Logs",
1227
+ "clearUsers": "Clear Users",
1228
+ "clearViolations": "Clear Violations",
1229
+ "clickLoadToView": "Click \"Load\" to view snapshots",
1230
+ "cpu": "CPU",
1231
+ "database": "Database",
1232
+ "databaseDesc": "Database size and table statistics",
1233
+ "deleteAllSuspicious": "Delete All Suspicious",
1234
+ "deleteSelected": "Delete Selected",
1235
+ "description": "Administrative utilities for troubleshooting and data management",
1236
+ "destructiveActions": "Destructive Actions",
1237
+ "environment": "Environment",
1238
+ "factoryReset": "Factory Reset",
1239
+ "libraryItems": "Library Items",
1240
+ "librarySnapshots": "Library Snapshots",
1241
+ "load": "Load",
1242
+ "logExplorerUnavailable": "Log explorer is only available in Docker environments",
1243
+ "logs": "Logs",
1244
+ "maintenance": "Maintenance",
1245
+ "manageSnapshots": "Manage library snapshots used for Storage Trend and Quality Evolution charts",
1246
+ "memory": "Memory",
1247
+ "noSuspiciousSnapshots": "No suspicious snapshots found",
1248
+ "obliterateAllJobs": "Obliterate All Jobs",
1249
+ "of": "of",
1250
+ "ok": "OK",
1251
+ "overview": "Overview",
1252
+ "plexAccounts": "Plex Accounts",
1253
+ "refreshAggregates": "Refresh Aggregates",
1254
+ "selected": "selected",
1255
+ "snapshots": "snapshot(s)",
1256
+ "suspicious": "Suspicious",
1257
+ "suspiciousOnly": "Suspicious only",
1258
+ "systemInformation": "System Information",
1259
+ "tasks": "Tasks",
1260
+ "terminations": "Terminations",
1261
+ "title": "Debug Tools",
1262
+ "totalSize": "Total Size",
1263
+ "uptime": "Uptime"
1661
1264
  },
1662
1265
  "devices": {
1663
- "title": "Device Compatibility",
1664
- "description": "See which devices direct play vs transcode each codec",
1665
1266
  "analyzedSessions": "Analyzed Sessions",
1666
1267
  "analyzedSessionsTooltip": "Sessions in device + codec combinations with at least {{count}} sessions and a known codec. Rare combinations and sessions with no codec info aren't counted.",
1667
- "directPlayRate": "Direct Play Rate",
1668
- "videoAndAudio": "Video + audio",
1669
- "uniqueDevices": "Unique Devices",
1670
- "uniqueCodecs": "Unique Codecs",
1671
- "deviceHealth": "Device Health",
1672
- "deviceHealthDesc": "Direct play rate by device type",
1673
- "transcodeHotspots": "Transcode Hotspots",
1674
- "transcodeHotspotsDesc": "Combinations causing the most transcodes",
1675
- "deviceAndCodec": "Device + Codec",
1676
- "transcodes": "Transcodes",
1677
- "pctOfTotal": "% of Total",
1678
- "noTranscodeHotspots": "No transcode hotspots",
1679
1268
  "compatibilityMatrix": "Compatibility Matrix",
1680
1269
  "compatibilityMatrixDesc": "Direct play rates by device and video codec. Sorted by session volume.",
1681
- "noDeviceDataPeriod": "No device data in this period",
1682
- "legend": "Legend:",
1270
+ "description": "See which devices direct play vs transcode each codec",
1271
+ "deviceAndCodec": "Device + Codec",
1272
+ "deviceHealth": "Device Health",
1273
+ "deviceHealthDesc": "Direct play rate by device type",
1683
1274
  "directPlayHigh": "≥80% Direct",
1684
- "directPlayMid": "50-79%",
1685
1275
  "directPlayLow": "<50%",
1276
+ "directPlayMid": "50-79%",
1277
+ "directPlayRate": "Direct Play Rate",
1278
+ "legend": "Legend:",
1279
+ "noDeviceDataPeriod": "No device data in this period",
1280
+ "noTranscodeHotspots": "No transcode hotspots",
1281
+ "noTranscodingUsers": "No transcoding users found",
1282
+ "pctOfTotal": "% of Total",
1283
+ "title": "Device Compatibility",
1686
1284
  "topTranscodingUsers": "Top Transcoding Users",
1687
1285
  "topTranscodingUsersDesc": "Users causing the most transcodes on your server",
1688
- "noTranscodingUsers": "No transcoding users found"
1286
+ "transcodeHotspots": "Transcode Hotspots",
1287
+ "transcodeHotspotsDesc": "Combinations causing the most transcodes",
1288
+ "transcodes": "Transcodes",
1289
+ "uniqueCodecs": "Unique Codecs",
1290
+ "uniqueDevices": "Unique Devices",
1291
+ "videoAndAudio": "Video + audio"
1689
1292
  },
1690
- "statsBandwidth": {
1691
- "title": "Bandwidth",
1692
- "description": "Streaming bandwidth usage and bitrate analysis",
1693
- "dataTransferred": "Data Transferred",
1694
- "avgBitrate": "Avg Bitrate",
1695
- "avgBitrateMbps": "Avg Bitrate (Mbps)",
1696
- "peakBitrate": "Peak: {{value}} Mbps",
1697
- "totalWatchTime": "Total Watch Time",
1698
- "uniqueUsers": "Unique Users",
1699
- "dailyUsage": "Daily Bandwidth Usage",
1700
- "dailyUsageDesc": "Average bitrate and session count over time",
1701
- "topUsers": "Top Bandwidth Users",
1702
- "topUsersDesc": "Users consuming the most bandwidth",
1703
- "noData": "No bandwidth data available"
1293
+ "history": {
1294
+ "deleteSession_one": "Delete {{count}} Session",
1295
+ "deleteSession_other": "Delete {{count}} Sessions",
1296
+ "deleteSessionsConfirm": "Are you sure you want to delete? This action cannot be undone.",
1297
+ "description": "Browse all streaming sessions with powerful filtering",
1298
+ "loadingMore": "Loading more...",
1299
+ "scrollForMore": "Scroll for more",
1300
+ "showingAllResults": "Showing all {{total}} results",
1301
+ "title": "History"
1704
1302
  },
1705
- "statsUsers": {
1706
- "noActivity": "No activity yet",
1707
- "noActivityDesc": "",
1708
- "top3": "Top 3",
1709
- "runnersUp": "Runners Up"
1710
- },
1711
- "plexCallback": {
1712
- "authComplete": "Authentication complete",
1713
- "windowWillClose": "This window will close automatically..."
1714
- },
1715
- "apiDocs": {
1716
- "backToSettings": "Back to Settings",
1717
- "apiKeyAutoLoaded": "API key auto-loaded",
1718
- "noApiKey": "No API key generated - create one in Settings to test endpoints",
1719
- "versionSwitcherLabel": "API documentation version",
1720
- "versionV1": "API v1",
1721
- "versionV2": "API v2",
1722
- "specLoadError": "Failed to load the API specification. Check your API key and try again."
1723
- },
1724
- "debug": {
1725
- "title": "Debug Tools",
1726
- "description": "Administrative utilities for troubleshooting and data management",
1727
- "overview": "Overview",
1728
- "librarySnapshots": "Library Snapshots",
1729
- "tasks": "Tasks",
1730
- "logs": "Logs",
1731
- "plexAccounts": "Plex Accounts",
1732
- "terminations": "Terminations",
1733
- "libraryItems": "Library Items",
1734
- "environment": "Environment",
1735
- "systemInformation": "System Information",
1736
- "cpu": "CPU",
1737
- "memory": "Memory",
1738
- "uptime": "Uptime",
1739
- "database": "Database",
1740
- "databaseDesc": "Database size and table statistics",
1741
- "totalSize": "Total Size",
1742
- "maintenance": "Maintenance",
1743
- "destructiveActions": "Destructive Actions",
1744
- "refreshAggregates": "Refresh Aggregates",
1745
- "clearStuckJobs": "Clear Stuck Jobs",
1746
- "obliterateAllJobs": "Obliterate All Jobs",
1747
- "clearQueryCache": "Clear Query Cache",
1748
- "clearMobileDevices": "Clear Mobile Devices",
1749
- "clearViolations": "Clear Violations",
1750
- "clearAutomations": "Delete all automations and runs",
1751
- "clearAutomationsConfirm": "Delete every automation and all of their runs?",
1752
- "clearTerminationLogs": "Clear Termination Logs",
1753
- "clearLibraryCache": "Clear Library Cache",
1754
- "clearSessions": "Clear Sessions",
1755
- "clearUsers": "Clear Users",
1756
- "clearServers": "Clear Servers",
1757
- "factoryReset": "Factory Reset",
1758
- "manageSnapshots": "Manage library snapshots used for Storage Trend and Quality Evolution charts",
1759
- "suspiciousOnly": "Suspicious only",
1760
- "load": "Load",
1761
- "noSuspiciousSnapshots": "No suspicious snapshots found",
1762
- "clickLoadToView": "Click \"Load\" to view snapshots",
1763
- "deleteSelected": "Delete Selected",
1764
- "deleteAllSuspicious": "Delete All Suspicious",
1765
- "suspicious": "Suspicious",
1766
- "ok": "OK",
1767
- "selected": "selected",
1768
- "snapshots": "snapshot(s)",
1769
- "of": "of",
1770
- "logExplorerUnavailable": "Log explorer is only available in Docker environments"
1771
- },
1772
- "media": {
1773
- "landing": {
1774
- "title": "Media",
1775
- "lens": {
1776
- "label": "Viewing as",
1777
- "allUsers": "All users"
1778
- },
1779
- "shelves": {
1780
- "recentlyAddedMovies": "Recently Added Movies",
1781
- "recentlyAddedShows": "Recently Added Shows",
1782
- "mostPopularMovies": "Most Popular Movies",
1783
- "mostPopularShows": "Most Popular Shows",
1784
- "emptyRecentlyAdded": "Nothing added in this period",
1785
- "emptyMostPopular": "No plays in this period",
1786
- "captionRecentlyAdded": "deduped across servers",
1787
- "captionMostPopular": {
1788
- "day": "today",
1789
- "week": "last 7 days",
1790
- "month": "last 30 days",
1791
- "year": "last 12 months",
1792
- "all": "all time",
1793
- "custom": "selected date range"
1794
- }
1795
- },
1796
- "card": {
1797
- "newEpisodes_one": "{{count}} new episode",
1798
- "newEpisodes_other": "{{count}} new episodes",
1799
- "addedAgo": "added {{date}}",
1800
- "addedCompactAgo": "added {{age}} ago",
1801
- "newEpisodesChip": "{{count}} new"
1802
- },
1803
- "deadWeight": {
1804
- "title": "Dead Weight",
1805
- "summary": "{{count}} never-watched titles · {{size}}",
1806
- "empty": "Nothing to reclaim - everything in your library has been watched",
1807
- "columns": {
1808
- "poster": "Poster",
1809
- "title": "Title",
1810
- "size": "Size",
1811
- "added": "Added",
1812
- "servers": "Servers"
1813
- },
1814
- "viewAll": "View all",
1815
- "viewAllTooltip": "Coming soon"
1816
- },
1817
- "loadError": "Couldn't load your media library"
1818
- },
1819
- "movies": {
1820
- "title": "Movies"
1821
- },
1822
- "shows": {
1823
- "title": "Shows"
1824
- },
1825
- "genres": {
1826
- "title": "Genres",
1827
- "subtitle": "Plays and watch time by genre, across every server in view.",
1828
- "chart": {
1829
- "title": "Plays by genre",
1830
- "valueLabel": "Plays",
1831
- "itemCount_one": "{{count}} title",
1832
- "itemCount_other": "{{count}} titles",
1833
- "ariaLabel": "Bar chart of plays by genre, sorted highest to lowest. The full breakdown is available in the table below."
1834
- },
1835
- "table": {
1836
- "title": "Genre breakdown",
1837
- "columns": {
1838
- "genre": "Genre",
1839
- "items": "Items",
1840
- "plays": "Plays",
1841
- "watchTime": "Watch time"
1842
- },
1843
- "browseMovies": "Browse {{genre}} movies",
1844
- "browseShows": "Browse {{genre}} shows"
1845
- },
1846
- "empty": {
1847
- "title": "No genres captured yet",
1848
- "description": "Genres come from your media servers' metadata sync. Check back after the next sync completes."
1849
- },
1850
- "loadError": "Couldn't load genres"
1851
- },
1852
- "detail": {
1853
- "title": "Media Details",
1854
- "breadcrumb": {
1855
- "ariaLabel": "Breadcrumb"
1856
- },
1857
- "notFound": {
1858
- "title": "Media not found",
1859
- "message": "This title doesn't exist or you don't have access to it.",
1860
- "backLink": "Back to Media"
1861
- },
1862
- "hero": {
1863
- "loadError": "Couldn't load this title",
1864
- "meta": {
1865
- "seasons_one": "{{count}} season",
1866
- "seasons_other": "{{count}} seasons",
1867
- "episodes_one": "{{count}} episode",
1868
- "episodes_other": "{{count}} episodes"
1869
- },
1870
- "availability": {
1871
- "added": "added {{date}}",
1872
- "addedRemoved": "added {{added}} – removed {{removed}}",
1873
- "replaced": "replaced {{date}}"
1874
- },
1875
- "removedEverywhere": {
1876
- "caption": "No longer available on any connected server"
1877
- },
1878
- "actions": {
1879
- "fullHistory": "Full history",
1880
- "openOnServer": "Open on server"
1881
- }
1303
+ "library": {
1304
+ "description": "Top movies and shows on your server",
1305
+ "emptyState": {
1306
+ "backfillAvailable": {
1307
+ "bodyGeneric": "Generate historical snapshots to see library trends over time.",
1308
+ "bodyWithDays": "Your library has {{days}} days of history. Generate snapshots to see trends in charts.",
1309
+ "syncRunningBody": "Historical data generation will start automatically once the sync completes.",
1310
+ "syncRunningTitle": "Library sync in progress...",
1311
+ "title": "Historical data available"
1882
1312
  },
1883
- "kpis": {
1884
- "ariaLabel": "Watch statistics",
1885
- "loadError": "Couldn't load watch statistics",
1886
- "completionLoadError": "Couldn't load completion",
1887
- "plays": {
1888
- "label": "Plays, all time",
1889
- "caption": "resume chains, short sessions excluded"
1890
- },
1891
- "watchTime": {
1892
- "label": "Watch time",
1893
- "detail": "+{{hours}}h in the last 30 days"
1894
- },
1895
- "viewers": {
1896
- "label": "Viewers",
1897
- "detail": "across all servers"
1898
- },
1899
- "completion": {
1900
- "label": "Avg completion",
1901
- "detail": "{{finished}} of {{total}} finished every episode",
1902
- "detailMovie": "{{finished}} of {{total}} watched to completion"
1903
- }
1313
+ "backfillRunning": {
1314
+ "fallbackBody": "Creating snapshots from library history. This may take a few minutes.",
1315
+ "progress": "{{processed}} of {{total}} libraries",
1316
+ "snapshotsSuffix": " ({{count}} snapshots)",
1317
+ "title": "Generating historical data..."
1904
1318
  },
1905
- "watchers": {
1906
- "title": "Watchers",
1907
- "loadError": "Couldn't load watchers",
1908
- "empty": "No one has watched this yet.",
1909
- "lastWatchedAgo": "{{age}} ago",
1910
- "completionLabel": "{{percent}}% complete",
1911
- "columns": {
1912
- "user": "User",
1913
- "plays": "Plays",
1914
- "episodes": "Episodes",
1915
- "completion": "Completion",
1916
- "lastWatched": "Last watched"
1917
- }
1319
+ "checkingStatus": "Checking library status...",
1320
+ "generateHistory": "Generate History",
1321
+ "multiServer": {
1322
+ "body": "Sync the servers below to see combined library statistics.",
1323
+ "needsBackfillIntro": "These servers are synced but have no historical data yet:",
1324
+ "title": "Some libraries need attention"
1918
1325
  },
1919
- "seasons": {
1920
- "title": "Seasons",
1921
- "loadError": "Couldn't load season data",
1922
- "empty": "No season data yet",
1923
- "episodeCount_one": "{{count}} episode",
1924
- "episodeCount_other": "{{count}} episodes",
1925
- "watchedPct": "{{percent}}% watched",
1926
- "stripSummary": "{{season}}: {{percent}}% watched",
1927
- "episodeLabel": {
1928
- "watched": "{{code}}: watched",
1929
- "partial": "{{code}}: partially watched",
1930
- "unwatched": "{{code}}: unwatched"
1931
- }
1326
+ "noMedia": {
1327
+ "body": "This library is synced but doesn't have any movies or shows in it yet.",
1328
+ "title": "No movies or shows yet"
1932
1329
  },
1933
- "platforms": {
1934
- "title": "Platforms",
1935
- "loadError": "Couldn't load platform breakdown",
1936
- "empty": "No platform data yet",
1937
- "unknown": "Unknown",
1938
- "columns": {
1939
- "platform": "Platform",
1940
- "plays": "Plays",
1941
- "watchTime": "Watch time"
1942
- }
1330
+ "notSynced": {
1331
+ "body": "Library statistics will appear here once the library has been synced. This typically happens automatically every hour.",
1332
+ "title": "Library not synced yet"
1943
1333
  },
1944
- "history": {
1945
- "title": "History",
1946
- "loadError": "Couldn't load history",
1947
- "empty": "No plays recorded yet",
1948
- "watched": "Watched",
1949
- "notWatched": "Not finished",
1950
- "columns": {
1951
- "date": "Date",
1952
- "user": "User",
1953
- "content": "Content",
1954
- "server": "Server",
1955
- "duration": "Duration"
1956
- }
1334
+ "notSyncedShort": "Not synced yet",
1335
+ "starting": "Starting...",
1336
+ "syncInProgress": {
1337
+ "body": "Library statistics will appear once the sync completes. This may take a few minutes depending on library size.",
1338
+ "title": "Library sync in progress..."
1957
1339
  },
1958
- "copies": {
1959
- "title": "Copies",
1960
- "loadError": "Couldn't load copies",
1961
- "unknownLibrary": "Unknown library",
1962
- "columns": {
1963
- "server": "Server",
1964
- "library": "Library",
1965
- "quality": "Quality",
1966
- "episodes": "Episodes",
1967
- "size": "Size",
1968
- "added": "Added"
1969
- },
1970
- "versionLabel": "File {{index}}"
1340
+ "syncNow": "Sync Now",
1341
+ "syncing": "Syncing...",
1342
+ "toast": {
1343
+ "backfillCompleteTitle": "Backfill complete",
1344
+ "backfillErrorTitle": "Backfill failed",
1345
+ "backfillFailedTitle": "Failed to start backfill",
1346
+ "backfillStartedDesc": "Historical snapshots are being generated.",
1347
+ "backfillStartedTitle": "Backfill started",
1348
+ "genericRetry": "Please try again.",
1349
+ "noServerSelected": "No server selected",
1350
+ "syncFailedTitle": "Failed to start sync",
1351
+ "syncStartedDesc": "This may take a few minutes depending on library size.",
1352
+ "syncStartedTitle": "Library sync started"
1971
1353
  }
1972
1354
  },
1973
- "posterCard": {
1974
- "rankSuffix": ", rank {{rank}}",
1975
- "onServers": "On {{servers}}",
1976
- "addedLabel": "Added {{date}}",
1977
- "plays_one": "{{count}} play",
1978
- "plays_other": "{{count}} plays",
1979
- "viewers_one": "{{count}} viewer",
1980
- "viewers_other": "{{count}} viewers",
1981
- "watchedState": {
1982
- "watched": "Watched",
1983
- "partial": "Partially watched",
1984
- "watchedByOthers": "Watched by others",
1985
- "watchedByYou": "Watched by you"
1986
- },
1987
- "tileLabel": {
1355
+ "noMoviePlays": "No movie plays in this period",
1356
+ "noShowPlays": "No TV show plays in this period",
1357
+ "overview": {
1358
+ "added": "Added",
1359
+ "description": "Library health and growth metrics",
1360
+ "failedToLoad": "Failed to load library statistics",
1361
+ "failedToLoadDesc": "Could not fetch library data. Please try again.",
1362
+ "lastUpdated": "Last updated:",
1363
+ "libraryGrowth": "Library Growth",
1364
+ "serversNeedSync": "These servers need to sync:",
1365
+ "shows": "shows",
1366
+ "thisMonth": "this month",
1367
+ "thisPeriod": "this period",
1368
+ "thisWeek": "this week",
1369
+ "thisYear": "this year",
1370
+ "totalItems": "Total Items"
1371
+ },
1372
+ "quality": {
1373
+ "all": "All",
1374
+ "description": "Resolution and codec distribution",
1375
+ "failedToLoad": "Failed to load quality data",
1376
+ "failedToLoadDesc": "Could not fetch quality data. Please try again.",
1377
+ "qualityEvolution": "Quality Evolution",
1378
+ "title": "Quality"
1379
+ },
1380
+ "storage": {
1381
+ "avgHoursPerGB": "avg hours/GB",
1382
+ "colCopies": "Copies",
1383
+ "colMatchType": "Match Type",
1384
+ "colRecoverable": "Recoverable Space",
1385
+ "colTitle": "Title",
1386
+ "confidence": "Confidence",
1387
+ "confidenceHigh": "High",
1388
+ "confidenceLow": "Low",
1389
+ "confidenceMedium": "Medium",
1390
+ "contentROI": "Content ROI",
1391
+ "contentROIDesc": "Watch value per storage cost",
1392
+ "days": "days",
1393
+ "description": "Storage usage, predictions, and optimization",
1394
+ "duplicates": "Duplicates",
1395
+ "duplicatesFailed": "Failed to load duplicates",
1396
+ "duplicatesSubtitle": "Titles stored as more than one physical file, across servers, libraries, and versions",
1397
+ "duplicatesTitle": "Duplicates",
1398
+ "failedToLoad": "Failed to load storage data",
1399
+ "failedToLoadDesc": "Could not fetch storage data. Please try again.",
1400
+ "groups": "groups",
1401
+ "growthPreChangeover": "based on pre-update history",
1402
+ "growthRate": "Growth Rate",
1403
+ "insufficientData": "Insufficient data",
1404
+ "items": "items",
1405
+ "loadingDuplicates": "Loading duplicates...",
1406
+ "mirror": "Mirror",
1407
+ "noDuplicatesDesc": "No titles with more than one physical file detected.",
1408
+ "noDuplicatesTitle": "No duplicates found",
1409
+ "of": "of",
1410
+ "predictions": "Predictions",
1411
+ "recoverable": "recoverable",
1412
+ "sameServer": "Same server",
1413
+ "staleContent": "Stale Content",
1414
+ "staleContentDesc": "Content that may be candidates for removal",
1415
+ "storageTrend": "Storage Trend",
1416
+ "title": "Storage",
1417
+ "totalStorage": "Total Storage",
1418
+ "unused": "unused",
1419
+ "zeroGrowth": "0 GB/mo"
1420
+ },
1421
+ "title": "Library",
1422
+ "topMovies": "Top Movies",
1423
+ "topShows": "Top TV Shows",
1424
+ "versionsBackfill": {
1425
+ "action": "Sync now",
1426
+ "banner": "File version data is still being collected for this server. Run a library sync to finish.",
1427
+ "syncFailed": "Sync failed to start on {{count}} server(s). Check your permissions and server status.",
1428
+ "syncStarted": "Library sync started."
1429
+ },
1430
+ "watch": {
1431
+ "avgPerItem": "avg per item",
1432
+ "bingeHighlights": "Binge Highlights",
1433
+ "bingeHighlightsDesc": "Shows with the most intensive viewing patterns",
1434
+ "bingeSessions": "",
1435
+ "busiest": "Busiest:",
1436
+ "completed": "Completed",
1437
+ "description": "Viewing behavior and content engagement",
1438
+ "failedToLoad": "Failed to load watch analytics",
1439
+ "failedToLoadDesc": "Could not fetch watch data.",
1440
+ "monthlyTrends": "Monthly Trends",
1441
+ "noData": "No watch data yet",
1442
+ "noDataDesc": "Watch analytics will appear here once content has been played. Check back after some viewing activity.",
1443
+ "peak": "Peak:",
1444
+ "peakHour": "Peak Hour",
1445
+ "percentWatched": "% watched",
1446
+ "quietest": "Quietest:",
1447
+ "title": "Watch Analytics",
1448
+ "totalWatchTime": "Total Watch Time",
1449
+ "viewingHours": "Viewing Hours",
1450
+ "watched": "Watched"
1451
+ }
1452
+ },
1453
+ "login": {
1454
+ "accountCreated": "Account created successfully!",
1455
+ "claimCodeDescription": "Check your server logs for the claim code to proceed with setup",
1456
+ "claimCodeHint": "The claim code is printed in the server logs when the container starts",
1457
+ "claimCodeLabel": "Claim Code",
1458
+ "claimCodeRequired": "First-time setup requires a claim code",
1459
+ "claimCodeSecurityNote": "This security measure ensures only authorized users can complete first-time setup",
1460
+ "completeInPopup": "Complete sign-in in the popup window",
1461
+ "connectedTo": "Connected to {{name}}",
1462
+ "continueWith": "Continue with {{provider}}",
1463
+ "createAccountDescription": "Create an account to manage your media servers",
1464
+ "createAccountFailed": "Failed to create account",
1465
+ "createAccountHeading": "Create your account to get started",
1466
+ "displayNamePlaceholder": "Choose a display name",
1467
+ "emailPlaceholder": "your@email.com",
1468
+ "enterClaimCode": "Enter Claim Code",
1469
+ "identifierPlaceholder": "Username or email address",
1470
+ "invalidCredentials": "Invalid email or password",
1471
+ "localDisabledHint": "Local sign-in is disabled for this instance. Ask an admin to run `enable-local-login` from the Tracearr CLI to re-enable it.",
1472
+ "loginFailed": "Login failed",
1473
+ "oidcError": "Single sign-on failed. Please try again or use another sign-in method.",
1474
+ "passwordPlaceholder": "At least 8 characters",
1475
+ "plexAuthFailed": "Plex authentication failed",
1476
+ "plexStartFailed": "Failed to start Plex login",
1477
+ "reopenPlexLogin": "Reopen Plex Login",
1478
+ "selectPlexServer": "Select your Plex server",
1479
+ "serverConnectFailed": "Failed to connect to server",
1480
+ "setupNote": "After creating your account, you'll add your Plex or Jellyfin servers from Settings.",
1481
+ "signInDescription": "Sign in to access your dashboard",
1482
+ "signInHeading": "Sign in to your account",
1483
+ "signupFailed": "Signup failed",
1484
+ "tagline": "Tracearr - Stream access management",
1485
+ "title": "Tracearr",
1486
+ "username": "Username",
1487
+ "usernameOrEmail": "Username or Email",
1488
+ "usernamePlaceholder": "yourusername",
1489
+ "validateClaimCode": "Validate Claim Code",
1490
+ "waitingForPlex": "Waiting for Plex authorization...",
1491
+ "yourPasswordPlaceholder": "Your password"
1492
+ },
1493
+ "maintenance": {
1494
+ "doNotRestart": "Do not restart or stop the server while this runs. Interrupting it can leave the database half-upgraded.",
1495
+ "initStep": {
1496
+ "migrations": "Applying database migrations",
1497
+ "services": "Starting services",
1498
+ "timescale": "Preparing TimescaleDB (this can take a while after an upgrade)"
1499
+ },
1500
+ "interruptionDescription": "One or more backend services have become unavailable. This page will automatically refresh when connectivity is restored.",
1501
+ "interruptionTitle": "Service interruption",
1502
+ "restoreFailed": "Restore failed",
1503
+ "restorePhase": {
1504
+ "complete": "Restore complete",
1505
+ "creating_restore_point": "Creating restore point",
1506
+ "rebuilding_aggregates": "Rebuilding aggregates",
1507
+ "restarting": "Restarting services",
1508
+ "restoring_database": "Restoring database",
1509
+ "running_migrations": "Running migrations",
1510
+ "shutting_down": "Shutting down services",
1511
+ "validating": "Validating backup"
1512
+ },
1513
+ "restoreTitle": "Restoring from backup...",
1514
+ "startingDescription": "The server is waiting for backend services to become available. This page will automatically refresh when everything is ready.",
1515
+ "startingTitle": "Tracearr is starting up...",
1516
+ "unreachable": "Can't reach the Tracearr server right now. Live updates are paused and will resume on their own."
1517
+ },
1518
+ "map": {
1519
+ "allActivity": "All activity",
1520
+ "allTypes": "All types",
1521
+ "allUsers": "All users",
1522
+ "badMounts": "",
1523
+ "basemapMissing": "",
1524
+ "basemapShadowed": "",
1525
+ "circles": "Circles",
1526
+ "heatmap": "Heatmap",
1527
+ "locations": "locations",
1528
+ "streams": "streams",
1529
+ "webglHint": "",
1530
+ "webglUnavailable": ""
1531
+ },
1532
+ "media": {
1533
+ "detail": {
1534
+ "breadcrumb": {
1535
+ "ariaLabel": "Breadcrumb"
1536
+ },
1537
+ "copies": {
1538
+ "columns": {
1539
+ "added": "Added",
1540
+ "episodes": "Episodes",
1541
+ "library": "Library",
1542
+ "quality": "Quality",
1543
+ "server": "Server",
1544
+ "size": "Size"
1545
+ },
1546
+ "loadError": "Couldn't load copies",
1547
+ "title": "Copies",
1548
+ "unknownLibrary": "Unknown library",
1549
+ "versionLabel": "File {{index}}"
1550
+ },
1551
+ "hero": {
1552
+ "actions": {
1553
+ "fullHistory": "Full history",
1554
+ "openOnServer": "Open on server"
1555
+ },
1556
+ "availability": {
1557
+ "added": "added {{date}}",
1558
+ "addedRemoved": "added {{added}} – removed {{removed}}",
1559
+ "replaced": "replaced {{date}}"
1560
+ },
1561
+ "loadError": "Couldn't load this title",
1562
+ "meta": {
1563
+ "episodes_one": "{{count}} episode",
1564
+ "episodes_other": "{{count}} episodes",
1565
+ "seasons_one": "{{count}} season",
1566
+ "seasons_other": "{{count}} seasons"
1567
+ },
1568
+ "removedEverywhere": {
1569
+ "caption": "No longer available on any connected server"
1570
+ }
1571
+ },
1572
+ "history": {
1573
+ "columns": {
1574
+ "content": "Content",
1575
+ "date": "Date",
1576
+ "duration": "Duration",
1577
+ "server": "Server",
1578
+ "user": "User"
1579
+ },
1580
+ "empty": "No plays recorded yet",
1581
+ "loadError": "Couldn't load history",
1582
+ "notWatched": "Not finished",
1583
+ "title": "History",
1584
+ "watched": "Watched"
1585
+ },
1586
+ "kpis": {
1587
+ "ariaLabel": "Watch statistics",
1588
+ "completion": {
1589
+ "detail": "{{finished}} of {{total}} finished every episode",
1590
+ "detailMovie": "{{finished}} of {{total}} watched to completion",
1591
+ "label": "Avg completion"
1592
+ },
1593
+ "completionLoadError": "Couldn't load completion",
1594
+ "loadError": "Couldn't load watch statistics",
1595
+ "plays": {
1596
+ "caption": "resume chains, short sessions excluded",
1597
+ "label": "Plays, all time"
1598
+ },
1599
+ "viewers": {
1600
+ "detail": "across all servers",
1601
+ "label": "Viewers"
1602
+ },
1603
+ "watchTime": {
1604
+ "detail": "+{{hours}}h in the last 30 days",
1605
+ "label": "Watch time"
1606
+ }
1607
+ },
1608
+ "notFound": {
1609
+ "backLink": "Back to Media",
1610
+ "message": "This title doesn't exist or you don't have access to it.",
1611
+ "title": "Media not found"
1612
+ },
1613
+ "platforms": {
1614
+ "columns": {
1615
+ "platform": "Platform",
1616
+ "plays": "Plays",
1617
+ "watchTime": "Watch time"
1618
+ },
1619
+ "empty": "No platform data yet",
1620
+ "loadError": "Couldn't load platform breakdown",
1621
+ "title": "Platforms",
1622
+ "unknown": "Unknown"
1623
+ },
1624
+ "seasons": {
1625
+ "empty": "No season data yet",
1626
+ "episodeCount_one": "{{count}} episode",
1627
+ "episodeCount_other": "{{count}} episodes",
1628
+ "episodeLabel": {
1629
+ "partial": "{{code}}: partially watched",
1630
+ "unwatched": "{{code}}: unwatched",
1631
+ "watched": "{{code}}: watched"
1632
+ },
1633
+ "loadError": "Couldn't load season data",
1634
+ "stripSummary": "{{season}}: {{percent}}% watched",
1635
+ "title": "Seasons",
1636
+ "watchedPct": "{{percent}}% watched"
1637
+ },
1638
+ "title": "Media Details",
1639
+ "watchers": {
1640
+ "columns": {
1641
+ "completion": "Completion",
1642
+ "episodes": "Episodes",
1643
+ "lastWatched": "Last watched",
1644
+ "plays": "Plays",
1645
+ "user": "User"
1646
+ },
1647
+ "completionLabel": "{{percent}}% complete",
1648
+ "empty": "No one has watched this yet.",
1649
+ "lastWatchedAgo": "{{age}} ago",
1650
+ "loadError": "Couldn't load watchers",
1651
+ "title": "Watchers"
1652
+ }
1653
+ },
1654
+ "genres": {
1655
+ "chart": {
1656
+ "ariaLabel": "Bar chart of plays by genre, sorted highest to lowest. The full breakdown is available in the table below.",
1657
+ "itemCount_one": "{{count}} title",
1658
+ "itemCount_other": "{{count}} titles",
1659
+ "title": "Plays by genre",
1660
+ "valueLabel": "Plays"
1661
+ },
1662
+ "empty": {
1663
+ "description": "Genres come from your media servers' metadata sync. Check back after the next sync completes.",
1664
+ "title": "No genres captured yet"
1665
+ },
1666
+ "loadError": "Couldn't load genres",
1667
+ "subtitle": "Plays and watch time by genre, across every server in view.",
1668
+ "table": {
1669
+ "browseMovies": "Browse {{genre}} movies",
1670
+ "browseShows": "Browse {{genre}} shows",
1671
+ "columns": {
1672
+ "genre": "Genre",
1673
+ "items": "Items",
1674
+ "plays": "Plays",
1675
+ "watchTime": "Watch time"
1676
+ },
1677
+ "title": "Genre breakdown"
1678
+ },
1679
+ "title": "Genres"
1680
+ },
1681
+ "grid": {
1682
+ "clearJumpAction": "Clear",
1683
+ "emptyAnchored": "Nothing at or after \"{{letter}}\" under these filters",
1684
+ "emptyFilter": "No titles match these filters",
1685
+ "emptySearch": "No titles match \"{{query}}\"",
1686
+ "loadError": "Couldn't load the catalog",
1687
+ "loaderError": "Couldn't load more titles",
1688
+ "retry": "Retry",
1689
+ "scrubber": {
1690
+ "current": "Letter {{letter}}",
1691
+ "label": "Jump to letter"
1692
+ },
1693
+ "showAll": "Show all",
1694
+ "showingFrom": "Showing from {{letter}}",
1695
+ "toolbar": {
1696
+ "ariaLabel": "Filters and sort",
1697
+ "count": "{{loaded}} of {{total}} titles · {{size}}",
1698
+ "countTotal_one": "{{count}} title · {{size}}",
1699
+ "countTotal_other": "{{count}} titles · {{size}}",
1700
+ "done": "Done",
1701
+ "filtersLabel": "Filters",
1702
+ "filtersSheetTitle": "Filters",
1703
+ "genreAll": "Any genre",
1704
+ "genreLabel": "Genre",
1705
+ "hdrAll": "Any",
1706
+ "hdrChip": "HDR",
1707
+ "hdrLabel": "Dynamic range",
1708
+ "hdrOnly": "HDR only",
1709
+ "libraryAll": "Any library",
1710
+ "libraryLabel": "Library",
1711
+ "moviesToggle": "Movies",
1712
+ "removeFilter": "Remove {{label}} filter",
1713
+ "resolutionAll": "Any resolution",
1714
+ "resolutionLabel": "Resolution",
1715
+ "searchLabel": "Search titles",
1716
+ "searchPlaceholder": "Search titles…",
1717
+ "serverAll": "Any server",
1718
+ "serverLabel": "Server",
1719
+ "showsToggle": "Shows",
1720
+ "sizeChipAtLeast": "≥ {{min}} GB",
1721
+ "sizeChipAtMost": "≤ {{max}} GB",
1722
+ "sizeChipRange": "{{min}}–{{max}} GB",
1723
+ "sizeGbMaxLabel": "Max size (GB)",
1724
+ "sizeGbMinLabel": "Min size (GB)",
1725
+ "sort": {
1726
+ "added": "Recently added",
1727
+ "plays": "Plays",
1728
+ "title": "Title A–Z",
1729
+ "viewers": "Viewers",
1730
+ "watch_time": "Watch time",
1731
+ "year": "Year"
1732
+ },
1733
+ "sortLabel": "Sort",
1734
+ "typeLabel": "Media type",
1735
+ "unwatchedByLens": "Unwatched by {{name}}",
1736
+ "watched": {
1737
+ "all": "All",
1738
+ "partial": "Partially watched",
1739
+ "unwatched": "Unwatched",
1740
+ "watched": "Watched"
1741
+ },
1742
+ "watchedLabel": "Watched",
1743
+ "yearFromLabel": "From year",
1744
+ "yearToLabel": "To year"
1745
+ }
1746
+ },
1747
+ "landing": {
1748
+ "card": {
1749
+ "addedAgo": "added {{date}}",
1750
+ "addedCompactAgo": "added {{age}} ago",
1751
+ "newEpisodesChip": "{{count}} new",
1752
+ "newEpisodes_one": "{{count}} new episode",
1753
+ "newEpisodes_other": "{{count}} new episodes"
1754
+ },
1755
+ "deadWeight": {
1756
+ "columns": {
1757
+ "added": "Added",
1758
+ "poster": "Poster",
1759
+ "servers": "Servers",
1760
+ "size": "Size",
1761
+ "title": "Title"
1762
+ },
1763
+ "empty": "Nothing to reclaim - everything in your library has been watched",
1764
+ "summary": "{{count}} never-watched titles · {{size}}",
1765
+ "title": "Dead Weight",
1766
+ "viewAll": "View all",
1767
+ "viewAllTooltip": "Coming soon"
1768
+ },
1769
+ "lens": {
1770
+ "allUsers": "All users",
1771
+ "label": "Viewing as"
1772
+ },
1773
+ "loadError": "Couldn't load your media library",
1774
+ "shelves": {
1775
+ "captionMostPopular": {
1776
+ "all": "all time",
1777
+ "custom": "selected date range",
1778
+ "day": "today",
1779
+ "month": "last 30 days",
1780
+ "week": "last 7 days",
1781
+ "year": "last 12 months"
1782
+ },
1783
+ "captionRecentlyAdded": "deduped across servers",
1784
+ "emptyMostPopular": "No plays in this period",
1785
+ "emptyRecentlyAdded": "Nothing added in this period",
1786
+ "mostPopularMovies": "Most Popular Movies",
1787
+ "mostPopularShows": "Most Popular Shows",
1788
+ "recentlyAddedMovies": "Recently Added Movies",
1789
+ "recentlyAddedShows": "Recently Added Shows"
1790
+ },
1791
+ "title": "Media"
1792
+ },
1793
+ "movies": {
1794
+ "title": "Movies"
1795
+ },
1796
+ "posterCard": {
1797
+ "addedLabel": "Added {{date}}",
1798
+ "moreServers": "+{{count}} more",
1799
+ "onServers": "On {{servers}}",
1800
+ "playsCompact_one": "{{compact}} play",
1801
+ "playsCompact_other": "{{compact}} plays",
1802
+ "plays_one": "{{count}} play",
1803
+ "plays_other": "{{count}} plays",
1804
+ "rankChip": "#{{rank}}",
1805
+ "rankSuffix": ", rank {{rank}}",
1806
+ "tileLabel": {
1988
1807
  "added": "added",
1989
1808
  "plays": "plays",
1990
- "viewers": "viewers",
1991
- "resolution": "resolution"
1809
+ "resolution": "resolution",
1810
+ "viewers": "viewers"
1811
+ },
1812
+ "versionsChip": "{{count}}×",
1813
+ "versions_one": "{{count}} version",
1814
+ "versions_other": "{{count}} versions",
1815
+ "viewers_one": "{{count}} viewer",
1816
+ "viewers_other": "{{count}} viewers",
1817
+ "watchedState": {
1818
+ "partial": "Partially watched",
1819
+ "watched": "Watched",
1820
+ "watchedByOthers": "Watched by others",
1821
+ "watchedByYou": "Watched by you"
1822
+ }
1823
+ },
1824
+ "shows": {
1825
+ "title": "Shows"
1826
+ }
1827
+ },
1828
+ "notFound": {
1829
+ "description": "The page you're looking for doesn't exist or has been moved.",
1830
+ "heading": "Page Not Found",
1831
+ "title": "404"
1832
+ },
1833
+ "plexCallback": {
1834
+ "authComplete": "Authentication complete",
1835
+ "windowWillClose": "This window will close automatically..."
1836
+ },
1837
+ "settings": {
1838
+ "destinations": {
1839
+ "add": "Add destination",
1840
+ "alertsGoTo": "",
1841
+ "alertsGoTo_other": "",
1842
+ "builtinNote": "Built in",
1843
+ "clearSecret": "Clear",
1844
+ "delete": "Delete",
1845
+ "deleteConfirm": "Delete {{name}}? Rules that send to it will be blocked until they are updated.",
1846
+ "description": "Where notifications go. Add as many as you like, and automations can send to any of them.",
1847
+ "emailDescription": "",
1848
+ "empty": "No destinations yet.",
1849
+ "fields": {
1850
+ "apiToken": "API token",
1851
+ "apiUrl": "API URL",
1852
+ "authToken": "Auth token",
1853
+ "fromAddress": "From address",
1854
+ "fromName": "From name",
1855
+ "host": "SMTP host",
1856
+ "messageStream": "",
1857
+ "messagesPerSecond": "Messages per second",
1858
+ "password": "Password",
1859
+ "port": "Port",
1860
+ "preset": "Provider",
1861
+ "replyTo": "Reply-to",
1862
+ "security": "Security",
1863
+ "serverUrl": "Server URL",
1864
+ "to": "Recipients",
1865
+ "topic": "Topic",
1866
+ "url": "URL",
1867
+ "userKey": "User key",
1868
+ "username": "Username",
1869
+ "webhookUrl": "Webhook URL"
1870
+ },
1871
+ "groups": {
1872
+ "alerts": "",
1873
+ "connection": "",
1874
+ "sender": ""
1875
+ },
1876
+ "hints": {
1877
+ "authTokenOptional": "Optional for public topics",
1878
+ "smtpBrevoPassword": "",
1879
+ "smtpBrevoUsername": "",
1880
+ "smtpGmailPassword": "",
1881
+ "smtpGmailUsername": "",
1882
+ "smtpMailgunPassword": "",
1883
+ "smtpMailgunUsername": "",
1884
+ "smtpMessageStream": "",
1885
+ "smtpPostmarkPassword": "",
1886
+ "smtpPostmarkUsername": "",
1887
+ "smtpPreset": "Fills the host, port and security for common providers. Amazon SES and Mailgun EU need the region edited into the host.",
1888
+ "smtpRate": "Per Tracearr instance; stay under your provider's limit",
1889
+ "smtpResendPassword": "",
1890
+ "smtpResendUsername": "",
1891
+ "smtpSendgridPassword": "",
1892
+ "smtpSendgridUsername": "",
1893
+ "smtpSesPassword": "",
1894
+ "smtpSesUsername": "",
1895
+ "smtpTo": "Comma-separated addresses that receive alerts from this destination",
1896
+ "smtpUsernameOptional": "Leave blank when the server needs no login"
1897
+ },
1898
+ "newslettersOnly": "",
1899
+ "noAlertRecipients": "",
1900
+ "options": {
1901
+ "presetBrevo": "Brevo",
1902
+ "presetCustom": "Custom",
1903
+ "presetGmail": "Gmail",
1904
+ "presetMailgun": "Mailgun",
1905
+ "presetPostmark": "Postmark",
1906
+ "presetResend": "Resend",
1907
+ "presetSendgrid": "SendGrid",
1908
+ "presetSes": "Amazon SES",
1909
+ "securityNone": "None (plain text, port 25)",
1910
+ "securityStarttls": "STARTTLS (usually port 587)",
1911
+ "securityTls": "TLS (usually port 465)"
1912
+ },
1913
+ "ownerOnly": "Only the owner can manage notification destinations.",
1914
+ "pushNote": "Delivered to paired mobile devices; each device filters in its own notification settings.",
1915
+ "receiveViolations": "Receive violations",
1916
+ "receiveViolationsHint": "",
1917
+ "receiveViolationsNeedsRecipients": "",
1918
+ "reencrypt": "Re-enter this destination's secret",
1919
+ "rowActions": "",
1920
+ "secretSet": "Set (leave blank to keep)",
1921
+ "test": "Test",
1922
+ "testHint": "Save first to test",
1923
+ "testNeedsForm": "Fill in the required fields to test",
1924
+ "types": {
1925
+ "apprise": "Apprise",
1926
+ "discord": "Discord",
1927
+ "email": "Email",
1928
+ "gotify": "Gotify",
1929
+ "jsonWebhook": "Webhook (JSON)",
1930
+ "ntfy": "ntfy",
1931
+ "push": "Mobile push",
1932
+ "pushover": "Pushover",
1933
+ "webToast": "Browser toasts"
1992
1934
  },
1993
- "rankChip": "#{{rank}}",
1994
- "playsCompact_one": "{{compact}} play",
1995
- "playsCompact_other": "{{compact}} plays",
1996
- "versionsChip": "{{count}}×",
1997
- "versions_one": "{{count}} version",
1998
- "versions_other": "{{count}} versions",
1999
- "moreServers": "+{{count}} more"
1935
+ "usedBy": "Used by {{count}} rule",
1936
+ "usedByNewsletters": "",
1937
+ "usedByNewsletters_other": "",
1938
+ "usedBy_other": "Used by {{count}} rules",
1939
+ "violationsOff": "",
1940
+ "violationsOn": "",
1941
+ "webToastNote": "Toasts in this browser."
2000
1942
  },
2001
- "grid": {
2002
- "toolbar": {
2003
- "ariaLabel": "Filters and sort",
2004
- "typeLabel": "Media type",
2005
- "moviesToggle": "Movies",
2006
- "showsToggle": "Shows",
2007
- "searchPlaceholder": "Search titles…",
2008
- "searchLabel": "Search titles",
2009
- "removeFilter": "Remove {{label}} filter",
2010
- "filtersLabel": "Filters",
2011
- "filtersSheetTitle": "Filters",
2012
- "done": "Done",
2013
- "watchedLabel": "Watched",
2014
- "watched": {
2015
- "all": "All",
2016
- "watched": "Watched",
2017
- "partial": "Partially watched",
2018
- "unwatched": "Unwatched"
2019
- },
2020
- "unwatchedByLens": "Unwatched by {{name}}",
2021
- "resolutionLabel": "Resolution",
2022
- "resolutionAll": "Any resolution",
2023
- "hdrLabel": "Dynamic range",
2024
- "hdrAll": "Any",
2025
- "hdrOnly": "HDR only",
2026
- "hdrChip": "HDR",
2027
- "genreLabel": "Genre",
2028
- "genreAll": "Any genre",
2029
- "serverLabel": "Server",
2030
- "serverAll": "Any server",
2031
- "libraryLabel": "Library",
2032
- "libraryAll": "Any library",
2033
- "yearFromLabel": "From year",
2034
- "yearToLabel": "To year",
2035
- "sizeGbMinLabel": "Min size (GB)",
2036
- "sizeGbMaxLabel": "Max size (GB)",
2037
- "sizeChipAtLeast": "≥ {{min}} GB",
2038
- "sizeChipAtMost": "≤ {{max}} GB",
2039
- "sizeChipRange": "{{min}}–{{max}} GB",
2040
- "sortLabel": "Sort",
2041
- "sort": {
2042
- "title": "Title A–Z",
2043
- "added": "Recently added",
2044
- "year": "Year",
2045
- "plays": "Plays",
2046
- "watch_time": "Watch time",
2047
- "viewers": "Viewers"
2048
- },
2049
- "count": "{{loaded}} of {{total}} titles · {{size}}",
2050
- "countTotal_one": "{{count}} title · {{size}}",
2051
- "countTotal_other": "{{count}} titles · {{size}}"
2052
- },
2053
- "scrubber": {
2054
- "label": "Jump to letter",
2055
- "current": "Letter {{letter}}"
1943
+ "jobs": {
1944
+ "lastRun": "Last run",
1945
+ "nextRun": "Next run",
1946
+ "runNow": "Run Now",
1947
+ "running": "Running...",
1948
+ "schedule": "Schedule"
1949
+ },
1950
+ "mobile": {
1951
+ "displayName": "Display Name",
1952
+ "displayNamePlaceholder": "e.g., My iPhone",
1953
+ "editDisplayName": "Edit Display Name",
1954
+ "editDisplayNameDesc": "Change how this device appears in your device list",
1955
+ "updating": "Updating..."
1956
+ },
1957
+ "plex": {
1958
+ "connectingTo": "Connecting to {{name}}...",
1959
+ "connectionError": {
1960
+ "dns": "DNS error",
1961
+ "http": "HTTP {{status}}",
1962
+ "refused": "Connection refused",
1963
+ "reset": "Connection reset",
1964
+ "timeout": "Timed out",
1965
+ "tls": "TLS error",
1966
+ "unknown": "Connection failed",
1967
+ "unreachable": "Host unreachable"
2056
1968
  },
2057
- "loaderError": "Couldn't load more titles",
2058
- "retry": "Retry",
2059
- "clearJumpAction": "Clear",
2060
- "showingFrom": "Showing from {{letter}}",
1969
+ "connectionsAvailable": "{{count}} connections available",
1970
+ "connectionsReachable": "{{reachable}} of {{total}} connections reachable",
1971
+ "custom": "Custom",
1972
+ "customUrl": "Custom URL",
1973
+ "deleteServersFirst": "Delete connected servers first to unlink this account",
1974
+ "hideFiltered": "Hide filtered",
1975
+ "linkAnotherAccount": "Link Another Plex Account",
1976
+ "linkPlexAccount": "Link Plex Account",
1977
+ "linking": "Linking...",
1978
+ "local": "Local",
1979
+ "loginEnabled": "Login Enabled",
1980
+ "mayNotConnect": "May not connect",
1981
+ "moreConnections": "+{{count}} more connections",
1982
+ "noAccountsLinked": "No Plex Accounts Linked",
1983
+ "noAccountsLinkedHint": "Link a Plex account to add Plex servers to Tracearr.",
1984
+ "noReachableConnections": "No reachable connections",
1985
+ "noServersFound": "No Plex servers found",
1986
+ "noServersFoundHint": "Make sure you own at least one Plex server",
1987
+ "ownerOnly": "",
1988
+ "reauthorizeAccount": "Reauthorize this Plex account",
1989
+ "recommended": "Recommended",
1990
+ "remote": "Remote",
1991
+ "secure": "Secure",
1992
+ "serversConnected_one": "{{count}} server connected",
1993
+ "serversConnected_other": "{{count}} servers connected",
2061
1994
  "showAll": "Show all",
2062
- "emptyFilter": "No titles match these filters",
2063
- "emptySearch": "No titles match \"{{query}}\"",
2064
- "emptyAnchored": "Nothing at or after \"{{letter}}\" under these filters",
2065
- "loadError": "Couldn't load the catalog"
1995
+ "unlinkAccount": "Unlink this Plex account",
1996
+ "unlinkConfirm": "Are you sure you want to unlink this Plex account? You won't be able to add servers from this account until you link it again.",
1997
+ "unlinkPlexAccount": "Unlink Plex Account"
2066
1998
  }
1999
+ },
2000
+ "statsBandwidth": {
2001
+ "avgBitrate": "Avg Bitrate",
2002
+ "avgBitrateMbps": "Avg Bitrate (Mbps)",
2003
+ "dailyUsage": "Daily Bandwidth Usage",
2004
+ "dailyUsageDesc": "Average bitrate and session count over time",
2005
+ "dataTransferred": "Data Transferred",
2006
+ "description": "Streaming bandwidth usage and bitrate analysis",
2007
+ "noData": "No bandwidth data available",
2008
+ "peakBitrate": "Peak: {{value}} Mbps",
2009
+ "title": "Bandwidth",
2010
+ "topUsers": "Top Bandwidth Users",
2011
+ "topUsersDesc": "Users consuming the most bandwidth",
2012
+ "totalWatchTime": "Total Watch Time",
2013
+ "uniqueUsers": "Unique Users"
2014
+ },
2015
+ "statsUsers": {
2016
+ "noActivity": "No activity yet",
2017
+ "noActivityDesc": "",
2018
+ "runnersUp": "Runners Up",
2019
+ "top3": "Top 3"
2020
+ },
2021
+ "terminateStream": {
2022
+ "killStream": "Kill Stream",
2023
+ "messageHint": "This message will be shown to them during playback",
2024
+ "messageLabel": "Message to user (optional)",
2025
+ "messagePlaceholder": "e.g., Please don't share your account",
2026
+ "stopMedia": "Stop \"{{mediaTitle}}\" for @{{username}}?",
2027
+ "terminating": "Terminating...",
2028
+ "title": "Terminate Stream"
2029
+ },
2030
+ "userDetail": {
2031
+ "acrossAllServers": "Across all linked accounts:",
2032
+ "adjustTrustScore": "Adjust Trust Score",
2033
+ "allServers": "All servers",
2034
+ "backToUsers": "Back to Users",
2035
+ "byRule": "By / Rule",
2036
+ "contactEmail": "",
2037
+ "contactEmailHelp": "",
2038
+ "contactEmailLabel": "",
2039
+ "contactEmailNoLogin": "",
2040
+ "contactEmailNone": "",
2041
+ "displayName": "",
2042
+ "editIdentity": "",
2043
+ "editIdentityDescription": "",
2044
+ "linkedAccounts": "Linked accounts",
2045
+ "manual": "Manual",
2046
+ "noTerminationsFound": "No stream terminations for this user.",
2047
+ "noViolationsFound": "No violations for this user.",
2048
+ "overallTrust": "Overall Trust",
2049
+ "serverScope": "Server",
2050
+ "sessions": "Sessions",
2051
+ "splitAccount": "Split into separate user",
2052
+ "splitConfirmDescription": "Detach this server account into its own user. Its watch history and violations move with it.",
2053
+ "splitConfirmLoading": "Splitting...",
2054
+ "splitConfirmTitle": "Split server account",
2055
+ "statistics": "Statistics",
2056
+ "terminationHistory": "Termination History",
2057
+ "title": "User Details",
2058
+ "unknownRule": "Unknown rule",
2059
+ "userInfo": "User Info",
2060
+ "userNotFound": "User not found",
2061
+ "violations": "Violations"
2062
+ },
2063
+ "users": {
2064
+ "filterHasAccessTo": "Has access to",
2065
+ "filterHasAccessToHint": "Shows people with an active account on every server selected.",
2066
+ "filterHasAccessToPlaceholder": "Any server",
2067
+ "mergeConfirm": "Merge",
2068
+ "mergeDialogDescription": "Every server account, session, and violation from the duplicate moves to the primary. The duplicate identity is deleted.",
2069
+ "mergeDialogTitle": "Merge users",
2070
+ "mergePickPrimary": "Choose the primary identity",
2071
+ "mergePrimaryBadge": "Primary",
2072
+ "mergePrimaryForced": "This account can log in, so it must stay the primary.",
2073
+ "mergeSameIdentity": "These accounts already belong to the same user",
2074
+ "mergeSameServerAcknowledge": "I understand the same-server history combine cannot be undone",
2075
+ "mergeSameServerDialogDescription": "This merge permanently combines both accounts on the same server. It cannot be undone.",
2076
+ "mergeSameServerFallbackName": "this server",
2077
+ "mergeSameServerWarning": "Both identities already have an account on the same server. Merging will permanently combine their session history, violations, and trust score into a single account on that server. This cannot be undone, and splitting the account afterward will not restore the original two accounts.",
2078
+ "mergeSameServerWarningTitle": "This action is irreversible",
2079
+ "mergeSelectAllActive": "Clear the select-all selection and pick exactly two users to merge",
2080
+ "mergeSelectTwo": "Select exactly two users to merge",
2081
+ "mergeServerAccountRemoved": "Removed",
2082
+ "mergeUsers": "Merge users",
2083
+ "noUsersFound": "No users found.",
2084
+ "resetTrustScore": "Reset Trust Score",
2085
+ "resetTrustScoreConfirm": "Are you sure you want to reset the trust score to 100? This action cannot be undone.",
2086
+ "resetTrustScoreTitle_one": "Reset Trust Score for {{count}} User",
2087
+ "resetTrustScoreTitle_other": "Reset Trust Score for {{count}} Users",
2088
+ "searchPlaceholder": "Search users...",
2089
+ "selectAllUsers": "Select all {{count}} users",
2090
+ "serversColumn": "Servers",
2091
+ "showRemoved": "Show removed",
2092
+ "suggestionsDescription": "These identities look like the same person across servers. Review and merge them if they match.",
2093
+ "suggestionsError": "Could not load merge suggestions",
2094
+ "suggestionsMatchEmail": "Same email",
2095
+ "suggestionsMatchUsername": "Same username",
2096
+ "suggestionsReview": "Review",
2097
+ "suggestionsTitle": "Possible duplicate users",
2098
+ "title": "Users"
2099
+ },
2100
+ "violations": {
2101
+ "allPeople": "All people",
2102
+ "allRules": "All rules",
2103
+ "allSeverities": "All Severities",
2104
+ "allStatuses": "All Statuses",
2105
+ "detail": {
2106
+ "acknowledged": "Acknowledged",
2107
+ "actions": "Actions Taken",
2108
+ "actual": "Actual",
2109
+ "conditionEvidence": "Condition Evidence",
2110
+ "conditionGroup": "Condition Group {{index}}",
2111
+ "created": "Created",
2112
+ "daysInactive": "Days Inactive",
2113
+ "detected": "Detected",
2114
+ "inactivity": "Inactivity Details",
2115
+ "lastActivity": "Last Activity",
2116
+ "map": "Session Locations",
2117
+ "matched": "{{matched}}/{{total}} matched",
2118
+ "neverActive": "Never active",
2119
+ "noSessions": "No sessions associated with this violation",
2120
+ "notFound": "Violation not found",
2121
+ "relatedSessions": "{{count}} related session",
2122
+ "relatedSessions_one": "{{count}} related session",
2123
+ "relatedSessions_other": "{{count}} related sessions",
2124
+ "sessions": "Sessions",
2125
+ "threshold": "Threshold",
2126
+ "timestamps": "Timestamps",
2127
+ "trigger": "Trigger",
2128
+ "userInfo": "User",
2129
+ "violationDetails": "Violation Details"
2130
+ },
2131
+ "dismissViolation": "Dismiss Violation",
2132
+ "dismissViolationConfirm": "Are you sure you want to dismiss this violation? This will remove it from the violation log permanently.",
2133
+ "dismissViolation_one": "Dismiss {{count}} Violation",
2134
+ "dismissViolation_other": "Dismiss {{count}} Violations",
2135
+ "dismissViolationsConfirm": "Are you sure you want to dismiss? This will remove them from the violation log permanently and restore associated trust scores.",
2136
+ "filterByPerson": "Filter violations by this person",
2137
+ "filterPeople": "People",
2138
+ "noViolationsFound": "No violations found",
2139
+ "noViolationsRecorded": "No violations have been recorded yet.",
2140
+ "peopleSelectedCount": "{{count}} people",
2141
+ "personFilterEmpty": "No matching people found",
2142
+ "personFilterError": "Failed to load people",
2143
+ "personFilterPlaceholder": "Filter by person",
2144
+ "selectAllViolations": "Select all {{count}} violations matching filters",
2145
+ "title": "Violations",
2146
+ "tryAdjustingFilters": "Try adjusting your filters"
2067
2147
  }
2068
2148
  }