mirror of
https://github.com/Eugeny/tabby.git
synced 2025-09-10 02:21:50 +00:00
Compare commits
119 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
0f01aaf44d | ||
![]() |
54531e234e | ||
![]() |
3bda4a9871 | ||
![]() |
c7e3ab42d9 | ||
![]() |
5d2956568e | ||
![]() |
8b3f482682 | ||
![]() |
f38f9882f8 | ||
![]() |
54d71adb26 | ||
![]() |
13eebd8957 | ||
![]() |
6c4f8d2611 | ||
![]() |
897bc77d05 | ||
![]() |
8b5b53ab26 | ||
![]() |
448fe29f50 | ||
![]() |
70ae9f875f | ||
![]() |
75764cd725 | ||
![]() |
5ae2d17cc8 | ||
![]() |
109a83db5b | ||
![]() |
9fe8d2a7df | ||
![]() |
d3bbd045dc | ||
![]() |
eb0fa29fad | ||
![]() |
6289229bf2 | ||
![]() |
b664b9eed9 | ||
![]() |
2569f9e322 | ||
![]() |
95152456ce | ||
![]() |
918761bbdc | ||
![]() |
ceb1b59409 | ||
![]() |
63374f532c | ||
![]() |
c57fe48e73 | ||
![]() |
02a3a8200b | ||
![]() |
3e8e3f7ccd | ||
![]() |
1ec218775e | ||
![]() |
cc8c200da0 | ||
![]() |
0a20716efd | ||
![]() |
9893fb51a7 | ||
![]() |
3466d42cb1 | ||
![]() |
9e9066d3cd | ||
![]() |
b469dd603b | ||
![]() |
f6eaff355b | ||
![]() |
7ff2b31a9f | ||
![]() |
dbf67e77e0 | ||
![]() |
b45769d379 | ||
![]() |
1695c0b522 | ||
![]() |
15d7be05f1 | ||
![]() |
a759c40ec8 | ||
![]() |
a8e977d34c | ||
![]() |
527a951b1e | ||
![]() |
afe9c9a84c | ||
![]() |
372662c787 | ||
![]() |
ca9e6a118e | ||
![]() |
b412bce37d | ||
![]() |
6622cbc550 | ||
![]() |
d3361b6f34 | ||
![]() |
13f715ddfd | ||
![]() |
ccea3572a7 | ||
![]() |
c24c752b76 | ||
![]() |
8751b9831f | ||
![]() |
d4d93cf236 | ||
![]() |
9b305026f7 | ||
![]() |
91fcdbf9b5 | ||
![]() |
b17e23a69e | ||
![]() |
88bbdd0da1 | ||
![]() |
53cbb8a7e3 | ||
![]() |
9df8a1b904 | ||
![]() |
0a0e451e97 | ||
![]() |
5376ac0f07 | ||
![]() |
238482932e | ||
![]() |
d4332ea361 | ||
![]() |
eb49499f09 | ||
![]() |
445a3d02da | ||
![]() |
06e5571812 | ||
![]() |
510edaabb5 | ||
![]() |
5ef36896c5 | ||
![]() |
5d22c15a78 | ||
![]() |
a33e11502b | ||
![]() |
4c9456d98d | ||
![]() |
e1ee818932 | ||
![]() |
e83210f0e6 | ||
![]() |
1d176047c4 | ||
![]() |
bd3ac21fb3 | ||
![]() |
559dd3955c | ||
![]() |
0ed05cb783 | ||
![]() |
87e8eefd49 | ||
![]() |
609b527a7c | ||
![]() |
fee163835f | ||
![]() |
c8b25cf911 | ||
![]() |
eb9698fa66 | ||
![]() |
eb60c3c3c6 | ||
![]() |
f2a48fc0c0 | ||
![]() |
8d01a9ad8d | ||
![]() |
4d8ddba8ea | ||
![]() |
91a7dd8b1d | ||
![]() |
38423eb139 | ||
![]() |
bde6fd6231 | ||
![]() |
14200f848f | ||
![]() |
f6895d7696 | ||
![]() |
64410a9302 | ||
![]() |
45274f9691 | ||
![]() |
54ab2a1f03 | ||
![]() |
782128308c | ||
![]() |
f2b6cdf97c | ||
![]() |
c025c44258 | ||
![]() |
9483d20994 | ||
![]() |
ff25e7fe2e | ||
![]() |
d12a48f3fc | ||
![]() |
1796ce4f1c | ||
![]() |
d404067e77 | ||
![]() |
f7544d0a2e | ||
![]() |
cbdce5c30e | ||
![]() |
d7ab8a00dc | ||
![]() |
6e0ded9a5e | ||
![]() |
f660ece383 | ||
![]() |
b692347c4e | ||
![]() |
9520d31f12 | ||
![]() |
7c0aacf0ad | ||
![]() |
9414be9ce0 | ||
![]() |
f2ed1b3df3 | ||
![]() |
f41abea747 | ||
![]() |
00ffa24e7d | ||
![]() |
b156752106 |
@@ -1,6 +1,9 @@
|
||||
{
|
||||
"files": [
|
||||
"README.md"
|
||||
"README.md",
|
||||
"README.zh-CN.md",
|
||||
"README.ru-RU.md",
|
||||
"README.ko-KR.md"
|
||||
],
|
||||
"imageSize": 100,
|
||||
"commit": false,
|
||||
@@ -559,6 +562,43 @@
|
||||
"contributions": [
|
||||
"financial"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "boonkerz",
|
||||
"name": "boonkerz",
|
||||
"avatar_url": "https://avatars.githubusercontent.com/u/277321?v=4",
|
||||
"profile": "https://github.com/boonkerz",
|
||||
"contributions": [
|
||||
"code",
|
||||
"translation"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "milotype",
|
||||
"name": "Milo Ivir",
|
||||
"avatar_url": "https://avatars.githubusercontent.com/u/43657314?v=4",
|
||||
"profile": "https://github.com/milotype",
|
||||
"contributions": [
|
||||
"translation"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "JasonCubic",
|
||||
"name": "JasonCubic",
|
||||
"avatar_url": "https://avatars.githubusercontent.com/u/8921015?v=4",
|
||||
"profile": "https://github.com/JasonCubic",
|
||||
"contributions": [
|
||||
"design"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "MaxWaldorf",
|
||||
"name": "MaxWaldorf",
|
||||
"avatar_url": "https://avatars.githubusercontent.com/u/15877853?v=4",
|
||||
"profile": "https://github.com/MaxWaldorf",
|
||||
"contributions": [
|
||||
"infra"
|
||||
]
|
||||
}
|
||||
],
|
||||
"contributorsPerLine": 7,
|
||||
|
7
.github/ISSUE_TEMPLATE/feature_request.md
vendored
7
.github/ISSUE_TEMPLATE/feature_request.md
vendored
@@ -7,6 +7,13 @@ assignees: ''
|
||||
|
||||
---
|
||||
|
||||
<!--
|
||||
# RULES:
|
||||
|
||||
* **ENGLISH ONLY** - this issue tracker is English-only. Please respect the people who take time to help you with your problems.
|
||||
* Search existing issues first: https://github.com/Eugeny/tabby/issues
|
||||
-->
|
||||
|
||||
**Is your feature request related to a problem? Please describe.**
|
||||
A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
|
||||
|
||||
|
10
.github/ISSUE_TEMPLATE/issue-report.md
vendored
10
.github/ISSUE_TEMPLATE/issue-report.md
vendored
@@ -8,12 +8,12 @@ assignees: ''
|
||||
---
|
||||
|
||||
<!--
|
||||
Before submitting an issue, make sure that:
|
||||
* You're running the latest Tabby version: https://github.com/Eugeny/tabby/releases
|
||||
* You've searched the existing issues: https://github.com/Eugeny/tabby/issues
|
||||
* Your problem is not caused by third-party plugins (disable _third-party_ plugins, restart and try to reproduce the problem).
|
||||
# READ CAREFULLY:
|
||||
|
||||
*Reports are accepted in English ONLY.*
|
||||
* **ENGLISH ONLY** - this issue tracker is English-only. Please respect the people who take time to help you with your problems.
|
||||
* Search existing issues first: https://github.com/Eugeny/tabby/issues
|
||||
* Test with the latest Tabby version: https://github.com/Eugeny/tabby/releases
|
||||
* Disable third-party plugins.
|
||||
-->
|
||||
|
||||
**Describe the problem**:
|
||||
|
15
.github/workflows/issue-translator.yml
vendored
Normal file
15
.github/workflows/issue-translator.yml
vendored
Normal file
@@ -0,0 +1,15 @@
|
||||
name: 'issue-translator'
|
||||
on:
|
||||
issue_comment:
|
||||
types: [created]
|
||||
issues:
|
||||
types: [opened]
|
||||
|
||||
jobs:
|
||||
build:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: tomsun28/issues-translate-action@v2.6
|
||||
with:
|
||||
IS_MODIFY_TITLE: true
|
||||
CUSTOM_BOT_NOTE: The translator bot has detected that this issue body's language is not English, and has translated it automatically.
|
@@ -204,6 +204,29 @@ Pull requests and plugins are welcome!
|
||||
<td align="center"><a href="https://github.com/cypherbits"><img src="https://avatars.githubusercontent.com/u/10424900?v=4?s=100" width="100px;" alt=""/><br /><sub><b>cypherbits</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=cypherbits" title="Documentation">📖</a></td>
|
||||
<td align="center"><a href="https://modulolotus.net"><img src="https://avatars.githubusercontent.com/u/946421?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Matthew Davidson</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=KingMob" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/al-wi"><img src="https://avatars.githubusercontent.com/u/11092199?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Alexander Wiedemann</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=al-wi" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://www.notion.so/3d45c6bd2cbd4f938873a4bd12e23375"><img src="https://avatars.githubusercontent.com/u/59506394?v=4?s=100" width="100px;" alt=""/><br /><sub><b>장보연</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=BoYeonJang" title="Documentation">📖</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/Me1onRind"><img src="https://avatars.githubusercontent.com/u/19531270?v=4?s=100" width="100px;" alt=""/><br /><sub><b>zZ</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=Me1onRind" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/tainoNZ"><img src="https://avatars.githubusercontent.com/u/49261322?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Aaron Davison</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=tainoNZ" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/composer404"><img src="https://avatars.githubusercontent.com/u/58251560?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Przemyslaw Kozik</b></sub></a><br /><a href="#design-composer404" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/highfredo"><img src="https://avatars.githubusercontent.com/u/5951524?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Alfredo Arellano de la Fuente</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=highfredo" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/NessunKim"><img src="https://avatars.githubusercontent.com/u/12974079?v=4?s=100" width="100px;" alt=""/><br /><sub><b>MH Kim</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=NessunKim" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://discord.gg/4c5EVTBhtp"><img src="https://avatars.githubusercontent.com/u/40345645?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Marmota</b></sub></a><br /><a href="#design-jaimeadf" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://ares.zone"><img src="https://avatars.githubusercontent.com/u/40336192?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Ares Andrew</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=TENX-S" title="Documentation">📖</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://usual.io/"><img src="https://avatars.githubusercontent.com/u/780052?v=4?s=100" width="100px;" alt=""/><br /><sub><b>George Korsnick</b></sub></a><br /><a href="#financial-gkor" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://about.me/ulu"><img src="https://avatars.githubusercontent.com/u/872764?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Artem Smirnov</b></sub></a><br /><a href="#financial-uluhonolulu" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/nevotheless"><img src="https://avatars.githubusercontent.com/u/779797?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Tim Kopplow</b></sub></a><br /><a href="#financial-nevotheless" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/mrthock"><img src="https://avatars.githubusercontent.com/u/88901709?v=4?s=100" width="100px;" alt=""/><br /><sub><b>mrthock</b></sub></a><br /><a href="#financial-mrthock" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/lrottach"><img src="https://avatars.githubusercontent.com/u/50323692?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Lukas Rottach</b></sub></a><br /><a href="#financial-lrottach" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/boonkerz"><img src="https://avatars.githubusercontent.com/u/277321?v=4?s=100" width="100px;" alt=""/><br /><sub><b>boonkerz</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=boonkerz" title="Code">💻</a> <a href="#translation-boonkerz" title="Translation">🌍</a></td>
|
||||
<td align="center"><a href="https://github.com/milotype"><img src="https://avatars.githubusercontent.com/u/43657314?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Milo Ivir</b></sub></a><br /><a href="#translation-milotype" title="Translation">🌍</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/JasonCubic"><img src="https://avatars.githubusercontent.com/u/8921015?v=4?s=100" width="100px;" alt=""/><br /><sub><b>JasonCubic</b></sub></a><br /><a href="#design-JasonCubic" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/MaxWaldorf"><img src="https://avatars.githubusercontent.com/u/15877853?v=4?s=100" width="100px;" alt=""/><br /><sub><b>MaxWaldorf</b></sub></a><br /><a href="#infra-MaxWaldorf" title="Infrastructure (Hosting, Build-Tools, etc)">🚇</a></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
|
11
README.md
11
README.md
@@ -21,7 +21,7 @@
|
||||
|
||||
<br/>
|
||||
<p align="center">
|
||||
This README is also available in: <a href="./README.ko-KR.md">Korean</a> <a href="./README.zh-CN.md">简体中文</a>
|
||||
This README is also available in: <a href="./README.ru-RU.md">Русский</a> <a href="./README.ko-KR.md">한국어</a> <a href="./README.zh-CN.md">简体中文</a>
|
||||
</p>
|
||||
|
||||
----
|
||||
@@ -108,7 +108,6 @@ Tabby will run as a portable app on Windows, if you create a `data` folder in th
|
||||
|
||||
Plugins and themes can be installed directly from the Settings view inside Tabby.
|
||||
|
||||
* [clickable-links](https://github.com/Eugeny/tabby-clickable-links) - makes paths and URLs in the terminal clickable
|
||||
* [docker](https://github.com/Eugeny/tabby-docker) - connect to Docker containers
|
||||
* [title-control](https://github.com/kbjr/terminus-title-control) - allows modifying the title of the terminal tabs by providing a prefix, suffix, and/or strings to be removed
|
||||
* [quick-cmds](https://github.com/Domain/terminus-quick-cmds) - quickly send commands to one or all terminal tabs
|
||||
@@ -227,6 +226,12 @@ Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/d
|
||||
<td align="center"><a href="https://github.com/nevotheless"><img src="https://avatars.githubusercontent.com/u/779797?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Tim Kopplow</b></sub></a><br /><a href="#financial-nevotheless" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/mrthock"><img src="https://avatars.githubusercontent.com/u/88901709?v=4?s=100" width="100px;" alt=""/><br /><sub><b>mrthock</b></sub></a><br /><a href="#financial-mrthock" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/lrottach"><img src="https://avatars.githubusercontent.com/u/50323692?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Lukas Rottach</b></sub></a><br /><a href="#financial-lrottach" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/boonkerz"><img src="https://avatars.githubusercontent.com/u/277321?v=4?s=100" width="100px;" alt=""/><br /><sub><b>boonkerz</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=boonkerz" title="Code">💻</a> <a href="#translation-boonkerz" title="Translation">🌍</a></td>
|
||||
<td align="center"><a href="https://github.com/milotype"><img src="https://avatars.githubusercontent.com/u/43657314?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Milo Ivir</b></sub></a><br /><a href="#translation-milotype" title="Translation">🌍</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/JasonCubic"><img src="https://avatars.githubusercontent.com/u/8921015?v=4?s=100" width="100px;" alt=""/><br /><sub><b>JasonCubic</b></sub></a><br /><a href="#design-JasonCubic" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/MaxWaldorf"><img src="https://avatars.githubusercontent.com/u/15877853?v=4?s=100" width="100px;" alt=""/><br /><sub><b>MaxWaldorf</b></sub></a><br /><a href="#infra-MaxWaldorf" title="Infrastructure (Hosting, Build-Tools, etc)">🚇</a></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
@@ -236,5 +241,3 @@ Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/d
|
||||
<!-- ALL-CONTRIBUTORS-LIST:END -->
|
||||
|
||||
This project follows the [all-contributors](https://github.com/all-contributors/all-contributors) specification. Contributions of any kind welcome!
|
||||
|
||||
<img src="https://ga-beacon.appspot.com/UA-3278102-18/github/readme" width="1"/>
|
||||
|
246
README.ru-RU.md
Normal file
246
README.ru-RU.md
Normal file
@@ -0,0 +1,246 @@
|
||||
[](https://tabby.sh)
|
||||
|
||||
|
||||
<p align="center">
|
||||
<a href="https://github.com/Eugeny/tabby/releases/latest"><img alt="GitHub All Releases" src="https://img.shields.io/github/downloads/eugeny/tabby/total.svg?label=DOWNLOADS&logo=github&style=for-the-badge"></a> <a href="https://nightly.link/Eugeny/tabby/workflows/build/master"><img src="https://shields.io/badge/-Nightly%20Builds-orange?logo=hackthebox&logoColor=fff&style=for-the-badge"/></a> <a href="https://matrix.to/#/#tabby-general:matrix.org"><img alt="Matrix" src="https://img.shields.io/matrix/tabby-general:matrix.org?logo=matrix&style=for-the-badge&color=magenta"></a>   <a href="https://translate.tabby.sh/"><img alt="Translate" src="https://shields.io/badge/Translate-UI-white?logo=googletranslate&style=for-the-badge&color=white&logoColor=fff"></a> <a href="https://twitter.com/eugeeeeny"><img alt="Twitter" src="https://shields.io/badge/Subscribe-News-blue?logo=twitter&style=for-the-badge&color=blue"></a>
|
||||
</p>
|
||||
|
||||
<p align="center">
|
||||
<a href="https://ko-fi.com/J3J8KWTF">
|
||||
<img src="https://cdn.ko-fi.com/cdn/kofi3.png?v=2" width="150">
|
||||
</a>
|
||||
</p>
|
||||
|
||||
----
|
||||
|
||||
### Загрузки:
|
||||
|
||||
* [Последняя версия](https://github.com/Eugeny/tabby/releases/latest)
|
||||
* [Репозитории](https://packagecloud.io/eugeny/tabby): [Debian/Ubuntu](https://packagecloud.io/eugeny/tabby/install#bash-deb), [RPM](https://packagecloud.io/eugeny/tabby/install#bash-rpm)
|
||||
* [Последний nightly-билд](https://nightly.link/Eugeny/tabby/workflows/build/master)
|
||||
|
||||
<br/>
|
||||
<p align="center">
|
||||
Этот README также доступен на: <a href="./README.md">Английском</a> <a href="./README.ko-KR.md">Корейском</a> <a href="./README.zh-CN.md">Китайском</a>
|
||||
</p>
|
||||
|
||||
----
|
||||
|
||||
[**Tabby**](https://tabby.sh) (ранее **Terminus**) — широко конфигурируемый эмулятор терминала, SSH- и COM-клиент для Windows, macOS и Linux:
|
||||
|
||||
* Встроенный SSH- и Telnet-клиент и менеджер подключений;
|
||||
* Встроенный последовтаельный терминал;
|
||||
* Темы и цветовые схемы;
|
||||
* Полностью настраеваемые сочетания клавиш;
|
||||
* Панели;
|
||||
* Запоминание вкладок;
|
||||
* Поддержка PowerShell (and PS Core), WSL, Git-Bash, Cygwin, MSYS2, Cmder и CMD;
|
||||
* Прямая передача файлов из и в SSH-сессии через Zmodem;
|
||||
* Полная поддержка Unicode, включая символы двойной ширины;
|
||||
* Не задыхается при быстром выводе;
|
||||
* Полноценный опыт работы с shell на Windows, включая дополнение слов и команд по Tab (при помощи Clink);
|
||||
* Втроенное защищённое хранилище для SSH-ключей и настроек;
|
||||
* SSH-, SFTP- и Telnet-клиент доступен как [веб-приложение](https://tabby.sh/app) (также для [самостоятелньного хостинга](https://github.com/Eugeny/tabby-web)).
|
||||
|
||||
# Содержание <!-- omit in toc -->
|
||||
|
||||
- [Правда и ложь про Tabby](#правда-и-ложь-про-tabby)
|
||||
- [Функции терминала](#функции-терминала)
|
||||
- [SSH-клиент](#ssh-клиент)
|
||||
- [Терминал последовательного порта](#терминал-последовательного-порта)
|
||||
- [Портативность](#портативность)
|
||||
- [Плагины](#плагины)
|
||||
- [Темы](#темы)
|
||||
- [Внести свой вклад](#внести-свой-вклад)
|
||||
|
||||
<a name="about"></a>
|
||||
|
||||
# Правда и ложь про Tabby
|
||||
|
||||
* **Правда:** Tabby — это альтернатива стандартному терминалу Windows (conhost), PowerShell ISE, PuTTY, macOS Terminal.app и iTerm.
|
||||
|
||||
* **Ложь:** Tabby — это не новая оболочка или замена MinGW или Cygwin. Также он нелёгок — если потребление ОЗУ крайне важно для вас, лучше взгляните на [Conemu](https://conemu.github.io) или [Alacritty](https://github.com/jwilm/alacritty).
|
||||
|
||||
<a name="terminal"></a>
|
||||
|
||||
# Функции терминала
|
||||
|
||||

|
||||
|
||||
* Терминал V220 + различные дополнения;
|
||||
* Деление окна на несколько панелей;
|
||||
* Вкладки на любой стороне окна;
|
||||
* Опционально закрепляемое окно с глобальной горячей клавишей для вызова («Quake console»);
|
||||
* Определение прогресса процесса;
|
||||
* Уведомления о завершении процессов;
|
||||
* Защита от выполнения команд при вставке, предупреждения о вставке нескольких строк;
|
||||
* Лигатуры шрифтов;
|
||||
* Пользовательские профили оболочки;
|
||||
* Опциональная ПКМ-вставка и копирование при выделении (в стиле PuTTY).
|
||||
|
||||
<a name="ssh"></a>
|
||||
# SSH-клиент
|
||||
|
||||

|
||||
|
||||
* SSH2-клиент с менеджером соединений;
|
||||
* Проброс портов и X11;
|
||||
* Управление автоматическими джамп-хостами;
|
||||
* Проброс агента (включая Pageant и встроеный в Windows OpenSSH Agent);
|
||||
* Скрипты для входа.
|
||||
|
||||
<a name="serial"></a>
|
||||
# Терминал последовательного порта
|
||||
|
||||
* Сохранение соединений;
|
||||
* Поддержка ввода readline;
|
||||
* Опциональый побатный ввод HEX и вывод hexdump;
|
||||
* Преобразование newline;
|
||||
* Автоматическое восстановление соединения.
|
||||
|
||||
<a name="portable"></a>
|
||||
# Портативность
|
||||
|
||||
На Windows Tabby будет работать в портативном режиме, если создать папку `data` там же, где расположен файл `Tabby.exe`.
|
||||
|
||||
<a name="plugins"></a>
|
||||
# Плагины
|
||||
|
||||
Плагины и темы можно установить напрямую из Настроек Tabby.
|
||||
|
||||
* [clickable-links](https://github.com/Eugeny/tabby-clickable-links) — делает пути и URL в терминале гиперссылками;
|
||||
* [docker](https://github.com/Eugeny/tabby-docker) — подключения к Docker-контейнерам;
|
||||
* [title-control](https://github.com/kbjr/terminus-title-control) — позволяет изменять названия вкладок, добавляя префиксы, суффиксы и позволяя удалять строки;
|
||||
* [quick-cmds](https://github.com/Domain/terminus-quick-cmds) — быстро передаёт команды в одну или все вкладки терминала;
|
||||
* [save-output](https://github.com/Eugeny/tabby-save-output) — запись вывода терминала в файл;
|
||||
* [sync-config](https://github.com/starxg/terminus-sync-config) — синхронизация конфига в Gist или Gitee;
|
||||
* [clippy](https://github.com/Eugeny/tabby-clippy) — плагин-пример, который постоянно будет вас бесить;
|
||||
* [workspace-manager](https://github.com/composer404/tabby-workspace-manager) — позволяет создавать пользовательские провили рабочего окружеиня на основе конфига;
|
||||
* [search-in-browser](https://github.com/composer404/tabby-search-in-browser) — открывает браузер по умолчанию с текстом, выделенном во вкладке Tabby.
|
||||
|
||||
<a name="themes"></a>
|
||||
# Темы
|
||||
|
||||
* [hype](https://github.com/Eugeny/tabby-theme-hype) — тема, вдохновлённая Hyper;
|
||||
* [relaxed](https://github.com/Relaxed-Theme/relaxed-terminal-themes#terminus) — тема Relaxed для Tabby;
|
||||
* [gruvbox](https://github.com/porkloin/terminus-theme-gruvbox);
|
||||
* [windows10](https://www.npmjs.com/package/terminus-theme-windows10);
|
||||
* [altair](https://github.com/yxuko/terminus-altair).
|
||||
|
||||
# Спонсоры <!-- omit in toc -->
|
||||
|
||||
[](https://packagecloud.io)
|
||||
|
||||
[**packagecloud**](https://packagecloud.io) предоставил бесплатный хостинг для Debian/RPM репозитория.
|
||||
|
||||
<a name="contributing"></a>
|
||||
# Внести свой вклад
|
||||
|
||||
Pull-запросы и плагины приветствуются!
|
||||
|
||||
Взгляните на [HACKING.md](https://github.com/Eugeny/tabby/blob/master/HACKING.md) и [API docs](https://docs.tabby.sh/), чтобы понять, как устроен проект, и ради очень краткого туториала по созданию плагинов.
|
||||
|
||||
---
|
||||
<a name="contributors"></a>
|
||||
|
||||
Огромное спасибо этим прекрасным людям ([описание эмодзи](https://allcontributors.org/docs/en/emoji-key)):
|
||||
|
||||
<!-- ALL-CONTRIBUTORS-LIST:START - Do not remove or modify this section -->
|
||||
<!-- prettier-ignore-start -->
|
||||
<!-- markdownlint-disable -->
|
||||
<table>
|
||||
<tr>
|
||||
<td align="center"><a href="http://www.russellmyers.com"><img src="https://avatars2.githubusercontent.com/u/184085?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Russell Myers</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=mezner" title="Code">💻</a></td>
|
||||
<td align="center"><a href="http://www.morwire.com"><img src="https://avatars1.githubusercontent.com/u/3991658?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Austin Warren</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=ehwarren" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/Drachenkaetzchen"><img src="https://avatars1.githubusercontent.com/u/162974?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Felicia Hummel</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=Drachenkaetzchen" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/mikemaccana"><img src="https://avatars2.githubusercontent.com/u/172594?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Mike MacCana</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=mikemaccana" title="Tests">⚠️</a> <a href="#design-mikemaccana" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/yxuko"><img src="https://avatars1.githubusercontent.com/u/1786317?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Yacine Kanzari</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=yxuko" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/BBJip"><img src="https://avatars2.githubusercontent.com/u/32908927?v=4?s=100" width="100px;" alt=""/><br /><sub><b>BBJip</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=BBJip" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/Futagirl"><img src="https://avatars2.githubusercontent.com/u/33533958?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Futagirl</b></sub></a><br /><a href="#design-Futagirl" title="Design">🎨</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://www.levrik.io"><img src="https://avatars3.githubusercontent.com/u/9491603?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Levin Rickert</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=levrik" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://kwonoj.github.io"><img src="https://avatars2.githubusercontent.com/u/1210596?v=4?s=100" width="100px;" alt=""/><br /><sub><b>OJ Kwon</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=kwonoj" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/Domain"><img src="https://avatars2.githubusercontent.com/u/903197?v=4?s=100" width="100px;" alt=""/><br /><sub><b>domain</b></sub></a><br /><a href="#plugin-Domain" title="Plugin/utility libraries">🔌</a> <a href="https://github.com/Eugeny/tabby/commits?author=Domain" title="Code">💻</a></td>
|
||||
<td align="center"><a href="http://www.jbrumond.me"><img src="https://avatars1.githubusercontent.com/u/195127?v=4?s=100" width="100px;" alt=""/><br /><sub><b>James Brumond</b></sub></a><br /><a href="#plugin-kbjr" title="Plugin/utility libraries">🔌</a></td>
|
||||
<td align="center"><a href="http://www.growingwiththeweb.com"><img src="https://avatars0.githubusercontent.com/u/2193314?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Daniel Imms</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=Tyriar" title="Code">💻</a> <a href="#plugin-Tyriar" title="Plugin/utility libraries">🔌</a> <a href="https://github.com/Eugeny/tabby/commits?author=Tyriar" title="Tests">⚠️</a></td>
|
||||
<td align="center"><a href="https://github.com/baflo"><img src="https://avatars2.githubusercontent.com/u/834350?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Florian Bachmann</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=baflo" title="Code">💻</a></td>
|
||||
<td align="center"><a href="http://michael-kuehnel.de"><img src="https://avatars2.githubusercontent.com/u/441011?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Michael Kühnel</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=mischah" title="Code">💻</a> <a href="#design-mischah" title="Design">🎨</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/NieLeben"><img src="https://avatars3.githubusercontent.com/u/47182955?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Tilmann Meyer</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=NieLeben" title="Code">💻</a></td>
|
||||
<td align="center"><a href="http://www.jubeat.net"><img src="https://avatars3.githubusercontent.com/u/11289158?v=4?s=100" width="100px;" alt=""/><br /><sub><b>PM Extra</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/issues?q=author%3APMExtra" title="Bug reports">🐛</a></td>
|
||||
<td align="center"><a href="https://jjuhas.keybase.pub//"><img src="https://avatars1.githubusercontent.com/u/6438760?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Jonathan</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=IgnusG" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://hans-koch.me"><img src="https://avatars0.githubusercontent.com/u/1093709?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Hans Koch</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=hammster" title="Code">💻</a></td>
|
||||
<td align="center"><a href="http://thepuzzlemaker.info"><img src="https://avatars3.githubusercontent.com/u/12666617?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Dak Smyth</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=ThePuzzlemaker" title="Code">💻</a></td>
|
||||
<td align="center"><a href="http://yfwz100.github.io"><img src="https://avatars2.githubusercontent.com/u/983211?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Wang Zhi</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=yfwz100" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/jack1142"><img src="https://avatars0.githubusercontent.com/u/6032823?v=4?s=100" width="100px;" alt=""/><br /><sub><b>jack1142</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=jack1142" title="Code">💻</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/hdougie"><img src="https://avatars1.githubusercontent.com/u/450799?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Howie Douglas</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=hdougie" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://chriskaczor.com"><img src="https://avatars2.githubusercontent.com/u/180906?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Chris Kaczor</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=ckaczor" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://www.boxmein.net"><img src="https://avatars1.githubusercontent.com/u/358714?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Johannes Kadak</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=boxmein" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/LeSeulArtichaut"><img src="https://avatars1.githubusercontent.com/u/38361244?v=4?s=100" width="100px;" alt=""/><br /><sub><b>LeSeulArtichaut</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=LeSeulArtichaut" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/CyrilTaylor"><img src="https://avatars0.githubusercontent.com/u/12631466?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Cyril Taylor</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=CyrilTaylor" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/nstefanou"><img src="https://avatars3.githubusercontent.com/u/51129173?v=4?s=100" width="100px;" alt=""/><br /><sub><b>nstefanou</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=nstefanou" title="Code">💻</a> <a href="#plugin-nstefanou" title="Plugin/utility libraries">🔌</a></td>
|
||||
<td align="center"><a href="https://github.com/orin220444"><img src="https://avatars3.githubusercontent.com/u/30747229?v=4?s=100" width="100px;" alt=""/><br /><sub><b>orin220444</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=orin220444" title="Code">💻</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/Goobles"><img src="https://avatars3.githubusercontent.com/u/8776771?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Gobius Dolhain</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=Goobles" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/3l0w"><img src="https://avatars2.githubusercontent.com/u/37798980?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Gwilherm Folliot</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=3l0w" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/Dimitory"><img src="https://avatars0.githubusercontent.com/u/475955?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Dmitry Pronin</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=dimitory" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/JonathanBeverley"><img src="https://avatars1.githubusercontent.com/u/20328966?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Jonathan Beverley</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=JonathanBeverley" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/zend"><img src="https://avatars1.githubusercontent.com/u/25160?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Zenghai Liang</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=zend" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://about.me/matishadow"><img src="https://avatars0.githubusercontent.com/u/9083085?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Mateusz Tracz</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=matishadow" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://zergpool.com"><img src="https://avatars3.githubusercontent.com/u/36234677?v=4?s=100" width="100px;" alt=""/><br /><sub><b>pinpin</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=pinpins" title="Code">💻</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/TakuroOnoda"><img src="https://avatars0.githubusercontent.com/u/1407926?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Takuro Onoda</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=TakuroOnoda" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/frauhottelmann"><img src="https://avatars2.githubusercontent.com/u/902705?v=4?s=100" width="100px;" alt=""/><br /><sub><b>frauhottelmann</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=frauhottelmann" title="Code">💻</a></td>
|
||||
<td align="center"><a href="http://patalong.pl"><img src="https://avatars.githubusercontent.com/u/29167842?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Piotr Patalong</b></sub></a><br /><a href="#design-VectorKappa" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/clarkwang"><img src="https://avatars.githubusercontent.com/u/157076?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Clark Wang</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=clarkwang" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/iamchating"><img src="https://avatars.githubusercontent.com/u/7088153?v=4?s=100" width="100px;" alt=""/><br /><sub><b>iamchating</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=iamchating" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/starxg"><img src="https://avatars.githubusercontent.com/u/34997494?v=4?s=100" width="100px;" alt=""/><br /><sub><b>starxg</b></sub></a><br /><a href="#plugin-starxg" title="Plugin/utility libraries">🔌</a></td>
|
||||
<td align="center"><a href="http://hashnote.net/"><img src="https://avatars.githubusercontent.com/u/546312?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Alisue</b></sub></a><br /><a href="#design-lambdalisue" title="Design">🎨</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/ydcool"><img src="https://avatars.githubusercontent.com/u/5668295?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Dominic Yin</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=ydcool" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/bdr99"><img src="https://avatars.githubusercontent.com/u/2292715?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Brandon Rothweiler</b></sub></a><br /><a href="#design-bdr99" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://git.io/JnP49"><img src="https://avatars.githubusercontent.com/u/63876444?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Logic Machine</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=logicmachine123" title="Documentation">📖</a></td>
|
||||
<td align="center"><a href="https://github.com/cypherbits"><img src="https://avatars.githubusercontent.com/u/10424900?v=4?s=100" width="100px;" alt=""/><br /><sub><b>cypherbits</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=cypherbits" title="Documentation">📖</a></td>
|
||||
<td align="center"><a href="https://modulolotus.net"><img src="https://avatars.githubusercontent.com/u/946421?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Matthew Davidson</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=KingMob" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/al-wi"><img src="https://avatars.githubusercontent.com/u/11092199?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Alexander Wiedemann</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=al-wi" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://www.notion.so/3d45c6bd2cbd4f938873a4bd12e23375"><img src="https://avatars.githubusercontent.com/u/59506394?v=4?s=100" width="100px;" alt=""/><br /><sub><b>장보연</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=BoYeonJang" title="Documentation">📖</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/Me1onRind"><img src="https://avatars.githubusercontent.com/u/19531270?v=4?s=100" width="100px;" alt=""/><br /><sub><b>zZ</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=Me1onRind" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/tainoNZ"><img src="https://avatars.githubusercontent.com/u/49261322?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Aaron Davison</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=tainoNZ" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/composer404"><img src="https://avatars.githubusercontent.com/u/58251560?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Przemyslaw Kozik</b></sub></a><br /><a href="#design-composer404" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/highfredo"><img src="https://avatars.githubusercontent.com/u/5951524?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Alfredo Arellano de la Fuente</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=highfredo" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/NessunKim"><img src="https://avatars.githubusercontent.com/u/12974079?v=4?s=100" width="100px;" alt=""/><br /><sub><b>MH Kim</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=NessunKim" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://discord.gg/4c5EVTBhtp"><img src="https://avatars.githubusercontent.com/u/40345645?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Marmota</b></sub></a><br /><a href="#design-jaimeadf" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://ares.zone"><img src="https://avatars.githubusercontent.com/u/40336192?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Ares Andrew</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=TENX-S" title="Documentation">📖</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://usual.io/"><img src="https://avatars.githubusercontent.com/u/780052?v=4?s=100" width="100px;" alt=""/><br /><sub><b>George Korsnick</b></sub></a><br /><a href="#financial-gkor" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://about.me/ulu"><img src="https://avatars.githubusercontent.com/u/872764?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Artem Smirnov</b></sub></a><br /><a href="#financial-uluhonolulu" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/nevotheless"><img src="https://avatars.githubusercontent.com/u/779797?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Tim Kopplow</b></sub></a><br /><a href="#financial-nevotheless" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/mrthock"><img src="https://avatars.githubusercontent.com/u/88901709?v=4?s=100" width="100px;" alt=""/><br /><sub><b>mrthock</b></sub></a><br /><a href="#financial-mrthock" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/lrottach"><img src="https://avatars.githubusercontent.com/u/50323692?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Lukas Rottach</b></sub></a><br /><a href="#financial-lrottach" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/boonkerz"><img src="https://avatars.githubusercontent.com/u/277321?v=4?s=100" width="100px;" alt=""/><br /><sub><b>boonkerz</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=boonkerz" title="Code">💻</a> <a href="#translation-boonkerz" title="Translation">🌍</a></td>
|
||||
<td align="center"><a href="https://github.com/milotype"><img src="https://avatars.githubusercontent.com/u/43657314?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Milo Ivir</b></sub></a><br /><a href="#translation-milotype" title="Translation">🌍</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/JasonCubic"><img src="https://avatars.githubusercontent.com/u/8921015?v=4?s=100" width="100px;" alt=""/><br /><sub><b>JasonCubic</b></sub></a><br /><a href="#design-JasonCubic" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/MaxWaldorf"><img src="https://avatars.githubusercontent.com/u/15877853?v=4?s=100" width="100px;" alt=""/><br /><sub><b>MaxWaldorf</b></sub></a><br /><a href="#infra-MaxWaldorf" title="Infrastructure (Hosting, Build-Tools, etc)">🚇</a></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<!-- markdownlint-restore -->
|
||||
<!-- prettier-ignore-end -->
|
||||
|
||||
<!-- ALL-CONTRIBUTORS-LIST:END -->
|
||||
|
||||
Данный проект следует заветам [all-contributors](https://github.com/all-contributors/all-contributors). Любые созидатели приветствуются!
|
||||
|
||||
<img src="https://ga-beacon.appspot.com/UA-3278102-18/github/readme" width="1"/>
|
@@ -2,7 +2,7 @@
|
||||
|
||||
|
||||
<p align="center">
|
||||
<a href="https://github.com/Eugeny/tabby/releases/latest"><img alt="GitHub All Releases" src="https://img.shields.io/github/downloads/eugeny/tabby/total.svg?label=DOWNLOADS&logo=github&style=for-the-badge"></a> <a href="https://nightly.link/Eugeny/tabby/workflows/build/master"><img src="https://shields.io/badge/-Nightly%20Builds-orange?logo=hackthebox&logoColor=fff&style=for-the-badge"/></a> <a href="https://matrix.to/#/#tabby-general:matrix.org"><img alt="Matrix" src="https://img.shields.io/matrix/tabby-general:matrix.org?logo=matrix&style=for-the-badge&color=magenta"></a> <a href="https://twitter.com/eugeeeeny"><img alt="Twitter" src="https://shields.io/badge/Subscribe-News-blue?logo=twitter&style=for-the-badge&color=blue"></a>
|
||||
<a href="https://github.com/Eugeny/tabby/releases/latest"><img alt="GitHub All Releases" src="https://img.shields.io/github/downloads/eugeny/tabby/total.svg?label=DOWNLOADS&logo=github&style=for-the-badge"></a> <a href="https://nightly.link/Eugeny/tabby/workflows/build/master"><img src="https://shields.io/badge/-Nightly%20Builds-orange?logo=hackthebox&logoColor=fff&style=for-the-badge"/></a> <a href="https://matrix.to/#/#tabby-general:matrix.org"><img alt="Matrix" src="https://img.shields.io/matrix/tabby-general:matrix.org?logo=matrix&style=for-the-badge&color=magenta"></a>   <a href="https://translate.tabby.sh/"><img alt="Translate" src="https://shields.io/badge/Translate-UI-white?logo=googletranslate&style=for-the-badge&color=white&logoColor=fff"></a> <a href="https://twitter.com/eugeeeeny"><img alt="Twitter" src="https://shields.io/badge/Subscribe-News-blue?logo=twitter&style=for-the-badge&color=blue"></a>
|
||||
</p>
|
||||
|
||||
<p align="center">
|
||||
@@ -19,6 +19,11 @@
|
||||
* [Repositories](https://packagecloud.io/eugeny/tabby): [Debian/Ubuntu-based](https://packagecloud.io/eugeny/tabby/install#bash-deb), [RPM-based](https://packagecloud.io/eugeny/tabby/install#bash-rpm)
|
||||
* [Latest nightly build](https://nightly.link/Eugeny/tabby/workflows/build/master)
|
||||
|
||||
<br/>
|
||||
<p align="center">
|
||||
本 README 还适用于以下语言: <a href="./README.ru-RU.md">Русский</a> <a href="./README.ko-KR.md">한국어</a> <a href="./README.zh-CN.md">简体中文</a>
|
||||
</p>
|
||||
|
||||
----
|
||||
|
||||
[**Tabby**](https://tabby.sh) (前身是 **Terminus**) 是一个可高度配置的终端模拟器和 SSH 或串口客户端,支持 Windows,macOS 和 Linux
|
||||
@@ -27,15 +32,15 @@
|
||||
* 集成串行终端
|
||||
* 定制主题和配色方案
|
||||
* 完全可配置的快捷键和多键快捷键
|
||||
* 拆分窗格
|
||||
* 记住你的标签
|
||||
* 分体式窗格
|
||||
* 自动保存标签页
|
||||
* 支持 PowerShell(和 PS Core)、WSL、Git-Bash、Cygwin、MSYS2、Cmder 和 CMD
|
||||
* 在 SSH 会话中通过 Zmodem 进行直接文件传输
|
||||
* 完整的 Unicode 支持,包括双角字符
|
||||
* 不会因快速的输出而卡住
|
||||
* Windows 上的正确 shell 体验,包括 tab 自动补全(通过 Clink)
|
||||
* Integrated encrypted container for SSH secrets and configuration
|
||||
* SSH、SFTP 和 Telnet 客户端可用作 [Web 应用程序](https://tabby.sh/app)(也可[托管](https://github.com/Eugeny/tabby-web))
|
||||
* Windows 上舒适的 shell 体验,包括 tab 自动补全(通过 Clink)
|
||||
* 为 SSH secrets 和设置集成了加密容器
|
||||
* SSH、SFTP 和 Telnet 客户端可用作 [Web 应用](https://tabby.sh/app)(也可[托管](https://github.com/Eugeny/tabby-web))
|
||||
|
||||
# 目录 <!-- omit in toc -->
|
||||
|
||||
@@ -43,7 +48,7 @@
|
||||
- [终端特性](#终端特性)
|
||||
- [SSH 客户端](#ssh-客户端)
|
||||
- [串行终端](#串行终端)
|
||||
- [可移植的](#可移植的)
|
||||
- [便携式应用](#便携式应用)
|
||||
- [插件](#插件)
|
||||
- [主题](#主题)
|
||||
- [贡献](#贡献)
|
||||
@@ -54,7 +59,7 @@
|
||||
|
||||
* **Tabby 是** Windows 标准终端 (conhost)、PowerShell ISE、PuTTY、macOS Terminal.app 和 iTerm 的替代品
|
||||
|
||||
* **Tabby 不是** Tabby 不是新的 shell,也不是 MinGW 或 Cygwin 的替代品。它也不是轻量级的 - 如果,请考虑 [Conemu](https://conemu.github.io) 或 [Alacritty](https://github.com/jwilm/alacritty)
|
||||
* **Tabby 不是**一个全新的 shell,也不是 MinGW 或 Cygwin 的替代品。它也不是轻量级的 - 如果你对内存的占用很敏感,请考虑 [Conemu](https://conemu.github.io) 或 [Alacritty](https://github.com/jwilm/alacritty)
|
||||
<a name="terminal"></a>
|
||||
|
||||
# 终端特性
|
||||
@@ -63,11 +68,11 @@
|
||||
|
||||
* 一个 V220 终端 + 各种插件
|
||||
* 多个嵌套的拆分窗格
|
||||
* Tabs on any side of the window
|
||||
* 可以将标签页设置在窗口的任意一侧
|
||||
* 带有全局生成热键的可选可停靠窗口(“Quake console”)
|
||||
* 进度检测
|
||||
* 流程完成通知
|
||||
* 括号粘贴,多行粘贴警告
|
||||
* 带括号的粘贴,多行粘贴提示
|
||||
* 连体字
|
||||
* 自定义 shell 配置文件
|
||||
* 可选的 RMB 粘贴和复制选择(PuTTY 风格)
|
||||
@@ -86,31 +91,31 @@
|
||||
<a name="serial"></a>
|
||||
# 串行终端
|
||||
|
||||
* 保存链接
|
||||
* Readline 输入支持
|
||||
* 保存连接
|
||||
* 逐行读取的输入支持
|
||||
* 可选的十六进制逐字节输入和十六进制转储输出
|
||||
* 换行转换
|
||||
* 自动重连
|
||||
|
||||
<a name="portable"></a>
|
||||
# 可移植的
|
||||
# 便携式应用
|
||||
|
||||
如果在 Tabby.exe 所在的同一位置创建数据文件夹,Tabby 将在 Windows 上作为便携式的应用程序运行。
|
||||
如果在 Tabby.exe 所在的目录创建一个名为`data`文件夹,Tabby 将可以在 Windows 上作为便携式的应用程序运行。
|
||||
|
||||
<a name="plugins"></a>
|
||||
# 插件
|
||||
|
||||
插件和主题可以直接从 Tabby 中的设置视图安装。
|
||||
插件和主题可以直接在 Tabby 设置中安装。
|
||||
|
||||
* [clickable-links](https://github.com/Eugeny/tabby-clickable-links) - 使终端中的路径和 URL 可点击
|
||||
* [docker](https://github.com/Eugeny/tabby-docker) - 连接到 Docker 容器
|
||||
* [title-control](https://github.com/kbjr/terminus-title-control) - 允许通过提供要删除的前缀、后缀和/或字符串来修改终端选项卡的标题
|
||||
* [quick-cmds](https://github.com/Domain/terminus-quick-cmds) - 快速向一个或所有终端选项卡发送命令
|
||||
* [docker](https://github.com/Eugeny/tabby-docker) - 连接 Docker 容器
|
||||
* [title-control](https://github.com/kbjr/terminus-title-control) - 允许通过提供要删除的前缀、后缀和/或字符串来修改标签页的标题
|
||||
* [quick-cmds](https://github.com/Domain/terminus-quick-cmds) - 快速向一个或所有标签页发送命令
|
||||
* [save-output](https://github.com/Eugeny/tabby-save-output) - 将终端输出记录到文件中
|
||||
* [sync-config](https://github.com/starxg/terminus-sync-config) - 将配置同步到 Gist 或 Gitee
|
||||
* [clippy](https://github.com/Eugeny/tabby-clippy) - 一个一直打扰你的示例插件
|
||||
* [clippy](https://github.com/Eugeny/tabby-clippy) - 一个可以一直烦你的示例插件
|
||||
* [workspace-manager](https://github.com/composer404/tabby-workspace-manager) - 允许根据给定的配置创建自定义工作区配置文件
|
||||
* [search-in-browser](https://github.com/composer404/tabby-search-in-browser) - 使用从 Tabby 选项卡中选择的文本打开默认系统浏览器
|
||||
* [search-in-browser](https://github.com/composer404/tabby-search-in-browser) - 从 Tabby 标签页带有选中的文本来打开系统默认浏览器
|
||||
|
||||
<a name="themes"></a>
|
||||
# 主题
|
||||
@@ -213,6 +218,20 @@
|
||||
<td align="center"><a href="https://github.com/highfredo"><img src="https://avatars.githubusercontent.com/u/5951524?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Alfredo Arellano de la Fuente</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=highfredo" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/NessunKim"><img src="https://avatars.githubusercontent.com/u/12974079?v=4?s=100" width="100px;" alt=""/><br /><sub><b>MH Kim</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=NessunKim" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://discord.gg/4c5EVTBhtp"><img src="https://avatars.githubusercontent.com/u/40345645?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Marmota</b></sub></a><br /><a href="#design-jaimeadf" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://ares.zone"><img src="https://avatars.githubusercontent.com/u/40336192?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Ares Andrew</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=TENX-S" title="Documentation">📖</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://usual.io/"><img src="https://avatars.githubusercontent.com/u/780052?v=4?s=100" width="100px;" alt=""/><br /><sub><b>George Korsnick</b></sub></a><br /><a href="#financial-gkor" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://about.me/ulu"><img src="https://avatars.githubusercontent.com/u/872764?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Artem Smirnov</b></sub></a><br /><a href="#financial-uluhonolulu" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/nevotheless"><img src="https://avatars.githubusercontent.com/u/779797?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Tim Kopplow</b></sub></a><br /><a href="#financial-nevotheless" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/mrthock"><img src="https://avatars.githubusercontent.com/u/88901709?v=4?s=100" width="100px;" alt=""/><br /><sub><b>mrthock</b></sub></a><br /><a href="#financial-mrthock" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/lrottach"><img src="https://avatars.githubusercontent.com/u/50323692?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Lukas Rottach</b></sub></a><br /><a href="#financial-lrottach" title="Financial">💵</a></td>
|
||||
<td align="center"><a href="https://github.com/boonkerz"><img src="https://avatars.githubusercontent.com/u/277321?v=4?s=100" width="100px;" alt=""/><br /><sub><b>boonkerz</b></sub></a><br /><a href="https://github.com/Eugeny/tabby/commits?author=boonkerz" title="Code">💻</a> <a href="#translation-boonkerz" title="Translation">🌍</a></td>
|
||||
<td align="center"><a href="https://github.com/milotype"><img src="https://avatars.githubusercontent.com/u/43657314?v=4?s=100" width="100px;" alt=""/><br /><sub><b>Milo Ivir</b></sub></a><br /><a href="#translation-milotype" title="Translation">🌍</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/JasonCubic"><img src="https://avatars.githubusercontent.com/u/8921015?v=4?s=100" width="100px;" alt=""/><br /><sub><b>JasonCubic</b></sub></a><br /><a href="#design-JasonCubic" title="Design">🎨</a></td>
|
||||
<td align="center"><a href="https://github.com/MaxWaldorf"><img src="https://avatars.githubusercontent.com/u/15877853?v=4?s=100" width="100px;" alt=""/><br /><sub><b>MaxWaldorf</b></sub></a><br /><a href="#infra-MaxWaldorf" title="Infrastructure (Hosting, Build-Tools, etc)">🚇</a></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
@@ -221,6 +240,4 @@
|
||||
|
||||
<!-- ALL-CONTRIBUTORS-LIST:END -->
|
||||
|
||||
This project follows the [all-contributors](https://github.com/all-contributors/all-contributors) specification. Contributions of any kind welcome!
|
||||
|
||||
<img src="https://ga-beacon.appspot.com/UA-3278102-18/github/readme" width="1"/>
|
||||
本项目遵循 [all-contributors](https://github.com/all-contributors/all-contributors) 规范。 欢迎任何形式的贡献!
|
||||
|
@@ -130,7 +130,6 @@ export class Application {
|
||||
this.setupMenu()
|
||||
}
|
||||
await window.ready
|
||||
window.present()
|
||||
return window
|
||||
}
|
||||
|
||||
|
@@ -27,7 +27,7 @@ abstract class GlasstronWindow extends BrowserWindow {
|
||||
abstract setBlur (_: boolean)
|
||||
}
|
||||
|
||||
const macOSVibrancyType = process.platform === 'darwin' ? compareVersions(macOSRelease().version, '10.14', '>=') ? 'fullscreen-ui' : 'dark' : null
|
||||
const macOSVibrancyType = process.platform === 'darwin' ? compareVersions(macOSRelease().version, '10.14', '>=') ? 'under-window' : 'dark' : null
|
||||
|
||||
const activityIcon = nativeImage.createFromPath(`${app.getAppPath()}/assets/activity.png`)
|
||||
|
||||
@@ -303,6 +303,9 @@ export class Window {
|
||||
this.window.on('enter-full-screen', () => this.send('host:window-enter-full-screen'))
|
||||
this.window.on('leave-full-screen', () => this.send('host:window-leave-full-screen'))
|
||||
|
||||
this.window.on('maximize', () => this.send('host:window-maximized'))
|
||||
this.window.on('unmaximize', () => this.send('host:window-unmaximized'))
|
||||
|
||||
this.window.on('close', event => {
|
||||
if (!this.closing) {
|
||||
event.preventDefault()
|
||||
|
@@ -38,7 +38,7 @@
|
||||
"optionalDependencies": {
|
||||
"@tabby-gang/windows-blurbehind": "^3.0.0",
|
||||
"macos-native-processlist": "^2.0.0",
|
||||
"serialport": "^10.0.1",
|
||||
"serialport": "^10.0.2",
|
||||
"windows-native-registry": "^3.1.0",
|
||||
"windows-process-tree": "^0.3.2"
|
||||
},
|
||||
|
@@ -1,7 +1,7 @@
|
||||
body {
|
||||
min-height: 100vh;
|
||||
overflow: hidden;
|
||||
background: #1D272D;
|
||||
background: transparent !important;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
}
|
||||
|
||||
|
@@ -3,4 +3,5 @@ export const PLUGIN_BLACKLIST = [
|
||||
'terminus-scrollbar', // now useless
|
||||
'terminus-clickable-links', // now bundled with Tabby
|
||||
'tabby-clickable-links', // now bundled with Tabby
|
||||
'terminus-clickable-ips', // broken, functionality now bundled with Tabby
|
||||
]
|
||||
|
@@ -1,3 +1,7 @@
|
||||
app-root {
|
||||
background: #1D272D;
|
||||
}
|
||||
|
||||
.preload-logo {
|
||||
-webkit-app-region: drag;
|
||||
position: fixed;
|
||||
|
@@ -40,17 +40,16 @@
|
||||
"@serialport/binding-abstract" "10.0.1"
|
||||
debug "^4.3.2"
|
||||
|
||||
"@serialport/bindings@10.0.1":
|
||||
version "10.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@serialport/bindings/-/bindings-10.0.1.tgz#b8f1d81dae370b954329ec9fdbabb23df74e6a35"
|
||||
integrity sha512-CcSE0OQQwpEup0LebG8bMFhVv+MB2wOm2yHWrdY6UiP3AEh7bB8F6sU1B/iq78BogyoIQ3ZDZBEi4I4F1hYVvA==
|
||||
"@serialport/bindings-cpp@^10.2.1":
|
||||
version "10.2.1"
|
||||
resolved "https://registry.yarnpkg.com/@serialport/bindings-cpp/-/bindings-cpp-10.2.1.tgz#e44a246142c11c83f0e4fd0cd16491702e6c3202"
|
||||
integrity sha512-PCnMBdy53/DLYx8dJg4e8Na1hMVGxE0d60IU6i03+k5SEmtPblixvIyytcllFhMRGQmH2zHHjP/2Big2Rjddwg==
|
||||
dependencies:
|
||||
"@serialport/binding-abstract" "10.0.1"
|
||||
"@serialport/parser-readline" "10.0.1"
|
||||
bindings "^1.5.0"
|
||||
debug "^4.3.2"
|
||||
node-addon-api "4.2.0"
|
||||
prebuild-install "^7.0.0"
|
||||
node-gyp-build "^4.3.0"
|
||||
|
||||
"@serialport/parser-byte-length@10.0.1":
|
||||
version "10.0.1"
|
||||
@@ -89,10 +88,10 @@
|
||||
resolved "https://registry.yarnpkg.com/@serialport/parser-regex/-/parser-regex-10.0.1.tgz#bcb302dda0a9d07ce9b3e554e3d2a41abf3fb5c5"
|
||||
integrity sha512-l8ECuUsan33x5pirQZodlmw0q70Jcxy+oHnXJaqchBTRCbtXlE7+PMFJnmNoIHGqDwt0XALbwpvKcnNBrgvT1g==
|
||||
|
||||
"@serialport/stream@10.0.1":
|
||||
version "10.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@serialport/stream/-/stream-10.0.1.tgz#f38c0e076e9e9ba3255e20e161576879f7d9ae18"
|
||||
integrity sha512-WQ5baxC56Jxo9mXgHq3BPxCXKnfOo3PZxpm6CDaKsZbdsdPYChogRsJCzKjAn6QaKIIFv3/5UdAXKmMCxkeVDA==
|
||||
"@serialport/stream@10.0.2":
|
||||
version "10.0.2"
|
||||
resolved "https://registry.yarnpkg.com/@serialport/stream/-/stream-10.0.2.tgz#3a242ea8a42356af9e4fb0924ca4a4a0efd36e37"
|
||||
integrity sha512-ZlC1M8/+hIO4JYI+cwJMAL2gkdf6Ahcen5gHJhM1Ibj40fRPOtxIWR1vgGFY1a/TKADDUZorE4RVYxmbheeZYw==
|
||||
dependencies:
|
||||
debug "^4.3.2"
|
||||
|
||||
@@ -331,13 +330,6 @@ bin-links@^1.1.2, bin-links@^1.1.8:
|
||||
npm-normalize-package-bin "^1.0.0"
|
||||
write-file-atomic "^2.3.0"
|
||||
|
||||
bindings@^1.5.0:
|
||||
version "1.5.0"
|
||||
resolved "https://registry.npmjs.org/bindings/-/bindings-1.5.0.tgz"
|
||||
integrity sha512-p2q/t/mhvuOj/UeLlV6566GD/guowlr0hHxClI0W9m7MWYkL1F0hLo+0Aexs9HSPCtR1SXQ0TD3MMKrXZajbiQ==
|
||||
dependencies:
|
||||
file-uri-to-path "1.0.0"
|
||||
|
||||
bl@^4.0.3:
|
||||
version "4.0.3"
|
||||
resolved "https://registry.npmjs.org/bl/-/bl-4.0.3.tgz"
|
||||
@@ -768,13 +760,6 @@ decompress-response@^4.2.0:
|
||||
dependencies:
|
||||
mimic-response "^2.0.0"
|
||||
|
||||
decompress-response@^6.0.0:
|
||||
version "6.0.0"
|
||||
resolved "https://registry.yarnpkg.com/decompress-response/-/decompress-response-6.0.0.tgz#ca387612ddb7e104bd16d85aab00d5ecf09c66fc"
|
||||
integrity sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==
|
||||
dependencies:
|
||||
mimic-response "^3.1.0"
|
||||
|
||||
deep-extend@^0.6.0:
|
||||
version "0.6.0"
|
||||
resolved "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz"
|
||||
@@ -1071,11 +1056,6 @@ figgy-pudding@^3.4.1, figgy-pudding@^3.5.1:
|
||||
resolved "https://registry.yarnpkg.com/figgy-pudding/-/figgy-pudding-3.5.2.tgz#b4eee8148abb01dcf1d1ac34367d59e12fa61d6e"
|
||||
integrity sha512-0btnI/H8f2pavGMN8w40mlSKOfTK2SVJmBfBeVIj3kNw0swwgzyRq0d5TJVOwodFmtvpPeWPN/MCcfuWF0Ezbw==
|
||||
|
||||
file-uri-to-path@1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz"
|
||||
integrity sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==
|
||||
|
||||
"filesize@>= 4.0.0":
|
||||
version "6.3.0"
|
||||
resolved "https://registry.yarnpkg.com/filesize/-/filesize-6.3.0.tgz#dff53cfb3f104c9e422f346d53be8dbcc971bf11"
|
||||
@@ -2126,11 +2106,6 @@ mimic-response@^2.0.0:
|
||||
resolved "https://registry.npmjs.org/mimic-response/-/mimic-response-2.1.0.tgz"
|
||||
integrity sha512-wXqjST+SLt7R009ySCglWBCFpjUygmCIfD790/kVbiGmUgfYGuB14PiTd5DwVxSV4NcYHjzMkoj5LjQZwTQLEA==
|
||||
|
||||
mimic-response@^3.1.0:
|
||||
version "3.1.0"
|
||||
resolved "https://registry.yarnpkg.com/mimic-response/-/mimic-response-3.1.0.tgz#2d1d59af9c1b129815accc2c46a022a5ce1fa3c9"
|
||||
integrity sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==
|
||||
|
||||
minimatch@^3.0.4:
|
||||
version "3.0.4"
|
||||
resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz"
|
||||
@@ -2264,13 +2239,6 @@ node-abi@^2.20.0, node-abi@^2.7.0:
|
||||
dependencies:
|
||||
semver "^5.4.1"
|
||||
|
||||
node-abi@^3.3.0:
|
||||
version "3.5.0"
|
||||
resolved "https://registry.yarnpkg.com/node-abi/-/node-abi-3.5.0.tgz#26e8b7b251c3260a5ac5ba5aef3b4345a0229248"
|
||||
integrity sha512-LtHvNIBgOy5mO8mPEUtkCW/YCRWYEKshIvqhe1GHHyXEHEB5mgICyYnAcl4qan3uFeRROErKGzatFHPf6kDxWw==
|
||||
dependencies:
|
||||
semver "^7.3.5"
|
||||
|
||||
node-addon-api@3.0.0:
|
||||
version "3.0.0"
|
||||
resolved "https://registry.npmjs.org/node-addon-api/-/node-addon-api-3.0.0.tgz"
|
||||
@@ -2295,6 +2263,11 @@ node-fetch-npm@^2.0.2:
|
||||
json-parse-better-errors "^1.0.0"
|
||||
safe-buffer "^5.1.1"
|
||||
|
||||
node-gyp-build@^4.3.0:
|
||||
version "4.3.0"
|
||||
resolved "https://registry.yarnpkg.com/node-gyp-build/-/node-gyp-build-4.3.0.tgz#9f256b03e5826150be39c764bf51e993946d71a3"
|
||||
integrity sha512-iWjXZvmboq0ja1pUGULQBexmxq8CV4xBhX7VDOTbL7ZR4FOowwY/VOtRxBN/yKxmdGoIp4j5ysNT4u3S2pDQ3Q==
|
||||
|
||||
node-gyp@^5.0.2, node-gyp@^5.1.0:
|
||||
version "5.1.1"
|
||||
resolved "https://registry.yarnpkg.com/node-gyp/-/node-gyp-5.1.1.tgz#eb915f7b631c937d282e33aed44cb7a025f62a3e"
|
||||
@@ -2889,25 +2862,6 @@ prebuild-install@^6.0.0:
|
||||
tunnel-agent "^0.6.0"
|
||||
which-pm-runs "^1.0.0"
|
||||
|
||||
prebuild-install@^7.0.0:
|
||||
version "7.0.0"
|
||||
resolved "https://registry.yarnpkg.com/prebuild-install/-/prebuild-install-7.0.0.tgz#3c5ce3902f1cb9d6de5ae94ca53575e4af0c1574"
|
||||
integrity sha512-IvSenf33K7JcgddNz2D5w521EgO+4aMMjFt73Uk9FRzQ7P+QZPKrp7qPsDydsSwjGt3T5xRNnM1bj1zMTD5fTA==
|
||||
dependencies:
|
||||
detect-libc "^1.0.3"
|
||||
expand-template "^2.0.3"
|
||||
github-from-package "0.0.0"
|
||||
minimist "^1.2.3"
|
||||
mkdirp-classic "^0.5.3"
|
||||
napi-build-utils "^1.0.1"
|
||||
node-abi "^3.3.0"
|
||||
npmlog "^4.0.1"
|
||||
pump "^3.0.0"
|
||||
rc "^1.2.7"
|
||||
simple-get "^4.0.0"
|
||||
tar-fs "^2.0.0"
|
||||
tunnel-agent "^0.6.0"
|
||||
|
||||
prepend-http@^1.0.1:
|
||||
version "1.0.4"
|
||||
resolved "https://registry.yarnpkg.com/prepend-http/-/prepend-http-1.0.4.tgz#d4f4562b0ce3696e41ac52d0e002e57a635dc6dc"
|
||||
@@ -3281,13 +3235,13 @@ serialize-error@^5.0.0:
|
||||
dependencies:
|
||||
type-fest "^0.8.0"
|
||||
|
||||
serialport@^10.0.1:
|
||||
version "10.0.1"
|
||||
resolved "https://registry.yarnpkg.com/serialport/-/serialport-10.0.1.tgz#2df0ddcedf507180229973fc46e175f123e7c46f"
|
||||
integrity sha512-RNEUs8mtf6m8593b2qRfkDakxbhPR4VQT0iNKEpJu/JfuWVrSYMqAAWnJOQXOWdJV6ib7rcxCHgHFyarGqJVWw==
|
||||
serialport@^10.0.2:
|
||||
version "10.0.2"
|
||||
resolved "https://registry.yarnpkg.com/serialport/-/serialport-10.0.2.tgz#64150fd2cd4cec35a88e0b8af66614a42b06e577"
|
||||
integrity sha512-hFQ6V/LFh0G4FmQsPjQCLqofalpHRWznXVA3lKlA19kUkdQrOmsz3CHQ72mPglbY+1PGGHZwXHPdTROtWP4qsA==
|
||||
dependencies:
|
||||
"@serialport/binding-mock" "10.0.1"
|
||||
"@serialport/bindings" "10.0.1"
|
||||
"@serialport/bindings-cpp" "^10.2.1"
|
||||
"@serialport/parser-byte-length" "10.0.1"
|
||||
"@serialport/parser-cctalk" "10.0.1"
|
||||
"@serialport/parser-delimiter" "10.0.1"
|
||||
@@ -3295,7 +3249,7 @@ serialport@^10.0.1:
|
||||
"@serialport/parser-readline" "10.0.1"
|
||||
"@serialport/parser-ready" "10.0.1"
|
||||
"@serialport/parser-regex" "10.0.1"
|
||||
"@serialport/stream" "10.0.1"
|
||||
"@serialport/stream" "10.0.2"
|
||||
debug "^4.3.2"
|
||||
|
||||
set-blocking@^2.0.0, set-blocking@~2.0.0:
|
||||
@@ -3341,15 +3295,6 @@ simple-get@^3.0.3:
|
||||
once "^1.3.1"
|
||||
simple-concat "^1.0.0"
|
||||
|
||||
simple-get@^4.0.0:
|
||||
version "4.0.0"
|
||||
resolved "https://registry.yarnpkg.com/simple-get/-/simple-get-4.0.0.tgz#73fa628278d21de83dadd5512d2cc1f4872bd675"
|
||||
integrity sha512-ZalZGexYr3TA0SwySsr5HlgOOinS4Jsa8YB2GJ6lUNAazyAu4KG/VmzMTwAt2YVXzzVj8QmefmAonZIK2BSGcQ==
|
||||
dependencies:
|
||||
decompress-response "^6.0.0"
|
||||
once "^1.3.1"
|
||||
simple-concat "^1.0.0"
|
||||
|
||||
slash@^2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/slash/-/slash-2.0.0.tgz#de552851a1759df3a8f206535442f5ec4ddeab44"
|
||||
|
@@ -40,7 +40,7 @@ publish:
|
||||
win:
|
||||
icon: "./build/windows/icon.ico"
|
||||
artifactName: tabby-${version}-portable.${ext}
|
||||
rfc3161TimeStampServer: http://timestamp.comodoca.com/rfc3161
|
||||
rfc3161TimeStampServer: http://timestamp.sectigo.com
|
||||
nsis:
|
||||
oneClick: false
|
||||
artifactName: tabby-${version}-setup.${ext}
|
||||
@@ -66,7 +66,7 @@ mac:
|
||||
NSRemovableVolumesUsageDescription: 'A subprocess requests access to files on a removable volume.'
|
||||
|
||||
linux:
|
||||
category: Utility
|
||||
category: "Utility;TerminalEmulator;System"
|
||||
icon: "./build/icons"
|
||||
artifactName: tabby-${version}-linux.${ext}
|
||||
executableArgs:
|
||||
|
143
locale/app.pot
143
locale/app.pot
@@ -10,12 +10,21 @@ msgstr ""
|
||||
msgid "Abort all"
|
||||
msgstr ""
|
||||
|
||||
msgid "Accept and remember key"
|
||||
msgstr ""
|
||||
|
||||
msgid "Accept just this once"
|
||||
msgstr ""
|
||||
|
||||
msgid "Acrylic background"
|
||||
msgstr ""
|
||||
|
||||
msgid "Add"
|
||||
msgstr ""
|
||||
|
||||
msgid "Add a port forward"
|
||||
msgstr ""
|
||||
|
||||
msgid "Add a private key"
|
||||
msgstr ""
|
||||
|
||||
@@ -141,6 +150,9 @@ msgstr ""
|
||||
msgid "Chinese (simplified)"
|
||||
msgstr ""
|
||||
|
||||
msgid "Chinese (traditional)"
|
||||
msgstr ""
|
||||
|
||||
msgid "Ciphers"
|
||||
msgstr ""
|
||||
|
||||
@@ -246,12 +258,18 @@ msgstr ""
|
||||
msgid "Could not decrypt config"
|
||||
msgstr ""
|
||||
|
||||
msgid "Croatian"
|
||||
msgstr ""
|
||||
|
||||
msgid "Current"
|
||||
msgstr ""
|
||||
|
||||
msgid "Current color scheme"
|
||||
msgstr ""
|
||||
|
||||
msgid "Current host key fingerprint"
|
||||
msgstr ""
|
||||
|
||||
msgid "Current process: {name}"
|
||||
msgstr ""
|
||||
|
||||
@@ -324,6 +342,9 @@ msgstr ""
|
||||
msgid "Disabled"
|
||||
msgstr ""
|
||||
|
||||
msgid "Disconnect"
|
||||
msgstr ""
|
||||
|
||||
msgid "Display on"
|
||||
msgstr ""
|
||||
|
||||
@@ -480,6 +501,9 @@ msgstr ""
|
||||
msgid "Forwarded ports"
|
||||
msgstr ""
|
||||
|
||||
msgid "French"
|
||||
msgstr ""
|
||||
|
||||
msgid "From color scheme"
|
||||
msgstr ""
|
||||
|
||||
@@ -498,15 +522,15 @@ msgstr ""
|
||||
msgid "Generate a pre-filled GitHub issue"
|
||||
msgstr ""
|
||||
|
||||
msgid "German"
|
||||
msgstr ""
|
||||
|
||||
msgid "Get"
|
||||
msgstr ""
|
||||
|
||||
msgid "Get it from the Tabby Web settings window"
|
||||
msgstr ""
|
||||
|
||||
msgid "GitHub"
|
||||
msgstr ""
|
||||
|
||||
msgid "Gives the window a blurred transparent background"
|
||||
msgstr ""
|
||||
|
||||
@@ -546,6 +570,9 @@ msgstr ""
|
||||
msgid "Host key"
|
||||
msgstr ""
|
||||
|
||||
msgid "Host key verification"
|
||||
msgstr ""
|
||||
|
||||
msgid "Hotkeys"
|
||||
msgstr ""
|
||||
|
||||
@@ -612,6 +639,9 @@ msgstr ""
|
||||
msgid "Language"
|
||||
msgstr ""
|
||||
|
||||
msgid "Last known host key fingerprint"
|
||||
msgstr ""
|
||||
|
||||
msgid "Launch WinSCP"
|
||||
msgstr ""
|
||||
|
||||
@@ -684,9 +714,6 @@ msgstr ""
|
||||
msgid "Name for the new config"
|
||||
msgstr ""
|
||||
|
||||
msgid "Named pipe"
|
||||
msgstr ""
|
||||
|
||||
msgid "Native"
|
||||
msgstr ""
|
||||
|
||||
@@ -711,6 +738,9 @@ msgstr ""
|
||||
msgid "New tab"
|
||||
msgstr ""
|
||||
|
||||
msgid "New tab: {profile}"
|
||||
msgstr ""
|
||||
|
||||
msgid "New terminal"
|
||||
msgstr ""
|
||||
|
||||
@@ -813,9 +843,6 @@ msgstr ""
|
||||
msgid "Overwrite the local config and start syncing?"
|
||||
msgstr ""
|
||||
|
||||
msgid "Paper"
|
||||
msgstr ""
|
||||
|
||||
msgid "Parity"
|
||||
msgstr ""
|
||||
|
||||
@@ -852,6 +879,9 @@ msgstr ""
|
||||
msgid "Plugins folder"
|
||||
msgstr ""
|
||||
|
||||
msgid "Polish"
|
||||
msgstr ""
|
||||
|
||||
msgid "Port"
|
||||
msgstr ""
|
||||
|
||||
@@ -885,9 +915,6 @@ msgstr ""
|
||||
msgid "Profiles & connections"
|
||||
msgstr ""
|
||||
|
||||
msgid "Profiles and connections"
|
||||
msgstr ""
|
||||
|
||||
msgid "Program"
|
||||
msgstr ""
|
||||
|
||||
@@ -984,7 +1011,7 @@ msgstr ""
|
||||
msgid "Run as administrator"
|
||||
msgstr ""
|
||||
|
||||
msgid "SFTP"
|
||||
msgid "Russian"
|
||||
msgstr ""
|
||||
|
||||
msgid "SOCKS proxy"
|
||||
@@ -999,7 +1026,9 @@ msgstr ""
|
||||
msgid "SSH connection"
|
||||
msgstr ""
|
||||
|
||||
msgid "SSH connection management is now done through the"
|
||||
msgid ""
|
||||
"SSH connection management is now done through the \"Profiles & "
|
||||
"connections\" tab"
|
||||
msgstr ""
|
||||
|
||||
msgid "SSH password for {user}@{host}:{port}"
|
||||
@@ -1137,6 +1166,9 @@ msgstr ""
|
||||
msgid "Show vault contents"
|
||||
msgstr ""
|
||||
|
||||
msgid "Show {type} profile selector"
|
||||
msgstr ""
|
||||
|
||||
msgid "Skip MoTD/banner"
|
||||
msgstr ""
|
||||
|
||||
@@ -1149,6 +1181,9 @@ msgstr ""
|
||||
msgid "Source code"
|
||||
msgstr ""
|
||||
|
||||
msgid "Spanish"
|
||||
msgstr ""
|
||||
|
||||
msgid "Split"
|
||||
msgstr ""
|
||||
|
||||
@@ -1209,69 +1244,12 @@ msgstr ""
|
||||
msgid "Sync window settings"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 1"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 10"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 11"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 12"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 13"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 14"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 15"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 16"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 17"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 18"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 19"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 2"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 20"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 3"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 4"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 5"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 6"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 7"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 8"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 9"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab activity"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab {number}"
|
||||
msgstr ""
|
||||
|
||||
msgid ""
|
||||
"Tabby could not start with your plugins, so all third party plugins have "
|
||||
"been disabled in this session. The error was:"
|
||||
@@ -1289,9 +1267,6 @@ msgstr ""
|
||||
msgid "Tabs width"
|
||||
msgstr ""
|
||||
|
||||
msgid "Telnet"
|
||||
msgstr ""
|
||||
|
||||
msgid "Telnet session"
|
||||
msgstr ""
|
||||
|
||||
@@ -1411,6 +1386,9 @@ msgstr ""
|
||||
msgid "Vault master passphrase needs to be set to allow storing secrets"
|
||||
msgstr ""
|
||||
|
||||
msgid "Verify host keys when connecting"
|
||||
msgstr ""
|
||||
|
||||
msgid "Version"
|
||||
msgstr ""
|
||||
|
||||
@@ -1435,6 +1413,9 @@ msgstr ""
|
||||
msgid "Warn when closing active connections"
|
||||
msgstr ""
|
||||
|
||||
msgid "Warning: remote host's key has suddenly changed!"
|
||||
msgstr ""
|
||||
|
||||
msgid "We're only tracking your Tabby and OS versions."
|
||||
msgstr ""
|
||||
|
||||
@@ -1491,6 +1472,11 @@ msgstr ""
|
||||
msgid "You can change it later, but it's unrecoverable if forgotten."
|
||||
msgstr ""
|
||||
|
||||
msgid ""
|
||||
"You could be under a man-in-the-middle attack right now, or the host key "
|
||||
"could have just been changed."
|
||||
msgstr ""
|
||||
|
||||
msgid "Zoom in"
|
||||
msgstr ""
|
||||
|
||||
@@ -1500,8 +1486,5 @@ msgstr ""
|
||||
msgid "click"
|
||||
msgstr ""
|
||||
|
||||
msgid "tab"
|
||||
msgstr ""
|
||||
|
||||
msgid "{name} copy"
|
||||
msgstr ""
|
1462
locale/de-DE.po
Normal file
1462
locale/de-DE.po
Normal file
File diff suppressed because it is too large
Load Diff
1489
locale/es-ES.po
Normal file
1489
locale/es-ES.po
Normal file
File diff suppressed because it is too large
Load Diff
1489
locale/fr-FR.po
Normal file
1489
locale/fr-FR.po
Normal file
File diff suppressed because it is too large
Load Diff
318
locale/hr-HR.po
318
locale/hr-HR.po
@@ -12,7 +12,7 @@ msgstr ""
|
||||
"Project-Id-Version: tabby\n"
|
||||
"Language-Team: Croatian\n"
|
||||
"Language: hr_HR\n"
|
||||
"PO-Revision-Date: 2022-01-13 23:46\n"
|
||||
"PO-Revision-Date: 2022-01-28 22:42\n"
|
||||
|
||||
msgid "A second font family used to display characters missing in the main font"
|
||||
msgstr "Druga obitelj fontova koja se koristi za prikaz nedostajućih znakova u glavnom fontu"
|
||||
@@ -26,6 +26,9 @@ msgstr "Pozadina u boji akrila"
|
||||
msgid "Add"
|
||||
msgstr "Dodaj"
|
||||
|
||||
msgid "Add a port forward"
|
||||
msgstr ""
|
||||
|
||||
msgid "Add a private key"
|
||||
msgstr "Dodaj privatni ključ"
|
||||
|
||||
@@ -51,7 +54,7 @@ msgid "Agent type"
|
||||
msgstr "Vrsta agenta"
|
||||
|
||||
msgid "Allows opening .bat files in tabs, but breaks some shells"
|
||||
msgstr ""
|
||||
msgstr "Omogućuje otvaranje .bat datoteka u karticama, ali kvari neke ljuske"
|
||||
|
||||
msgid "Allows quickly opening a terminal in the selected folder"
|
||||
msgstr "Omogućuje brzo otvaranje terminala u odabranoj mapi"
|
||||
@@ -81,19 +84,19 @@ msgid "Ask before closing the browser tab"
|
||||
msgstr "Pitaj prije zatvaranja regitra preglednika"
|
||||
|
||||
msgid "Audible"
|
||||
msgstr ""
|
||||
msgstr "Zvukovi"
|
||||
|
||||
msgid "Authentication method"
|
||||
msgstr "Način autentifikacije"
|
||||
|
||||
msgid "Author"
|
||||
msgstr ""
|
||||
msgstr "Autor"
|
||||
|
||||
msgid "Auto"
|
||||
msgstr "Automatski"
|
||||
|
||||
msgid "Auto-open a terminal on app start"
|
||||
msgstr ""
|
||||
msgstr "Automatski otvori terminal tijekom pokretanja programa"
|
||||
|
||||
msgid "Automatic"
|
||||
msgstr "Automatski"
|
||||
@@ -102,10 +105,10 @@ msgid "Automatic Updates"
|
||||
msgstr "Automatska aktualiziranja"
|
||||
|
||||
msgid "Automatically upload changes and check for updates every minute"
|
||||
msgstr ""
|
||||
msgstr "Automatski prenesi promjene i traži nove verzije svake minute"
|
||||
|
||||
msgid "Available"
|
||||
msgstr ""
|
||||
msgstr "Dostupno"
|
||||
|
||||
msgid "Background type"
|
||||
msgstr "Vrsta pozadine"
|
||||
@@ -129,7 +132,7 @@ msgid "Bottom"
|
||||
msgstr "Dolje"
|
||||
|
||||
msgid "Bracketed paste (requires shell support)"
|
||||
msgstr ""
|
||||
msgstr "Umetanje sadržaja s uglatim zagradama (zahtijeva podršku školjke)"
|
||||
|
||||
msgid "Built-in"
|
||||
msgstr "Ugrađeno"
|
||||
@@ -147,6 +150,9 @@ msgid "Check for updates"
|
||||
msgstr "Traži nove verzije"
|
||||
|
||||
msgid "Chinese (simplified)"
|
||||
msgstr "Kineski (pojednostavljeni)"
|
||||
|
||||
msgid "Chinese (traditional)"
|
||||
msgstr ""
|
||||
|
||||
msgid "Ciphers"
|
||||
@@ -159,7 +165,7 @@ msgid "Clear terminal"
|
||||
msgstr "Isprazni terminal"
|
||||
|
||||
msgid "Clipboard"
|
||||
msgstr ""
|
||||
msgstr "Međuspremnik"
|
||||
|
||||
msgid "Close"
|
||||
msgstr "Zatvori"
|
||||
@@ -171,16 +177,16 @@ msgid "Close focused pane"
|
||||
msgstr "Zatvori aktivnu ploču"
|
||||
|
||||
msgid "Close other tabs"
|
||||
msgstr "Zatvori druge registre"
|
||||
msgstr "Zatvori druge kartice"
|
||||
|
||||
msgid "Close tab"
|
||||
msgstr "Zatvori registar"
|
||||
msgstr "Zatvori karticu"
|
||||
|
||||
msgid "Close tabs to the left"
|
||||
msgstr "Zatvori registre prema lijevo"
|
||||
msgstr "Zatvori kartice prema lijevo"
|
||||
|
||||
msgid "Close tabs to the right"
|
||||
msgstr "Zatvori registre prema desno"
|
||||
msgstr "Zatvori kartice prema desno"
|
||||
|
||||
msgid "Color"
|
||||
msgstr "Boja"
|
||||
@@ -210,7 +216,7 @@ msgid "Config uploaded"
|
||||
msgstr "Konfiguracija prenesena"
|
||||
|
||||
msgid "Configs"
|
||||
msgstr ""
|
||||
msgstr "Konfiguracije"
|
||||
|
||||
msgid "Connect through a proxy server"
|
||||
msgstr "Poveži se putem proxy poslužitelja"
|
||||
@@ -228,13 +234,13 @@ msgid "Connection"
|
||||
msgstr "Veza"
|
||||
|
||||
msgid "Connection failed: {error}"
|
||||
msgstr ""
|
||||
msgstr "Veza neuspjela: {error}"
|
||||
|
||||
msgid "Connection name will be used instead"
|
||||
msgstr ""
|
||||
msgstr "Umjesto toga će se koristiti ime veze"
|
||||
|
||||
msgid "Context menu"
|
||||
msgstr ""
|
||||
msgstr "Kontekstni izbornik"
|
||||
|
||||
msgid "Copied"
|
||||
msgstr "Kopirano"
|
||||
@@ -246,7 +252,7 @@ msgid "Copy current path"
|
||||
msgstr "Kopiraj trenutačnu stazu"
|
||||
|
||||
msgid "Copy on select"
|
||||
msgstr ""
|
||||
msgstr "Kopiraj nakon odabiranja"
|
||||
|
||||
msgid "Copy to clipboard"
|
||||
msgstr "Kopiraj u međuspremnik"
|
||||
@@ -254,6 +260,9 @@ msgstr "Kopiraj u međuspremnik"
|
||||
msgid "Could not decrypt config"
|
||||
msgstr "Neuspjelo dešifriranje konfiguracije"
|
||||
|
||||
msgid "Croatian"
|
||||
msgstr ""
|
||||
|
||||
msgid "Current"
|
||||
msgstr "Trenutačno"
|
||||
|
||||
@@ -276,7 +285,7 @@ msgid "Debugging"
|
||||
msgstr "Otklanjanje grešaka"
|
||||
|
||||
msgid "Default profile for new tabs"
|
||||
msgstr "Standardni profil za nove registre"
|
||||
msgstr "Standardni profil za nove kartice"
|
||||
|
||||
msgid "Default profile settings"
|
||||
msgstr "Postavke standardnog profila"
|
||||
@@ -285,7 +294,7 @@ msgid "Defaults"
|
||||
msgstr "Standardne vrijednosti"
|
||||
|
||||
msgid "Defaults for {type}"
|
||||
msgstr ""
|
||||
msgstr "Standardne vrijednosti za {type}"
|
||||
|
||||
msgid "Delete"
|
||||
msgstr "Izbriši"
|
||||
@@ -321,16 +330,16 @@ msgid "Direct"
|
||||
msgstr "Direktno"
|
||||
|
||||
msgid "Disable"
|
||||
msgstr ""
|
||||
msgstr "Deaktiviraj"
|
||||
|
||||
msgid "Disable GPU acceleration"
|
||||
msgstr "Deativiraj ubrzanje GPU-a"
|
||||
|
||||
msgid "Disable dynamic tab title"
|
||||
msgstr ""
|
||||
msgstr "Deaktiviraj dinamički naslov kartice"
|
||||
|
||||
msgid "Disabled"
|
||||
msgstr ""
|
||||
msgstr "Deaktivirano"
|
||||
|
||||
msgid "Display on"
|
||||
msgstr "Ekran uključen"
|
||||
@@ -339,7 +348,7 @@ msgid "Do not abort"
|
||||
msgstr "Nemoj prekinuti"
|
||||
|
||||
msgid "Do not remember"
|
||||
msgstr ""
|
||||
msgstr "Nemoj zapamtiti"
|
||||
|
||||
msgid "Dock always on top"
|
||||
msgstr "Prikvači uvijek gore"
|
||||
@@ -357,13 +366,13 @@ msgid "Docking"
|
||||
msgstr "Prikvačivanje"
|
||||
|
||||
msgid "Double-click selection will stop at these characters"
|
||||
msgstr ""
|
||||
msgstr "Dvostruki pritisak odabira prekinut će pri ovim znakovima"
|
||||
|
||||
msgid "Down"
|
||||
msgstr "Dolje"
|
||||
|
||||
msgid "Download"
|
||||
msgstr ""
|
||||
msgstr "Preuzmi"
|
||||
|
||||
msgid "Duplicate"
|
||||
msgstr "Dupliciraj"
|
||||
@@ -372,7 +381,7 @@ msgid "Duplicate as administrator"
|
||||
msgstr "Dupliciraj kao administratora"
|
||||
|
||||
msgid "Duplicate tab"
|
||||
msgstr "Dupliciraj registar"
|
||||
msgstr "Dupliciraj karticu"
|
||||
|
||||
msgid "Dynamic"
|
||||
msgstr "Dinamički"
|
||||
@@ -381,13 +390,13 @@ msgid "Edit"
|
||||
msgstr "Uredi"
|
||||
|
||||
msgid "Enable"
|
||||
msgstr ""
|
||||
msgstr "Aktiviraj"
|
||||
|
||||
msgid "Enable analytics"
|
||||
msgstr "Aktiviraj analitikčke podatke"
|
||||
|
||||
msgid "Enable automatic installation of updates when they become available."
|
||||
msgstr "Autkiviraj automatsko instaliranje novih verzija kad postanu dostupne."
|
||||
msgstr "Akiviraj automatsko instaliranje novih verzija kad postanu dostupne."
|
||||
|
||||
msgid "Enable font ligatures"
|
||||
msgstr "Aktiviraj ligature fontova"
|
||||
@@ -417,7 +426,7 @@ msgid "Erase the Vault"
|
||||
msgstr "Izbriši trezor"
|
||||
|
||||
msgid "Error in {plugin}:"
|
||||
msgstr ""
|
||||
msgstr "Greška u {plugin}:"
|
||||
|
||||
msgid "Exact match"
|
||||
msgstr "Točno podudaranje"
|
||||
@@ -488,6 +497,9 @@ msgstr "Proslijedi priključak"
|
||||
msgid "Forwarded ports"
|
||||
msgstr "Proslijeđeni priključci"
|
||||
|
||||
msgid "French"
|
||||
msgstr ""
|
||||
|
||||
msgid "From color scheme"
|
||||
msgstr "Iz sheme boja"
|
||||
|
||||
@@ -495,7 +507,7 @@ msgid "From theme"
|
||||
msgstr "Iz teme"
|
||||
|
||||
msgid "Frontend"
|
||||
msgstr ""
|
||||
msgstr "Sučelje"
|
||||
|
||||
msgid "Full"
|
||||
msgstr "Potpuno"
|
||||
@@ -506,14 +518,14 @@ msgstr "Opće"
|
||||
msgid "Generate a pre-filled GitHub issue"
|
||||
msgstr "Generiraj unaprijed ispunjeni GitHub problem"
|
||||
|
||||
msgid "Get"
|
||||
msgid "German"
|
||||
msgstr ""
|
||||
|
||||
msgid "Get"
|
||||
msgstr "Preuzmi"
|
||||
|
||||
msgid "Get it from the Tabby Web settings window"
|
||||
msgstr ""
|
||||
|
||||
msgid "GitHub"
|
||||
msgstr ""
|
||||
msgstr "Preuzmi iz prozora Tabby-web postavki"
|
||||
|
||||
msgid "Gives the window a blurred transparent background"
|
||||
msgstr "Daje prozoru zamućenu prozirnu pozadinu"
|
||||
@@ -525,7 +537,7 @@ msgid "Green"
|
||||
msgstr "Zelena"
|
||||
|
||||
msgid "Group"
|
||||
msgstr ""
|
||||
msgstr "Grupa"
|
||||
|
||||
msgid "Help track the number of Tabby installs across the world!"
|
||||
msgstr "Pomogni pratiti broj Tabby instalacija diljem svijeta!"
|
||||
@@ -534,31 +546,31 @@ msgid "Hexadecimal"
|
||||
msgstr "Heksadecimalni"
|
||||
|
||||
msgid "Hide tab close button"
|
||||
msgstr "Sakrij gumb za zatvaranje registra"
|
||||
msgstr "Sakrij gumb za zatvaranje kartice"
|
||||
|
||||
msgid "Hide tab index"
|
||||
msgstr "Sakrij indeks registra"
|
||||
msgstr "Sakrij indeks kartice"
|
||||
|
||||
msgid "Hide window on focus loss"
|
||||
msgstr ""
|
||||
msgstr "Sakrij prozor kad nije aktivan"
|
||||
|
||||
msgid "Hides the docked terminal when you click away."
|
||||
msgstr "Skriva prikvačeni terminal kad pritisneš negdje drugdje."
|
||||
|
||||
msgid "Homepage"
|
||||
msgstr ""
|
||||
msgstr "Naslovnica"
|
||||
|
||||
msgid "Host"
|
||||
msgstr "Host"
|
||||
msgstr "Host računalo"
|
||||
|
||||
msgid "Host key"
|
||||
msgstr "Ključ hosta"
|
||||
msgstr "Tipka host računala"
|
||||
|
||||
msgid "Hotkeys"
|
||||
msgstr "Tipkovni prečaci"
|
||||
|
||||
msgid "Icon"
|
||||
msgstr ""
|
||||
msgstr "Ikona"
|
||||
|
||||
msgid "If disabled, only custom profiles will show up in the profile selector"
|
||||
msgstr "Ako je deaktivirano, u biraču profila prikazat će se samo prilagođeni profili"
|
||||
@@ -576,10 +588,10 @@ msgid "Input newlines"
|
||||
msgstr "Upiši nove retke"
|
||||
|
||||
msgid "Installed"
|
||||
msgstr ""
|
||||
msgstr "Instalirano"
|
||||
|
||||
msgid "Installing the update will close all tabs and restart Tabby."
|
||||
msgstr "Instaliranjem nove verzije zatvorit će se svi registri i Tabby će se ponovo pokrenuti."
|
||||
msgstr "Instaliranjem nove verzije zatvorit će se sve kartice i Tabby će se ponovo pokrenuti."
|
||||
|
||||
msgid "Intelligent Ctrl-C (copy/abort)"
|
||||
msgstr "Inteligenti Ctrl-C (kopiraj/prekini)"
|
||||
@@ -633,7 +645,7 @@ msgid "Left"
|
||||
msgstr "Lijevo"
|
||||
|
||||
msgid "Lets the shell handle Meta key instead of OS"
|
||||
msgstr ""
|
||||
msgstr "Omogućuje ljusci baratanje meta-tipkom umjesto OS-a"
|
||||
|
||||
msgid "Line by line"
|
||||
msgstr "Redak po redak"
|
||||
@@ -648,7 +660,7 @@ msgid "Loading"
|
||||
msgstr "Učitavanje"
|
||||
|
||||
msgid "Loading configs..."
|
||||
msgstr ""
|
||||
msgstr "Učitavanje konfiguracija …"
|
||||
|
||||
msgid "Local"
|
||||
msgstr "Lokalno"
|
||||
@@ -663,7 +675,7 @@ msgid "Login scripts"
|
||||
msgstr "Skripta za prijavu"
|
||||
|
||||
msgid "Long-click for context menu"
|
||||
msgstr ""
|
||||
msgstr "Pritisni dugo za kontekstni izbornik"
|
||||
|
||||
msgid "Manage profiles"
|
||||
msgstr "Upravljaj profilima"
|
||||
@@ -675,16 +687,16 @@ msgid "Maximize the active pane"
|
||||
msgstr "Maksimalno proširi aktivnu ploču"
|
||||
|
||||
msgid "Modified on {date}"
|
||||
msgstr ""
|
||||
msgstr "Promijenjeno {date}"
|
||||
|
||||
msgid "Move tab to the left"
|
||||
msgstr "Pomakni registar na lijevo"
|
||||
msgstr "Premjesti karticu lijevo"
|
||||
|
||||
msgid "Move tab to the right"
|
||||
msgstr "Pomakni registar na desno"
|
||||
msgstr "Premjesti karticu desno"
|
||||
|
||||
msgid "Move to \"Ungrouped\""
|
||||
msgstr "Premjeti u „Negrupirani”"
|
||||
msgstr "Premjesti u „Negrupirani”"
|
||||
|
||||
msgid "Name"
|
||||
msgstr "Ime"
|
||||
@@ -692,14 +704,11 @@ msgstr "Ime"
|
||||
msgid "Name for the new config"
|
||||
msgstr "Ime nove konfiguracije"
|
||||
|
||||
msgid "Named pipe"
|
||||
msgstr "Imenovani proces"
|
||||
|
||||
msgid "Native"
|
||||
msgstr "Izvorni"
|
||||
|
||||
msgid "New admin tab"
|
||||
msgstr "Registar za novog administratora"
|
||||
msgstr "Kartica za novog administratora"
|
||||
|
||||
msgid "New config on {platform}"
|
||||
msgstr "Nova konfiguracija na {platform}"
|
||||
@@ -719,6 +728,9 @@ msgstr "Ime novog profila"
|
||||
msgid "New tab"
|
||||
msgstr "Nova kartica"
|
||||
|
||||
msgid "New tab: {profile}"
|
||||
msgstr ""
|
||||
|
||||
msgid "New terminal"
|
||||
msgstr "Novi terminal"
|
||||
|
||||
@@ -735,7 +747,7 @@ msgid "No color"
|
||||
msgstr "Bez boje"
|
||||
|
||||
msgid "No modifier"
|
||||
msgstr ""
|
||||
msgstr "Bez modifikatora"
|
||||
|
||||
msgid "None"
|
||||
msgstr "Ništa"
|
||||
@@ -753,7 +765,7 @@ msgid "Notify when done"
|
||||
msgstr "Obavijesti kad ja gotovo"
|
||||
|
||||
msgid "Number of lines kept in the buffer"
|
||||
msgstr ""
|
||||
msgstr "Broj redaka zadržanih u predmemoriji"
|
||||
|
||||
msgid "OS default"
|
||||
msgstr "Standard sustava"
|
||||
@@ -765,7 +777,7 @@ msgid "Off"
|
||||
msgstr "Isključi"
|
||||
|
||||
msgid "Official"
|
||||
msgstr ""
|
||||
msgstr "Službeno"
|
||||
|
||||
msgid "On GitHub Discussions"
|
||||
msgstr "Na GitHub diskusijama"
|
||||
@@ -821,14 +833,11 @@ msgstr "Prepisati konfiguraciju na udaljenoj strani i započeti sinkronizaciju?"
|
||||
msgid "Overwrite the local config and start syncing?"
|
||||
msgstr "Prepisati lokalnu konfiguraciju i započeti sinkronizaciju?"
|
||||
|
||||
msgid "Paper"
|
||||
msgstr "Papir"
|
||||
|
||||
msgid "Parity"
|
||||
msgstr "Paritet"
|
||||
|
||||
msgid "Partial config sync is not possible when the config is encrypted via Vault."
|
||||
msgstr ""
|
||||
msgstr "Djelomično sinkroniziranje konfiguracije nije moguće kad je konfiguracija šifrirana putem trezora."
|
||||
|
||||
msgid "Passphrase for a private key with hash {hash}..."
|
||||
msgstr "Tekstualna lozinka za privatni ključ s hashem {hash}..."
|
||||
@@ -846,7 +855,7 @@ msgid "Paste multiple lines?"
|
||||
msgstr "Umetnuti višestruke retke?"
|
||||
|
||||
msgid "Paste on middle-click"
|
||||
msgstr ""
|
||||
msgstr "Umetni pritiskom srednjeg gumba miša"
|
||||
|
||||
msgid "Path or address of the local X11 socket"
|
||||
msgstr "Staza ili adresa lokalne X11 utičnice"
|
||||
@@ -855,9 +864,12 @@ msgid "Pin"
|
||||
msgstr "Prikvači"
|
||||
|
||||
msgid "Plugins"
|
||||
msgstr ""
|
||||
msgstr "Dodaci"
|
||||
|
||||
msgid "Plugins folder"
|
||||
msgstr "Mapa dodataka"
|
||||
|
||||
msgid "Polish"
|
||||
msgstr ""
|
||||
|
||||
msgid "Port"
|
||||
@@ -873,10 +885,10 @@ msgid "Prevents accidental closing"
|
||||
msgstr "Sprečava slučajno zatvaranje"
|
||||
|
||||
msgid "Prevents accidental execution of pasted commands"
|
||||
msgstr ""
|
||||
msgstr "Sprečava slučajno izvršavanje umetnutih naredbi"
|
||||
|
||||
msgid "Previous tab"
|
||||
msgstr "Prethodni registar"
|
||||
msgstr "Prethodna kartica"
|
||||
|
||||
msgid "Private keys"
|
||||
msgstr "Privatni ključevi"
|
||||
@@ -893,9 +905,6 @@ msgstr "Profili"
|
||||
msgid "Profiles & connections"
|
||||
msgstr "Profili i veze"
|
||||
|
||||
msgid "Profiles and connections"
|
||||
msgstr "Profili i veze"
|
||||
|
||||
msgid "Program"
|
||||
msgstr "Program"
|
||||
|
||||
@@ -936,7 +945,7 @@ msgid "Release notes"
|
||||
msgstr "Napomene uz izdanje"
|
||||
|
||||
msgid "Remember for {time}"
|
||||
msgstr ""
|
||||
msgstr "Zapamti {time}"
|
||||
|
||||
msgid "Remote"
|
||||
msgstr "Udaljeni repozitorij"
|
||||
@@ -948,7 +957,7 @@ msgid "Rename Tab"
|
||||
msgstr "Preimenuj karticu"
|
||||
|
||||
msgid "Rendering"
|
||||
msgstr ""
|
||||
msgstr "Iscrtavanje"
|
||||
|
||||
msgid "Reopen last tab"
|
||||
msgstr "Ponovo otvori zadnju karticu"
|
||||
@@ -960,7 +969,7 @@ msgid "Report a problem"
|
||||
msgstr "Prijavi problem"
|
||||
|
||||
msgid "Require a key to click links"
|
||||
msgstr ""
|
||||
msgstr "Zatraži tipku za pritiskanje poveznica"
|
||||
|
||||
msgid "Reset zoom"
|
||||
msgstr "Resetiraj uvećanje"
|
||||
@@ -978,28 +987,28 @@ msgid "Restart the app to apply changes"
|
||||
msgstr "Za primjenu promjena ponovo pokreni program"
|
||||
|
||||
msgid "Restore terminal tabs on app start"
|
||||
msgstr ""
|
||||
msgstr "Obnovi kartice terminala tijekom pokretanja programa"
|
||||
|
||||
msgid "Reuse session for multiple tabs"
|
||||
msgstr "Ponovo koristi sesiju za više registratora"
|
||||
msgstr "Ponovo koristi sesiju za više kartica"
|
||||
|
||||
msgid "Right"
|
||||
msgstr "Desno"
|
||||
|
||||
msgid "Right click"
|
||||
msgstr ""
|
||||
msgstr "Pritisni desnu tipku miša"
|
||||
|
||||
msgid "Run as administrator"
|
||||
msgstr "Pokreni kao administrator"
|
||||
|
||||
msgid "SFTP"
|
||||
msgstr "SFTP"
|
||||
msgid "Russian"
|
||||
msgstr ""
|
||||
|
||||
msgid "SOCKS proxy"
|
||||
msgstr "SOCKS proxy"
|
||||
|
||||
msgid "SOCKS proxy host"
|
||||
msgstr "SOCKS proxy računalo"
|
||||
msgstr "SOCKS proxy host računalo"
|
||||
|
||||
msgid "SOCKS proxy port"
|
||||
msgstr "SOCKS proxy priključak"
|
||||
@@ -1007,8 +1016,8 @@ msgstr "SOCKS proxy priključak"
|
||||
msgid "SSH connection"
|
||||
msgstr "SSH veza"
|
||||
|
||||
msgid "SSH connection management is now done through the"
|
||||
msgstr "Upravljanje SSH vezom sada se vrši putem"
|
||||
msgid "SSH connection management is now done through the \"Profiles & connections\" tab"
|
||||
msgstr ""
|
||||
|
||||
msgid "SSH password for {user}@{host}:{port}"
|
||||
msgstr "SSH lozinka za {user}@{host}:{port}"
|
||||
@@ -1035,22 +1044,22 @@ msgid "Saved layout"
|
||||
msgstr "Spremljeni raspored"
|
||||
|
||||
msgid "Scroll on input"
|
||||
msgstr ""
|
||||
msgstr "Pomakni nakon unosa"
|
||||
|
||||
msgid "Scroll terminal to bottom"
|
||||
msgstr ""
|
||||
msgstr "Pomakni terminal na kraj"
|
||||
|
||||
msgid "Scrollback"
|
||||
msgstr ""
|
||||
msgstr "Pomicanje unatrag"
|
||||
|
||||
msgid "Scrolls the terminal to the bottom on user input"
|
||||
msgstr ""
|
||||
msgstr "Pomiče terminal na kraj nakon unosa korisnika"
|
||||
|
||||
msgid "Search"
|
||||
msgstr "Pretraga"
|
||||
|
||||
msgid "Secret sync token"
|
||||
msgstr ""
|
||||
msgstr "Tajni token za sinkronizaciju"
|
||||
|
||||
msgid "Select"
|
||||
msgstr "Odaberi"
|
||||
@@ -1083,7 +1092,7 @@ msgid "Serial: {description}"
|
||||
msgstr "Serijski priključak: {description}"
|
||||
|
||||
msgid "Set Tabby as %COMSPEC%"
|
||||
msgstr ""
|
||||
msgstr "Postavi Tabby kao %COMSPEC%"
|
||||
|
||||
msgid "Set master passphrase"
|
||||
msgstr "Postavi tekstualnu master lozinku"
|
||||
@@ -1113,13 +1122,13 @@ msgid "Shell integration"
|
||||
msgstr "Integracija ljuske"
|
||||
|
||||
msgid "Show Mixer"
|
||||
msgstr ""
|
||||
msgstr "Prikaži mikser"
|
||||
|
||||
msgid "Show Serial connections"
|
||||
msgstr "Prikaži veze serijskih priključaka"
|
||||
|
||||
msgid "Show a confirmation box when pasting multiple lines"
|
||||
msgstr ""
|
||||
msgstr "Prikaži okvir za potvrdu prilikom umetanja više redaka"
|
||||
|
||||
msgid "Show built-in profiles in selector"
|
||||
msgstr "Prikaži ugrađene profile u selektoru"
|
||||
@@ -1145,6 +1154,9 @@ msgstr "Prikaži napomene uz izdanje"
|
||||
msgid "Show vault contents"
|
||||
msgstr "Prikaži sadržaj trezora"
|
||||
|
||||
msgid "Show {type} profile selector"
|
||||
msgstr ""
|
||||
|
||||
msgid "Skip MoTD/banner"
|
||||
msgstr "Preskoči MoTD/banner"
|
||||
|
||||
@@ -1157,6 +1169,9 @@ msgstr "Privlači prozor na jednu stranu ekrana"
|
||||
msgid "Source code"
|
||||
msgstr "Izvorni kod"
|
||||
|
||||
msgid "Spanish"
|
||||
msgstr ""
|
||||
|
||||
msgid "Split"
|
||||
msgstr "Podijeli"
|
||||
|
||||
@@ -1176,7 +1191,7 @@ msgid "Standard"
|
||||
msgstr "Standardno"
|
||||
|
||||
msgid "Startup"
|
||||
msgstr ""
|
||||
msgstr "Pokretanje"
|
||||
|
||||
msgid "Stop bits"
|
||||
msgstr "Bitovi prekida"
|
||||
@@ -1197,88 +1212,31 @@ msgid "Switch profile in the active pane"
|
||||
msgstr "Zamijeni profil u trenutačnoj ploči"
|
||||
|
||||
msgid "Switches terminal frontend implementation (experimental)"
|
||||
msgstr ""
|
||||
msgstr "Zamjenjuje implementaciju sučelja terminala (eksperimentalno)"
|
||||
|
||||
msgid "Sync"
|
||||
msgstr ""
|
||||
msgstr "Sinkronizraj"
|
||||
|
||||
msgid "Sync Vault"
|
||||
msgstr ""
|
||||
msgstr "Sinkronizraj trezor"
|
||||
|
||||
msgid "Sync automatically"
|
||||
msgstr ""
|
||||
msgstr "Sinkronizraj automatski"
|
||||
|
||||
msgid "Sync host"
|
||||
msgstr ""
|
||||
msgstr "Sinkronizraj host računalo"
|
||||
|
||||
msgid "Sync hotkeys"
|
||||
msgstr ""
|
||||
msgstr "Sinkronizraj tipkovne prečace"
|
||||
|
||||
msgid "Sync window settings"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tab 1"
|
||||
msgstr "Registar 1"
|
||||
|
||||
msgid "Tab 10"
|
||||
msgstr "Registar 10"
|
||||
|
||||
msgid "Tab 11"
|
||||
msgstr "Registar 11"
|
||||
|
||||
msgid "Tab 12"
|
||||
msgstr "Registar 12"
|
||||
|
||||
msgid "Tab 13"
|
||||
msgstr "Registar 13"
|
||||
|
||||
msgid "Tab 14"
|
||||
msgstr "Registar 14"
|
||||
|
||||
msgid "Tab 15"
|
||||
msgstr "Registar 15"
|
||||
|
||||
msgid "Tab 16"
|
||||
msgstr "Registar 16"
|
||||
|
||||
msgid "Tab 17"
|
||||
msgstr "Registar 17"
|
||||
|
||||
msgid "Tab 18"
|
||||
msgstr "Registar 18"
|
||||
|
||||
msgid "Tab 19"
|
||||
msgstr "Registar 19"
|
||||
|
||||
msgid "Tab 2"
|
||||
msgstr "Registar 2"
|
||||
|
||||
msgid "Tab 20"
|
||||
msgstr "Registar 20"
|
||||
|
||||
msgid "Tab 3"
|
||||
msgstr "Registar 3"
|
||||
|
||||
msgid "Tab 4"
|
||||
msgstr "Registar 4"
|
||||
|
||||
msgid "Tab 5"
|
||||
msgstr "Registar 5"
|
||||
|
||||
msgid "Tab 6"
|
||||
msgstr "Registar 6"
|
||||
|
||||
msgid "Tab 7"
|
||||
msgstr "Registar 7"
|
||||
|
||||
msgid "Tab 8"
|
||||
msgstr "Registar 8"
|
||||
|
||||
msgid "Tab 9"
|
||||
msgstr "Registar 9"
|
||||
msgstr "Sinkronizraj postavke prozora"
|
||||
|
||||
msgid "Tab activity"
|
||||
msgstr "Aktivnost u registru"
|
||||
msgstr "Aktivnost kartice"
|
||||
|
||||
msgid "Tab {number}"
|
||||
msgstr ""
|
||||
|
||||
msgid "Tabby could not start with your plugins, so all third party plugins have been disabled in this session. The error was:"
|
||||
msgstr "Tabby se nije mogao pokrenuti s tvojim dodacima, stoga su svi strani dodaci deaktivirani u ovoj sesiji. Greška je bila:"
|
||||
@@ -1287,16 +1245,13 @@ msgid "Tabby news and updates on Twitter"
|
||||
msgstr "Tabby novosti i nove verzje na Twitteru"
|
||||
|
||||
msgid "Tabs"
|
||||
msgstr "Registri"
|
||||
msgstr "Kartice"
|
||||
|
||||
msgid "Tabs location"
|
||||
msgstr "Mjesto registara"
|
||||
msgstr "Mjesto kartica"
|
||||
|
||||
msgid "Tabs width"
|
||||
msgstr "Širina registara"
|
||||
|
||||
msgid "Telnet"
|
||||
msgstr "Telnet"
|
||||
msgstr "Širina kartica"
|
||||
|
||||
msgid "Telnet session"
|
||||
msgstr "Telnet sesija"
|
||||
@@ -1308,7 +1263,7 @@ msgid "Terminal background"
|
||||
msgstr "Pozadina terminala"
|
||||
|
||||
msgid "Terminal bell"
|
||||
msgstr ""
|
||||
msgstr "Zvono terminala"
|
||||
|
||||
msgid "Thank you for downloading Tabby!"
|
||||
msgstr "Zahvaljujemo na preuzimanju programa Tabby!"
|
||||
@@ -1335,7 +1290,7 @@ msgid "Toggle fullscreen mode"
|
||||
msgstr "Uključi/isključi cjeloekranski prikaz"
|
||||
|
||||
msgid "Toggle last tab"
|
||||
msgstr "Uključi/isključi zadnji registar"
|
||||
msgstr "Uključi/isključi zadnju karticu"
|
||||
|
||||
msgid "Toggle terminal window"
|
||||
msgstr "Uključi/isključi prozor terminala"
|
||||
@@ -1356,7 +1311,7 @@ msgid "Ungrouped"
|
||||
msgstr "Negrupirani"
|
||||
|
||||
msgid "Uninstall"
|
||||
msgstr ""
|
||||
msgstr "Deinstaliraj"
|
||||
|
||||
msgid "Unknown"
|
||||
msgstr "Nepoznato"
|
||||
@@ -1374,19 +1329,19 @@ msgid "Update"
|
||||
msgstr "Aktualiziraj"
|
||||
|
||||
msgid "Upgrade to {version}"
|
||||
msgstr ""
|
||||
msgstr "Nadogradi na {version}"
|
||||
|
||||
msgid "Upload"
|
||||
msgstr "Prenesi"
|
||||
|
||||
msgid "Upload as a new config"
|
||||
msgstr ""
|
||||
msgstr "Prenesi kao novu konfiguraciju"
|
||||
|
||||
msgid "Use ConPTY"
|
||||
msgstr "Koristi ConPTY"
|
||||
|
||||
msgid "Use {altKeyName} as the Meta key"
|
||||
msgstr ""
|
||||
msgstr "Koristi {altKeyName} kao meta-tipku"
|
||||
|
||||
msgid "User default"
|
||||
msgstr "Korisnički standard"
|
||||
@@ -1416,25 +1371,25 @@ msgid "Vault master passphrase needs to be set to allow storing secrets"
|
||||
msgstr "Za spremanje tajni, tekstualna master lozinka trezora mora biti postavljena"
|
||||
|
||||
msgid "Version"
|
||||
msgstr ""
|
||||
msgstr "Verzija"
|
||||
|
||||
msgid "Version: {version}"
|
||||
msgstr ""
|
||||
msgstr "Verzija: {version}"
|
||||
|
||||
msgid "Vibrancy"
|
||||
msgstr "Svjetlost"
|
||||
|
||||
msgid "Visual"
|
||||
msgstr ""
|
||||
msgstr "Prikaz"
|
||||
|
||||
msgid "WSL terminal bell can only be muted via Volume Mixer"
|
||||
msgstr ""
|
||||
msgstr "Zvono WSL terminala može se isključiti samo putem miksera glasnoće"
|
||||
|
||||
msgid "WSL terminal only supports TrueColor with ConPTY"
|
||||
msgstr "WSL terminal podržava samo TrueColor s ConPTY"
|
||||
|
||||
msgid "Warn on multi-line paste"
|
||||
msgstr ""
|
||||
msgstr "Upozori prilikom umetanja više redaka"
|
||||
|
||||
msgid "Warn when closing active connections"
|
||||
msgstr "Upozori pri zatvaranju aktivnih veza"
|
||||
@@ -1452,7 +1407,7 @@ msgid "When WinSCP is detected, you can launch an SCP session from the context m
|
||||
msgstr "Kad se otkrije WinSCP, SCP sesiju možeš prekinuti iz kontekstualnog izbornika."
|
||||
|
||||
msgid "When enabled, links are only clickable while holding this key"
|
||||
msgstr ""
|
||||
msgstr "Kad je aktivirano, veze se mogu pritisnuti samo dok držiš ovu tipku"
|
||||
|
||||
msgid "Whether a custom window or an OS native window should be used"
|
||||
msgstr "Da li koristiti prilagođeni prozor ili izvorni prozor OS-a"
|
||||
@@ -1464,10 +1419,10 @@ msgid "Window"
|
||||
msgstr "Prozor"
|
||||
|
||||
msgid "Window dimension along the edge"
|
||||
msgstr ""
|
||||
msgstr "Dimenzija prozora uz rub"
|
||||
|
||||
msgid "Window dimension away from the edge"
|
||||
msgstr ""
|
||||
msgstr "Dimenzija prozora od ruba"
|
||||
|
||||
msgid "Window frame"
|
||||
msgstr "Okvir prozora"
|
||||
@@ -1476,7 +1431,7 @@ msgid "Windows 10 build 18309 or above is recommended for ConPTY"
|
||||
msgstr "Za ConPTY se preporučuje Windows 10 gradnja 18309 ili novija"
|
||||
|
||||
msgid "Word separators"
|
||||
msgstr ""
|
||||
msgstr "Znakovi razdvajanja riječi"
|
||||
|
||||
msgid "Working directory"
|
||||
msgstr "Radna mapa"
|
||||
@@ -1502,9 +1457,6 @@ msgstr "Umanji prikaz"
|
||||
msgid "click"
|
||||
msgstr "pritisni"
|
||||
|
||||
msgid "tab"
|
||||
msgstr "registar"
|
||||
|
||||
msgid "{name} copy"
|
||||
msgstr "kopija {name}"
|
||||
|
||||
|
1462
locale/pl-PL.po
Normal file
1462
locale/pl-PL.po
Normal file
File diff suppressed because it is too large
Load Diff
1462
locale/ru-RU.po
Normal file
1462
locale/ru-RU.po
Normal file
File diff suppressed because it is too large
Load Diff
203
locale/zh-CN.po
203
locale/zh-CN.po
@@ -12,7 +12,7 @@ msgstr ""
|
||||
"Project-Id-Version: tabby\n"
|
||||
"Language-Team: Chinese Simplified\n"
|
||||
"Language: zh_CN\n"
|
||||
"PO-Revision-Date: 2022-01-15 14:12\n"
|
||||
"PO-Revision-Date: 2022-01-30 20:02\n"
|
||||
|
||||
msgid "A second font family used to display characters missing in the main font"
|
||||
msgstr "第二种字体,用于显示主字体中缺失的字符"
|
||||
@@ -20,12 +20,21 @@ msgstr "第二种字体,用于显示主字体中缺失的字符"
|
||||
msgid "Abort all"
|
||||
msgstr "中止全部"
|
||||
|
||||
msgid "Accept and remember key"
|
||||
msgstr "接受并记住密钥"
|
||||
|
||||
msgid "Accept just this once"
|
||||
msgstr "只接受本次"
|
||||
|
||||
msgid "Acrylic background"
|
||||
msgstr "亚克力背景"
|
||||
|
||||
msgid "Add"
|
||||
msgstr "添加"
|
||||
|
||||
msgid "Add a port forward"
|
||||
msgstr "添加端口转发"
|
||||
|
||||
msgid "Add a private key"
|
||||
msgstr "添加私钥"
|
||||
|
||||
@@ -51,7 +60,7 @@ msgid "Agent type"
|
||||
msgstr "Agent 类型"
|
||||
|
||||
msgid "Allows opening .bat files in tabs, but breaks some shells"
|
||||
msgstr "允许在选项卡中打开.bat文件,但会中断一些shell"
|
||||
msgstr "允许在标签页中打开.bat文件,但会中断某些shell"
|
||||
|
||||
msgid "Allows quickly opening a terminal in the selected folder"
|
||||
msgstr "允许在选定的文件夹中快速打开终端"
|
||||
@@ -66,7 +75,7 @@ msgid "Application settings"
|
||||
msgstr "应用程序设置"
|
||||
|
||||
msgid "Are you sure you want to close Tabby? You can disable this prompt in Settings -> Window."
|
||||
msgstr "您确定要关闭 Tabby 吗?您可以在设置 -> 窗口中关闭此提示"
|
||||
msgstr "您确定要关闭 Tabby 吗?您可以在 设置 -> 窗口 中关闭此提示。"
|
||||
|
||||
msgid "Are you sure?"
|
||||
msgstr "您确定吗?"
|
||||
@@ -81,19 +90,19 @@ msgid "Ask before closing the browser tab"
|
||||
msgstr "关闭标签页前询问"
|
||||
|
||||
msgid "Audible"
|
||||
msgstr "有声"
|
||||
msgstr "声音"
|
||||
|
||||
msgid "Authentication method"
|
||||
msgstr "身份验证方法"
|
||||
|
||||
msgid "Author"
|
||||
msgstr "开发者"
|
||||
msgstr "作者"
|
||||
|
||||
msgid "Auto"
|
||||
msgstr "自动"
|
||||
|
||||
msgid "Auto-open a terminal on app start"
|
||||
msgstr "在应用程序启动时自动打开终端"
|
||||
msgstr "在应用程序启动时自动打开一个终端窗口"
|
||||
|
||||
msgid "Automatic"
|
||||
msgstr "自动"
|
||||
@@ -123,13 +132,13 @@ msgid "Blue"
|
||||
msgstr "蓝色"
|
||||
|
||||
msgid "Blur"
|
||||
msgstr "模糊化"
|
||||
msgstr "模糊"
|
||||
|
||||
msgid "Bottom"
|
||||
msgstr "底部"
|
||||
|
||||
msgid "Bracketed paste (requires shell support)"
|
||||
msgstr "括号粘贴(需要 Shell 支持)"
|
||||
msgstr "Bracketed 粘贴(需要 Shell 支持)"
|
||||
|
||||
msgid "Built-in"
|
||||
msgstr "内置"
|
||||
@@ -149,6 +158,9 @@ msgstr "检查更新"
|
||||
msgid "Chinese (simplified)"
|
||||
msgstr "中文(简体)"
|
||||
|
||||
msgid "Chinese (traditional)"
|
||||
msgstr "中文(繁体)"
|
||||
|
||||
msgid "Ciphers"
|
||||
msgstr "加密方法"
|
||||
|
||||
@@ -171,7 +183,7 @@ msgid "Close focused pane"
|
||||
msgstr "关闭已聚焦窗格"
|
||||
|
||||
msgid "Close other tabs"
|
||||
msgstr "关闭其它标签"
|
||||
msgstr "关闭其它标签页"
|
||||
|
||||
msgid "Close tab"
|
||||
msgstr "关闭标签页"
|
||||
@@ -254,12 +266,18 @@ msgstr "复制到剪贴板"
|
||||
msgid "Could not decrypt config"
|
||||
msgstr "无法解密配置"
|
||||
|
||||
msgid "Croatian"
|
||||
msgstr "克罗地亚语"
|
||||
|
||||
msgid "Current"
|
||||
msgstr "当前"
|
||||
|
||||
msgid "Current color scheme"
|
||||
msgstr "当前配色方案"
|
||||
|
||||
msgid "Current host key fingerprint"
|
||||
msgstr "当前主机密钥指纹"
|
||||
|
||||
msgid "Current process: {name}"
|
||||
msgstr "当前进程:{name}"
|
||||
|
||||
@@ -276,7 +294,7 @@ msgid "Debugging"
|
||||
msgstr "调试"
|
||||
|
||||
msgid "Default profile for new tabs"
|
||||
msgstr "新标签页默认配置"
|
||||
msgstr "新标签页的默认配置"
|
||||
|
||||
msgid "Default profile settings"
|
||||
msgstr "默认配置设置"
|
||||
@@ -332,6 +350,9 @@ msgstr "禁用动态标签页标题"
|
||||
msgid "Disabled"
|
||||
msgstr "已禁用"
|
||||
|
||||
msgid "Disconnect"
|
||||
msgstr "断开连接"
|
||||
|
||||
msgid "Display on"
|
||||
msgstr "显示于"
|
||||
|
||||
@@ -339,19 +360,19 @@ msgid "Do not abort"
|
||||
msgstr "不要中止"
|
||||
|
||||
msgid "Do not remember"
|
||||
msgstr "不要记住"
|
||||
msgstr "不记住"
|
||||
|
||||
msgid "Dock always on top"
|
||||
msgstr "窗口置顶"
|
||||
msgstr "窗口保持置顶"
|
||||
|
||||
msgid "Dock the terminal"
|
||||
msgstr "停靠终端"
|
||||
|
||||
msgid "Docked terminal size"
|
||||
msgstr "停靠终端大小"
|
||||
msgstr "停靠的终端大小"
|
||||
|
||||
msgid "Docked terminal space"
|
||||
msgstr "停靠终端空间"
|
||||
msgstr "停靠的终端空间"
|
||||
|
||||
msgid "Docking"
|
||||
msgstr "停靠"
|
||||
@@ -488,6 +509,9 @@ msgstr "转发端口"
|
||||
msgid "Forwarded ports"
|
||||
msgstr "已转发端口"
|
||||
|
||||
msgid "French"
|
||||
msgstr "法语"
|
||||
|
||||
msgid "From color scheme"
|
||||
msgstr "来自配色方案"
|
||||
|
||||
@@ -506,15 +530,15 @@ msgstr "通用"
|
||||
msgid "Generate a pre-filled GitHub issue"
|
||||
msgstr "生成一个预填写的 GitHub 问题"
|
||||
|
||||
msgid "German"
|
||||
msgstr "德语"
|
||||
|
||||
msgid "Get"
|
||||
msgstr "获取"
|
||||
|
||||
msgid "Get it from the Tabby Web settings window"
|
||||
msgstr "从 Tabby Web 设置窗口获取"
|
||||
|
||||
msgid "GitHub"
|
||||
msgstr "GitHub"
|
||||
|
||||
msgid "Gives the window a blurred transparent background"
|
||||
msgstr "使窗口具有模糊透明的背景"
|
||||
|
||||
@@ -528,7 +552,7 @@ msgid "Group"
|
||||
msgstr "分组"
|
||||
|
||||
msgid "Help track the number of Tabby installs across the world!"
|
||||
msgstr "帮助跟踪 Tabby 在世界各地的安装次数!"
|
||||
msgstr "帮助追踪 Tabby 在世界各地的安装次数!"
|
||||
|
||||
msgid "Hexadecimal"
|
||||
msgstr "十六进制"
|
||||
@@ -554,6 +578,9 @@ msgstr "主机"
|
||||
msgid "Host key"
|
||||
msgstr "主机密钥"
|
||||
|
||||
msgid "Host key verification"
|
||||
msgstr "主机密钥校验"
|
||||
|
||||
msgid "Hotkeys"
|
||||
msgstr "快捷键"
|
||||
|
||||
@@ -579,7 +606,7 @@ msgid "Installed"
|
||||
msgstr "已安装"
|
||||
|
||||
msgid "Installing the update will close all tabs and restart Tabby."
|
||||
msgstr "安装更新将关闭全部标签页并重启Tabby"
|
||||
msgstr "安装更新将关闭全部标签页并重启 Tabby。"
|
||||
|
||||
msgid "Intelligent Ctrl-C (copy/abort)"
|
||||
msgstr "智能 Ctrl-C (复制/中止)"
|
||||
@@ -620,6 +647,9 @@ msgstr "键盘交互认证"
|
||||
msgid "Language"
|
||||
msgstr "语言"
|
||||
|
||||
msgid "Last known host key fingerprint"
|
||||
msgstr "最后已知的主机密钥指纹"
|
||||
|
||||
msgid "Launch WinSCP"
|
||||
msgstr "启动 WinSCP"
|
||||
|
||||
@@ -627,7 +657,7 @@ msgid "Launch WinSCP for current SSH session"
|
||||
msgstr "为当前的 SSH 会话启动 WinSCP"
|
||||
|
||||
msgid "Learn how to allow Tabby to detect remote shell's working directory."
|
||||
msgstr "了解如何让 Tabby 检测远程 shell 的工作目录"
|
||||
msgstr "了解如何让 Tabby 检测远程 shell 的工作目录。"
|
||||
|
||||
msgid "Left"
|
||||
msgstr "左侧"
|
||||
@@ -678,10 +708,10 @@ msgid "Modified on {date}"
|
||||
msgstr "修改于 {date}"
|
||||
|
||||
msgid "Move tab to the left"
|
||||
msgstr "将标签页向左移动"
|
||||
msgstr "将标签页移至左侧"
|
||||
|
||||
msgid "Move tab to the right"
|
||||
msgstr "将标签页向右移动"
|
||||
msgstr "将标签页移至右侧"
|
||||
|
||||
msgid "Move to \"Ungrouped\""
|
||||
msgstr "移动到 “未分组”"
|
||||
@@ -692,14 +722,11 @@ msgstr "名称"
|
||||
msgid "Name for the new config"
|
||||
msgstr "新配置名称"
|
||||
|
||||
msgid "Named pipe"
|
||||
msgstr "已命名管道"
|
||||
|
||||
msgid "Native"
|
||||
msgstr "原生"
|
||||
|
||||
msgid "New admin tab"
|
||||
msgstr "新管理标签页"
|
||||
msgstr "新的管理标签页"
|
||||
|
||||
msgid "New config on {platform}"
|
||||
msgstr "{platform} 上的新配置"
|
||||
@@ -719,6 +746,9 @@ msgstr "新配置名称"
|
||||
msgid "New tab"
|
||||
msgstr "新标签页"
|
||||
|
||||
msgid "New tab: {profile}"
|
||||
msgstr "新标签页:{profile}"
|
||||
|
||||
msgid "New terminal"
|
||||
msgstr "新终端"
|
||||
|
||||
@@ -798,7 +828,7 @@ msgid "Output is shown as a hexdump"
|
||||
msgstr "输出显示为十六进制转储"
|
||||
|
||||
msgid "Output is shown as it is received"
|
||||
msgstr "输出在收到时显示"
|
||||
msgstr "按收到的原有样式显示输出"
|
||||
|
||||
msgid "Output mode"
|
||||
msgstr "输出模式"
|
||||
@@ -821,9 +851,6 @@ msgstr "覆盖远程的配置并开始同步?"
|
||||
msgid "Overwrite the local config and start syncing?"
|
||||
msgstr "覆盖本地配置并开始同步?"
|
||||
|
||||
msgid "Paper"
|
||||
msgstr "纸张"
|
||||
|
||||
msgid "Parity"
|
||||
msgstr "奇偶校验"
|
||||
|
||||
@@ -860,6 +887,9 @@ msgstr "插件"
|
||||
msgid "Plugins folder"
|
||||
msgstr "插件文件夹"
|
||||
|
||||
msgid "Polish"
|
||||
msgstr "波兰语"
|
||||
|
||||
msgid "Port"
|
||||
msgstr "端口"
|
||||
|
||||
@@ -867,7 +897,7 @@ msgid "Ports"
|
||||
msgstr "端口"
|
||||
|
||||
msgid "Press the key now"
|
||||
msgstr "现在请输入按键"
|
||||
msgstr "请输入按键"
|
||||
|
||||
msgid "Prevents accidental closing"
|
||||
msgstr "防止意外关闭"
|
||||
@@ -893,9 +923,6 @@ msgstr "配置"
|
||||
msgid "Profiles & connections"
|
||||
msgstr "配置和连接"
|
||||
|
||||
msgid "Profiles and connections"
|
||||
msgstr "配置和连接"
|
||||
|
||||
msgid "Program"
|
||||
msgstr "程序"
|
||||
|
||||
@@ -992,8 +1019,8 @@ msgstr "右键点击"
|
||||
msgid "Run as administrator"
|
||||
msgstr "以管理员身份运行"
|
||||
|
||||
msgid "SFTP"
|
||||
msgstr "SFTP"
|
||||
msgid "Russian"
|
||||
msgstr "俄语"
|
||||
|
||||
msgid "SOCKS proxy"
|
||||
msgstr "SOCKS 代理"
|
||||
@@ -1007,8 +1034,8 @@ msgstr "SOCKS 代理端口"
|
||||
msgid "SSH connection"
|
||||
msgstr "SSH 连接"
|
||||
|
||||
msgid "SSH connection management is now done through the"
|
||||
msgstr "现在,SSH 连接管理使用"
|
||||
msgid "SSH connection management is now done through the \"Profiles & connections\" tab"
|
||||
msgstr "现在,SSH 连接管理通过“配置和连接“选项卡完成"
|
||||
|
||||
msgid "SSH password for {user}@{host}:{port}"
|
||||
msgstr "{user}@{host}:{port} 的 SSH 密码"
|
||||
@@ -1145,11 +1172,14 @@ msgstr "显示更新日志"
|
||||
msgid "Show vault contents"
|
||||
msgstr "显示保险库内容"
|
||||
|
||||
msgid "Show {type} profile selector"
|
||||
msgstr "显示 {type} 配置选择器"
|
||||
|
||||
msgid "Skip MoTD/banner"
|
||||
msgstr "跳过 MoTD/横幅消息"
|
||||
|
||||
msgid "Slow feed"
|
||||
msgstr "缓慢接收"
|
||||
msgstr "逐字节接收"
|
||||
|
||||
msgid "Snaps the window to a side of the screen"
|
||||
msgstr "将窗口贴靠至屏幕的一侧"
|
||||
@@ -1157,6 +1187,9 @@ msgstr "将窗口贴靠至屏幕的一侧"
|
||||
msgid "Source code"
|
||||
msgstr "源码"
|
||||
|
||||
msgid "Spanish"
|
||||
msgstr "西班牙语"
|
||||
|
||||
msgid "Split"
|
||||
msgstr "拆分"
|
||||
|
||||
@@ -1217,71 +1250,14 @@ msgstr "同步快捷键"
|
||||
msgid "Sync window settings"
|
||||
msgstr "同步窗口设置"
|
||||
|
||||
msgid "Tab 1"
|
||||
msgstr "标签页 1"
|
||||
|
||||
msgid "Tab 10"
|
||||
msgstr "标签页 10"
|
||||
|
||||
msgid "Tab 11"
|
||||
msgstr "标签页 11"
|
||||
|
||||
msgid "Tab 12"
|
||||
msgstr "标签页 12"
|
||||
|
||||
msgid "Tab 13"
|
||||
msgstr "标签页 13"
|
||||
|
||||
msgid "Tab 14"
|
||||
msgstr "标签页 14"
|
||||
|
||||
msgid "Tab 15"
|
||||
msgstr "标签页 15"
|
||||
|
||||
msgid "Tab 16"
|
||||
msgstr "标签页 16"
|
||||
|
||||
msgid "Tab 17"
|
||||
msgstr "标签页 17"
|
||||
|
||||
msgid "Tab 18"
|
||||
msgstr "标签页 18"
|
||||
|
||||
msgid "Tab 19"
|
||||
msgstr "标签页 19"
|
||||
|
||||
msgid "Tab 2"
|
||||
msgstr "标签页 2"
|
||||
|
||||
msgid "Tab 20"
|
||||
msgstr "标签页 20"
|
||||
|
||||
msgid "Tab 3"
|
||||
msgstr "标签页 3"
|
||||
|
||||
msgid "Tab 4"
|
||||
msgstr "标签页 4"
|
||||
|
||||
msgid "Tab 5"
|
||||
msgstr "标签页 5"
|
||||
|
||||
msgid "Tab 6"
|
||||
msgstr "标签页 6"
|
||||
|
||||
msgid "Tab 7"
|
||||
msgstr "标签页 7"
|
||||
|
||||
msgid "Tab 8"
|
||||
msgstr "标签页 8"
|
||||
|
||||
msgid "Tab 9"
|
||||
msgstr "标签页 9"
|
||||
|
||||
msgid "Tab activity"
|
||||
msgstr "标签页活动"
|
||||
|
||||
msgid "Tab {number}"
|
||||
msgstr "标签页 {number}"
|
||||
|
||||
msgid "Tabby could not start with your plugins, so all third party plugins have been disabled in this session. The error was:"
|
||||
msgstr "Tabby不能使用您的插件启动,因此本会话中禁用了所有第三方插件。错误信息:"
|
||||
msgstr "Tabby 不能使用您的插件启动,因此本次会话中禁用了所有第三方插件。错误信息:"
|
||||
|
||||
msgid "Tabby news and updates on Twitter"
|
||||
msgstr "Tabby 在 Twitter 的新闻和更新"
|
||||
@@ -1295,9 +1271,6 @@ msgstr "标签页位置"
|
||||
msgid "Tabs width"
|
||||
msgstr "标签页宽度"
|
||||
|
||||
msgid "Telnet"
|
||||
msgstr "Telnet"
|
||||
|
||||
msgid "Telnet session"
|
||||
msgstr "Telnet 会话"
|
||||
|
||||
@@ -1335,7 +1308,7 @@ msgid "Toggle fullscreen mode"
|
||||
msgstr "切换全屏模式"
|
||||
|
||||
msgid "Toggle last tab"
|
||||
msgstr "切换到最后一个选项卡"
|
||||
msgstr "切换到最后一个标签页"
|
||||
|
||||
msgid "Toggle terminal window"
|
||||
msgstr "切换终端窗口"
|
||||
@@ -1374,7 +1347,7 @@ msgid "Update"
|
||||
msgstr "更新"
|
||||
|
||||
msgid "Upgrade to {version}"
|
||||
msgstr "升级到 {version}"
|
||||
msgstr "升级至 {version}"
|
||||
|
||||
msgid "Upload"
|
||||
msgstr "上传"
|
||||
@@ -1389,7 +1362,7 @@ msgid "Use {altKeyName} as the Meta key"
|
||||
msgstr "使用 {altKeyName} 作为 Meta 键"
|
||||
|
||||
msgid "User default"
|
||||
msgstr "用户默认值"
|
||||
msgstr "用户默认"
|
||||
|
||||
msgid "Username"
|
||||
msgstr "用户名"
|
||||
@@ -1415,6 +1388,9 @@ msgstr "保险库未配置"
|
||||
msgid "Vault master passphrase needs to be set to allow storing secrets"
|
||||
msgstr "为允许存储密钥,您必须设置保险库的主密码"
|
||||
|
||||
msgid "Verify host keys when connecting"
|
||||
msgstr "连接时校验主机密钥"
|
||||
|
||||
msgid "Version"
|
||||
msgstr "版本"
|
||||
|
||||
@@ -1439,8 +1415,11 @@ msgstr "多行粘贴时显示警告"
|
||||
msgid "Warn when closing active connections"
|
||||
msgstr "当关闭活动连接时,显示警告"
|
||||
|
||||
msgid "Warning: remote host's key has suddenly changed!"
|
||||
msgstr "警告:远程主机密钥突然改变!"
|
||||
|
||||
msgid "We're only tracking your Tabby and OS versions."
|
||||
msgstr "我们只获取您的 Tabby 和操作系统版本信息"
|
||||
msgstr "我们只获取您的 Tabby 和操作系统版本信息。"
|
||||
|
||||
msgid "Welcome"
|
||||
msgstr "欢迎"
|
||||
@@ -1473,7 +1452,7 @@ msgid "Window frame"
|
||||
msgstr "窗口框架样式"
|
||||
|
||||
msgid "Windows 10 build 18309 or above is recommended for ConPTY"
|
||||
msgstr "Windows 10 版本号 18309 或以上推荐 ConPTY"
|
||||
msgstr "Windows 10 版本 18309 以上推荐 ConPTY"
|
||||
|
||||
msgid "Word separators"
|
||||
msgstr "单词分隔符"
|
||||
@@ -1482,7 +1461,7 @@ msgid "Working directory"
|
||||
msgstr "工作目录"
|
||||
|
||||
msgid "Working directory detection"
|
||||
msgstr "工作目录检测"
|
||||
msgstr "查找工作目录"
|
||||
|
||||
msgid "X11 forwarding"
|
||||
msgstr "X11 转发"
|
||||
@@ -1493,6 +1472,9 @@ msgstr "黄色"
|
||||
msgid "You can change it later, but it's unrecoverable if forgotten."
|
||||
msgstr "您可以稍后更改,但在忘记时无法恢复"
|
||||
|
||||
msgid "You could be under a man-in-the-middle attack right now, or the host key could have just been changed."
|
||||
msgstr "您可能正在遭受中间人攻击,或您的主机密钥已经被更改。"
|
||||
|
||||
msgid "Zoom in"
|
||||
msgstr "放大"
|
||||
|
||||
@@ -1502,9 +1484,6 @@ msgstr "缩小"
|
||||
msgid "click"
|
||||
msgstr "点击"
|
||||
|
||||
msgid "tab"
|
||||
msgstr "标签页"
|
||||
|
||||
msgid "{name} copy"
|
||||
msgstr "{name} 副本"
|
||||
|
||||
|
1489
locale/zh-TW.po
Normal file
1489
locale/zh-TW.po
Normal file
File diff suppressed because it is too large
Load Diff
13
package.json
13
package.json
@@ -26,21 +26,22 @@
|
||||
"@typescript-eslint/parser": "^4.33.0",
|
||||
"apply-loader": "2.0.0",
|
||||
"axios": "^0.21.2",
|
||||
"browserify-sign": "^4.2.1",
|
||||
"clone-deep": "^4.0.1",
|
||||
"compare-versions": "^4",
|
||||
"core-js": "^3.18.2",
|
||||
"cross-env": "7.0.3",
|
||||
"css-loader": "^6.5.1",
|
||||
"deep-equal": "2.0.5",
|
||||
"electron": "16.0.6",
|
||||
"electron": "16.0.8",
|
||||
"electron-builder": "^22.14.5",
|
||||
"electron-download": "^4.1.1",
|
||||
"electron-installer-snap": "^5.1.0",
|
||||
"electron-notarize": "^1.1.1",
|
||||
"electron-rebuild": "^3.2.5",
|
||||
"electron-rebuild": "^3.2.7",
|
||||
"eslint": "^7.32.0",
|
||||
"file-loader": "^6.2.0",
|
||||
"graceful-fs": "^4.2.8",
|
||||
"graceful-fs": "^4.2.9",
|
||||
"html-loader": "2.1.2",
|
||||
"json-loader": "^0.5.7",
|
||||
"lru-cache": "^6.0.0",
|
||||
@@ -62,7 +63,7 @@
|
||||
"raw-loader": "4.0.2",
|
||||
"sass-loader": "^12.4.0",
|
||||
"shell-quote": "^1.7.3",
|
||||
"shelljs": "0.8.4",
|
||||
"shelljs": "0.8.5",
|
||||
"slugify": "^1.6.5",
|
||||
"sortablejs": "^1.14.0",
|
||||
"source-code-pro": "^2.38.0",
|
||||
@@ -77,9 +78,9 @@
|
||||
"typescript": "^4.3.5",
|
||||
"utils-decorators": "^1.10.4",
|
||||
"val-loader": "4.0.0",
|
||||
"webpack": "^5.65.0",
|
||||
"webpack": "^5.67.0",
|
||||
"webpack-bundle-analyzer": "^4.5.0",
|
||||
"webpack-cli": "^4.9.1",
|
||||
"webpack-cli": "^4.9.2",
|
||||
"yaml-loader": "0.6.0",
|
||||
"zone.js": "^0.11.4"
|
||||
},
|
||||
|
39
patches/ssh2+1.5.0.patch
Normal file
39
patches/ssh2+1.5.0.patch
Normal file
@@ -0,0 +1,39 @@
|
||||
diff --git a/node_modules/ssh2/lib/protocol/keyParser.js b/node_modules/ssh2/lib/protocol/keyParser.js
|
||||
index 9860e3f..ee82e51 100644
|
||||
--- a/node_modules/ssh2/lib/protocol/keyParser.js
|
||||
+++ b/node_modules/ssh2/lib/protocol/keyParser.js
|
||||
@@ -15,6 +15,7 @@ const {
|
||||
sign: sign_,
|
||||
verify: verify_,
|
||||
} = require('crypto');
|
||||
+const { createVerify: createVerifyDSS } = require('browserify-sign')
|
||||
const supportedOpenSSLCiphers = getCiphers();
|
||||
|
||||
const { Ber } = require('asn1');
|
||||
@@ -404,6 +405,17 @@ const BaseKey = {
|
||||
return new Error('No public key available');
|
||||
if (!algo || typeof algo !== 'string')
|
||||
algo = this[SYM_HASH_ALGO];
|
||||
+
|
||||
+ if (algo === 'dss1') {
|
||||
+ const verifier = createVerifyDSS('DSA-SHA1');
|
||||
+ verifier.update(data);
|
||||
+ try {
|
||||
+ return verifier.verify(pem, signature);
|
||||
+ } catch (ex) {
|
||||
+ return ex;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
try {
|
||||
return verify_(algo, data, pem, signature);
|
||||
} catch (ex) {
|
||||
@@ -1343,7 +1355,7 @@ function parseDER(data, baseType, comment, fullType) {
|
||||
return new Error('Malformed OpenSSH public key');
|
||||
pubPEM = genOpenSSLDSAPub(p, q, g, y);
|
||||
pubSSH = genOpenSSHDSAPub(p, q, g, y);
|
||||
- algo = 'sha1';
|
||||
+ algo = 'dss1';
|
||||
break;
|
||||
}
|
||||
case 'ssh-ed25519': {
|
@@ -5,5 +5,5 @@ const log = require('npmlog')
|
||||
|
||||
vars.packagesWithDocs.forEach(([dest, src]) => {
|
||||
log.info('docs', src)
|
||||
sh.exec(`yarn typedoc --out docs/api/${dest} --tsconfig ${src}/tsconfig.typings.json ${src}/src/index.ts`)
|
||||
sh.exec(`yarn typedoc --out docs/api/${dest} --tsconfig ${src}/tsconfig.typings.json ${src}/src/index.ts`, { fatal: true })
|
||||
})
|
||||
|
@@ -5,5 +5,5 @@ const log = require('npmlog')
|
||||
|
||||
vars.builtinPlugins.forEach(plugin => {
|
||||
log.info('typings', plugin)
|
||||
sh.exec(`npx tsc --project ${plugin}/tsconfig.typings.json`)
|
||||
sh.exec(`yarn tsc --project ${plugin}/tsconfig.typings.json`, { fatal: true })
|
||||
})
|
||||
|
@@ -13,15 +13,14 @@ const tempHtml = 'locale/tmp-html'
|
||||
for (const plugin of vars.builtinPlugins) {
|
||||
log.info('extract-pug', plugin)
|
||||
|
||||
sh.exec(`yarn pug --doctype html -s --pretty -O '{require: function(){}}' -o ${tempHtml}/${plugin} ${plugin}`)
|
||||
sh.exec(`yarn pug --doctype html -s --pretty -O '{require: function(){}}' -o ${tempHtml}/${plugin} ${plugin}`, { fatal: true })
|
||||
|
||||
log.info('extract-ts', plugin)
|
||||
sh.exec(`node node_modules/.bin/ngx-translate-extract -i ${plugin}/src -m -s -f pot -o ${tempOutput}`)
|
||||
|
||||
sh.exec(`node node_modules/.bin/ngx-translate-extract -i ${plugin}/src -m -s -f pot -o ${tempOutput}`, { fatal: true })
|
||||
}
|
||||
|
||||
log.info('extract-pug')
|
||||
sh.exec(`node node_modules/.bin/ngx-translate-extract -i ${tempHtml} -f pot -s -o ${tempOutput}`)
|
||||
sh.exec(`node node_modules/.bin/ngx-translate-extract -i ${tempHtml} -f pot -s -o ${tempOutput}`, { fatal: true })
|
||||
|
||||
sh.rm('-r', tempHtml)
|
||||
await fs.rename(tempOutput, pot)
|
||||
|
@@ -1,30 +1,26 @@
|
||||
#!/usr/bin/env node
|
||||
const sh = require('shelljs')
|
||||
const path = require('path')
|
||||
const vars = require('./vars')
|
||||
const log = require('npmlog')
|
||||
|
||||
const localBinPath = path.resolve(__dirname, '../node_modules/.bin')
|
||||
const npx = `${localBinPath}/npx`
|
||||
|
||||
log.info('patch')
|
||||
sh.exec(`${npx} patch-package`)
|
||||
sh.exec(`yarn patch-package`, { fatal: true })
|
||||
|
||||
log.info('deps', 'app')
|
||||
|
||||
sh.cd('app')
|
||||
sh.exec(`${npx} yarn install --force`)
|
||||
sh.exec(`yarn install --force`, { fatal: true })
|
||||
sh.cd('..')
|
||||
|
||||
sh.cd('web')
|
||||
sh.exec(`${npx} yarn install --force`)
|
||||
sh.exec(`${npx} patch-package`)
|
||||
sh.exec(`yarn install --force`, { fatal: true })
|
||||
sh.exec(`yarn patch-package`, { fatal: true })
|
||||
sh.cd('..')
|
||||
|
||||
vars.allPackages.forEach(plugin => {
|
||||
log.info('deps', plugin)
|
||||
sh.cd(plugin)
|
||||
sh.exec(`${npx} yarn install --force`)
|
||||
sh.exec(`yarn install --force`, { fatal: true })
|
||||
sh.cd('..')
|
||||
})
|
||||
|
||||
|
@@ -11,25 +11,25 @@ sh.mkdir('-p', target)
|
||||
fs.writeFileSync(path.join(target, 'package.json'), '{}')
|
||||
sh.cd(target)
|
||||
vars.builtinPlugins.forEach(plugin => {
|
||||
if (plugin === 'tabby-web') {
|
||||
return
|
||||
}
|
||||
log.info('install', plugin)
|
||||
sh.cp('-r', path.join('..', plugin), '.')
|
||||
sh.rm('-rf', path.join(plugin, 'node_modules'))
|
||||
sh.cd(plugin)
|
||||
sh.exec(`yarn install --force --production`)
|
||||
if (plugin === 'tabby-web') {
|
||||
return
|
||||
}
|
||||
log.info('install', plugin)
|
||||
sh.cp('-r', path.join('..', plugin), '.')
|
||||
sh.rm('-rf', path.join(plugin, 'node_modules'))
|
||||
sh.cd(plugin)
|
||||
sh.exec(`yarn install --force --production`, { fatal: true })
|
||||
|
||||
|
||||
log.info('rebuild', 'native')
|
||||
if (fs.existsSync('node_modules')) {
|
||||
rebuild({
|
||||
buildPath: path.resolve('.'),
|
||||
electronVersion: vars.electronVersion,
|
||||
arch: process.env.ARCH ?? process.arch,
|
||||
force: true,
|
||||
})
|
||||
}
|
||||
sh.cd('..')
|
||||
log.info('rebuild', 'native')
|
||||
if (fs.existsSync('node_modules')) {
|
||||
rebuild({
|
||||
buildPath: path.resolve('.'),
|
||||
electronVersion: vars.electronVersion,
|
||||
arch: process.env.ARCH ?? process.arch,
|
||||
force: true,
|
||||
})
|
||||
}
|
||||
sh.cd('..')
|
||||
})
|
||||
fs.unlinkSync(path.join(target, 'package.json'), '{}')
|
||||
|
@@ -7,7 +7,7 @@ const { execSync } = require('child_process')
|
||||
vars.allPackages.forEach(plugin => {
|
||||
log.info('bump', plugin)
|
||||
sh.cd(plugin)
|
||||
sh.exec('npm --no-git-tag-version version ' + vars.version)
|
||||
sh.exec('npm --no-git-tag-version version ' + vars.version, { fatal: true })
|
||||
execSync('npm publish', { stdio: 'inherit' })
|
||||
sh.cd('..')
|
||||
})
|
||||
|
44
tabby-community-color-schemes/schemes/Light Owl
Normal file
44
tabby-community-color-schemes/schemes/Light Owl
Normal file
@@ -0,0 +1,44 @@
|
||||
!
|
||||
! Light Owl
|
||||
! https://github.com/sdras/night-owl-vscode-theme
|
||||
!
|
||||
*.foreground: #403f53
|
||||
*.background: #fbfbfb
|
||||
*.cursorColor: #90a7b2
|
||||
!
|
||||
! Black
|
||||
*.color0: #403f53
|
||||
*.color8: #403f53
|
||||
!
|
||||
! Red
|
||||
*.color1: #de3d3b
|
||||
*.color9: #de3d3b
|
||||
!
|
||||
! Green
|
||||
*.color2: #08916a
|
||||
*.color10: #08916a
|
||||
!
|
||||
! Yellow
|
||||
*.color3: #e0af02
|
||||
*.color11: #daaa01
|
||||
!
|
||||
! Blue
|
||||
*.color4: #288ed7
|
||||
*.color12: #288ed7
|
||||
!
|
||||
! Magenta
|
||||
*.color5: #d6438a
|
||||
*.color13: #d6438a
|
||||
!
|
||||
! Cyan
|
||||
*.color6: #2aa298
|
||||
*.color14: #2aa298
|
||||
!
|
||||
! White
|
||||
*.color7: #f0f0f0
|
||||
*.color15: #979797
|
||||
!
|
||||
! Bold, Italic, Underline
|
||||
!*.colorBD:
|
||||
!*.colorIT:
|
||||
!*.colorUL:
|
44
tabby-community-color-schemes/schemes/Night Owl
Normal file
44
tabby-community-color-schemes/schemes/Night Owl
Normal file
@@ -0,0 +1,44 @@
|
||||
!
|
||||
! Night Owl
|
||||
! https://github.com/sdras/night-owl-vscode-theme
|
||||
!
|
||||
*.foreground: #d6deeb
|
||||
*.background: #011627
|
||||
*.cursorColor: #80a4c2
|
||||
!
|
||||
! Black
|
||||
*.color0: #011627
|
||||
*.color8: #969696
|
||||
!
|
||||
! Red
|
||||
*.color1: #ef5350
|
||||
*.color9: #ef5350
|
||||
!
|
||||
! Green
|
||||
*.color2: #22da6e
|
||||
*.color10: #22da6e
|
||||
!
|
||||
! Yellow
|
||||
*.color3: #addb67
|
||||
*.color11: #ffeb95
|
||||
!
|
||||
! Blue
|
||||
*.color4: #82aaff
|
||||
*.color12: #82aaff
|
||||
!
|
||||
! Magenta
|
||||
*.color5: #c792ea
|
||||
*.color13: #c792ea
|
||||
!
|
||||
! Cyan
|
||||
*.color6: #21c7a8
|
||||
*.color14: #7fdbca
|
||||
!
|
||||
! White
|
||||
*.color7: #ffffff
|
||||
*.color15: #ffffff
|
||||
!
|
||||
! Bold, Italic, Underline
|
||||
!*.colorBD:
|
||||
!*.colorIT:
|
||||
!*.colorUL:
|
@@ -37,7 +37,7 @@ export class ButtonProvider extends ToolbarButtonProvider {
|
||||
icon: this.hostApp.platform === Platform.Web
|
||||
? require('./icons/plus.svg')
|
||||
: require('./icons/profiles.svg'),
|
||||
title: this.translate.instant('Profiles and connections'),
|
||||
title: this.translate.instant('Profiles & connections'),
|
||||
click: () => this.activate(),
|
||||
},
|
||||
...this.profilesService.getRecentProfiles().map(profile => ({
|
||||
|
@@ -214,6 +214,10 @@ export class AppRootComponent {
|
||||
}
|
||||
}
|
||||
|
||||
@HostBinding('class.vibrant') get isVibrant () {
|
||||
return this.config.store.appearance.vibrancy
|
||||
}
|
||||
|
||||
private getToolbarButtons (aboveZero: boolean): ToolbarButton[] {
|
||||
let buttons: ToolbarButton[] = []
|
||||
this.config.enabledServices(this.toolbarButtonProviders).forEach(provider => {
|
||||
|
@@ -1,4 +1,4 @@
|
||||
import { Observable, Subject, distinctUntilChanged } from 'rxjs'
|
||||
import { Observable, Subject, distinctUntilChanged, filter, debounceTime } from 'rxjs'
|
||||
import { EmbeddedViewRef, ViewContainerRef, ViewRef } from '@angular/core'
|
||||
import { RecoveryToken } from '../api/tabRecovery'
|
||||
import { BaseComponent } from './base.component'
|
||||
@@ -47,7 +47,9 @@ export abstract class BaseTabComponent extends BaseComponent {
|
||||
/**
|
||||
* CSS color override for the tab's header
|
||||
*/
|
||||
color: string|null = null
|
||||
get color (): string|null { return this._color }
|
||||
set color (value: string|null) { this._color = value }
|
||||
private _color: string|null = null
|
||||
|
||||
hasFocus = false
|
||||
|
||||
@@ -61,7 +63,6 @@ export abstract class BaseTabComponent extends BaseComponent {
|
||||
/* @hidden */
|
||||
viewContainerEmbeddedRef?: EmbeddedViewRef<any>
|
||||
|
||||
private progressClearTimeout: number
|
||||
private titleChange = new Subject<string>()
|
||||
private focused = new Subject<void>()
|
||||
private blurred = new Subject<void>()
|
||||
@@ -87,6 +88,12 @@ export abstract class BaseTabComponent extends BaseComponent {
|
||||
this.blurred$.subscribe(() => {
|
||||
this.hasFocus = false
|
||||
})
|
||||
this.subscribeUntilDestroyed(this.progress.pipe(
|
||||
filter(x => x !== null),
|
||||
debounceTime(5000),
|
||||
), () => {
|
||||
this.setProgress(null)
|
||||
})
|
||||
}
|
||||
|
||||
setTitle (title: string): void {
|
||||
@@ -103,14 +110,6 @@ export abstract class BaseTabComponent extends BaseComponent {
|
||||
*/
|
||||
setProgress (progress: number|null): void {
|
||||
this.progress.next(progress)
|
||||
if (progress) {
|
||||
if (this.progressClearTimeout) {
|
||||
clearTimeout(this.progressClearTimeout)
|
||||
}
|
||||
this.progressClearTimeout = setTimeout(() => {
|
||||
this.setProgress(null)
|
||||
}, 5000) as any
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -158,6 +158,7 @@ export type SplitDropZoneInfo = {
|
||||
></split-tab-spanner>
|
||||
<split-tab-drop-zone
|
||||
*ngFor='let dropZone of _dropZones'
|
||||
[enabled]='dropZonesEnabled'
|
||||
[parent]='this'
|
||||
[dropZone]='dropZone'
|
||||
(tabDropped)='onTabDropped($event, dropZone)'
|
||||
@@ -603,6 +604,10 @@ export class SplitTabComponent extends BaseTabComponent implements AfterViewInit
|
||||
this.tabAdopted.next(tab)
|
||||
}
|
||||
|
||||
get dropZonesEnabled (): boolean {
|
||||
return this.getAllTabs().length > 1
|
||||
}
|
||||
|
||||
destroy (): void {
|
||||
super.destroy()
|
||||
for (const x of this.getAllTabs()) {
|
||||
@@ -624,6 +629,16 @@ export class SplitTabComponent extends BaseTabComponent implements AfterViewInit
|
||||
super.clearActivity()
|
||||
}
|
||||
|
||||
get color (): string|null {
|
||||
return this.getFocusedTab()?.color ?? null
|
||||
}
|
||||
|
||||
set color (color: string|null) {
|
||||
for (const t of this.getAllTabs()) {
|
||||
t.color = color
|
||||
}
|
||||
}
|
||||
|
||||
private updateTitle (): void {
|
||||
this.setTitle(this.getAllTabs().map(x => x.title).join(' | '))
|
||||
}
|
||||
|
@@ -23,22 +23,32 @@ import { SplitDropZoneInfo } from './splitTab.component'
|
||||
export class SplitTabDropZoneComponent extends SelfPositioningComponent {
|
||||
@Input() dropZone: SplitDropZoneInfo
|
||||
@Input() parent: BaseTabComponent
|
||||
@Input() enabled = false
|
||||
@Output() tabDropped = new EventEmitter<BaseTabComponent>()
|
||||
@HostBinding('class.active') isActive = false
|
||||
@HostBinding('class.highlighted') isHighlighted = false
|
||||
|
||||
// eslint-disable-next-line @typescript-eslint/no-useless-constructor
|
||||
constructor (
|
||||
element: ElementRef,
|
||||
app: AppService,
|
||||
) {
|
||||
super(element)
|
||||
this.subscribeUntilDestroyed(app.tabDragActive$, tab => {
|
||||
this.isActive = !!tab && tab !== this.parent && (this.dropZone.type === 'relative' || tab !== this.dropZone.container.children[this.dropZone.position])
|
||||
this.isActive = !!(tab && this.canActivateFor(tab))
|
||||
this.layout()
|
||||
})
|
||||
}
|
||||
|
||||
canActivateFor (tab: BaseTabComponent) {
|
||||
if (tab === this.parent || !this.enabled) {
|
||||
return false
|
||||
}
|
||||
if (this.dropZone.type === 'absolute' && tab === this.dropZone.container.children[this.dropZone.position]) {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
ngOnChanges () {
|
||||
this.layout()
|
||||
}
|
||||
|
@@ -15,7 +15,7 @@ footer.d-flex.align-items-center
|
||||
.btn-group.mr-auto
|
||||
button.btn.btn-dark((click)='homeBase.openGitHub()')
|
||||
i.fab.fa-github
|
||||
span(translate) GitHub
|
||||
span GitHub
|
||||
button.btn.btn-dark((click)='homeBase.reportBug()')
|
||||
i.fas.fa-bug
|
||||
span(translate) Report a problem
|
||||
|
@@ -37,6 +37,7 @@ $tabs-height: 38px;
|
||||
text-align: center;
|
||||
transition: 0.25s all;
|
||||
align-self: center;
|
||||
margin-top: 1px;
|
||||
}
|
||||
|
||||
.name {
|
||||
|
@@ -1,6 +1,7 @@
|
||||
/* eslint-disable @typescript-eslint/explicit-module-boundary-types */
|
||||
import { Component, Input, Optional, Inject, HostBinding, HostListener, NgZone } from '@angular/core'
|
||||
import { NgbModal } from '@ng-bootstrap/ng-bootstrap'
|
||||
import { auditTime } from 'rxjs'
|
||||
import { TabContextMenuItemProvider } from '../api/tabContextMenuProvider'
|
||||
import { BaseTabComponent } from './baseTab.component'
|
||||
import { RenameTabModalComponent } from './renameTabModal.component'
|
||||
@@ -47,7 +48,9 @@ export class TabHeaderComponent extends BaseComponent {
|
||||
}
|
||||
|
||||
ngOnInit () {
|
||||
this.subscribeUntilDestroyed(this.tab.progress$, progress => {
|
||||
this.subscribeUntilDestroyed(this.tab.progress$.pipe(
|
||||
auditTime(300),
|
||||
), progress => {
|
||||
this.zone.run(() => {
|
||||
this.progress = progress
|
||||
})
|
||||
|
@@ -6,6 +6,16 @@
|
||||
|
||||
.text-center.mb-5(translate) Thank you for downloading Tabby!
|
||||
|
||||
.form-line
|
||||
.header
|
||||
.title(translate) Language
|
||||
select.form-control([(ngModel)]='config.store.language', (ngModelChange)='config.save()')
|
||||
option([ngValue]='null', translate) Automatic
|
||||
option(
|
||||
[value]='lang.code',
|
||||
*ngFor='let lang of locale.allLanguages'
|
||||
) {{lang.name|translate}}
|
||||
|
||||
.form-line
|
||||
.header
|
||||
.title(translate) Enable analytics
|
||||
|
@@ -3,7 +3,7 @@ import { Component } from '@angular/core'
|
||||
import { TranslateService } from '@ngx-translate/core'
|
||||
import { BaseTabComponent } from './baseTab.component'
|
||||
import { ConfigService } from '../services/config.service'
|
||||
import { HostWindowService } from '../api/hostWindow'
|
||||
import { LocaleService } from '../services/locale.service'
|
||||
|
||||
/** @hidden */
|
||||
@Component({
|
||||
@@ -15,8 +15,8 @@ export class WelcomeTabComponent extends BaseTabComponent {
|
||||
enableGlobalHotkey = true
|
||||
|
||||
constructor (
|
||||
private hostWindow: HostWindowService,
|
||||
public config: ConfigService,
|
||||
public locale: LocaleService,
|
||||
translate: TranslateService,
|
||||
) {
|
||||
super()
|
||||
@@ -30,6 +30,6 @@ export class WelcomeTabComponent extends BaseTabComponent {
|
||||
this.config.store.hotkeys['toggle-window'] = []
|
||||
}
|
||||
await this.config.save()
|
||||
this.hostWindow.reload()
|
||||
this.destroy()
|
||||
}
|
||||
}
|
||||
|
@@ -75,3 +75,5 @@ hotkeys:
|
||||
- '⌘-E'
|
||||
switch-profile:
|
||||
- '⌘-Shift-E'
|
||||
appearance:
|
||||
vibrancy: true
|
||||
|
@@ -58,83 +58,83 @@ export class AppHotkeyProvider extends HotkeyProvider {
|
||||
},
|
||||
{
|
||||
id: 'tab-1',
|
||||
name: this.translate.instant('Tab 1'),
|
||||
name: this.translate.instant('Tab {number}', { number: 1 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-2',
|
||||
name: this.translate.instant('Tab 2'),
|
||||
name: this.translate.instant('Tab {number}', { number: 2 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-3',
|
||||
name: this.translate.instant('Tab 3'),
|
||||
name: this.translate.instant('Tab {number}', { number: 3 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-4',
|
||||
name: this.translate.instant('Tab 4'),
|
||||
name: this.translate.instant('Tab {number}', { number: 4 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-5',
|
||||
name: this.translate.instant('Tab 5'),
|
||||
name: this.translate.instant('Tab {number}', { number: 5 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-6',
|
||||
name: this.translate.instant('Tab 6'),
|
||||
name: this.translate.instant('Tab {number}', { number: 6 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-7',
|
||||
name: this.translate.instant('Tab 7'),
|
||||
name: this.translate.instant('Tab {number}', { number: 7 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-8',
|
||||
name: this.translate.instant('Tab 8'),
|
||||
name: this.translate.instant('Tab {number}', { number: 8 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-9',
|
||||
name: this.translate.instant('Tab 9'),
|
||||
name: this.translate.instant('Tab {number}', { number: 9 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-10',
|
||||
name: this.translate.instant('Tab 10'),
|
||||
name: this.translate.instant('Tab {number}', { number: 10 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-11',
|
||||
name: this.translate.instant('Tab 11'),
|
||||
name: this.translate.instant('Tab {number}', { number: 11 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-12',
|
||||
name: this.translate.instant('Tab 12'),
|
||||
name: this.translate.instant('Tab {number}', { number: 12 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-13',
|
||||
name: this.translate.instant('Tab 13'),
|
||||
name: this.translate.instant('Tab {number}', { number: 13 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-14',
|
||||
name: this.translate.instant('Tab 14'),
|
||||
name: this.translate.instant('Tab {number}', { number: 14 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-15',
|
||||
name: this.translate.instant('Tab 15'),
|
||||
name: this.translate.instant('Tab {number}', { number: 15 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-16',
|
||||
name: this.translate.instant('Tab 16'),
|
||||
name: this.translate.instant('Tab {number}', { number: 16 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-17',
|
||||
name: this.translate.instant('Tab 17'),
|
||||
name: this.translate.instant('Tab {number}', { number: 17 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-18',
|
||||
name: this.translate.instant('Tab 18'),
|
||||
name: this.translate.instant('Tab {number}', { number: 18 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-19',
|
||||
name: this.translate.instant('Tab 19'),
|
||||
name: this.translate.instant('Tab {number}', { number: 19 }),
|
||||
},
|
||||
{
|
||||
id: 'tab-20',
|
||||
name: this.translate.instant('Tab 20'),
|
||||
name: this.translate.instant('Tab {number}', { number: 20 }),
|
||||
},
|
||||
{
|
||||
id: 'split-right',
|
||||
@@ -201,11 +201,11 @@ export class AppHotkeyProvider extends HotkeyProvider {
|
||||
...this.hotkeys,
|
||||
...profiles.map(profile => ({
|
||||
id: `profile.${AppHotkeyProvider.getProfileHotkeyName(profile)}`,
|
||||
name: `New tab: ${profile.name}`,
|
||||
name: this.translate.instant('New tab: {profile}', { profile: profile.name }),
|
||||
})),
|
||||
...this.profilesService.getProviders().map(provider => ({
|
||||
id: `profile-selectors.${provider.id}`,
|
||||
name: `Show ${provider.name} profile selector`,
|
||||
name: this.translate.instant('Show {type} profile selector', { type: provider.name }),
|
||||
})),
|
||||
]
|
||||
}
|
||||
|
@@ -149,6 +149,7 @@ const PROVIDERS = [
|
||||
SortablejsModule,
|
||||
DragDropModule,
|
||||
TranslateModule,
|
||||
CdkAutoDropGroup,
|
||||
],
|
||||
})
|
||||
export default class AppModule { // eslint-disable-line @typescript-eslint/no-extraneous-class
|
||||
|
@@ -130,9 +130,7 @@ export class HotkeysService {
|
||||
const keyName = getKeyName(eventData)
|
||||
if (eventName === 'keydown') {
|
||||
this.addPressedKey(keyName, eventData)
|
||||
if (!nativeEvent.repeat) {
|
||||
this.recognitionPhase = true
|
||||
}
|
||||
this.recognitionPhase = true
|
||||
this.updateModifiers(eventData)
|
||||
}
|
||||
if (eventName === 'keyup') {
|
||||
@@ -158,8 +156,10 @@ export class HotkeysService {
|
||||
|
||||
const matched = this.matchActiveHotkey()
|
||||
this.zone.run(() => {
|
||||
if (matched && this.recognitionPhase) {
|
||||
this.emitHotkeyOn(matched)
|
||||
if (matched) {
|
||||
if (this.recognitionPhase) {
|
||||
this.emitHotkeyOn(matched)
|
||||
}
|
||||
} else if (this.pressedHotkey) {
|
||||
this.emitHotkeyOff(this.pressedHotkey)
|
||||
}
|
||||
@@ -288,10 +288,9 @@ export class HotkeysService {
|
||||
|
||||
private emitHotkeyOn (hotkey: string) {
|
||||
if (this.pressedHotkey) {
|
||||
if (this.pressedHotkey === hotkey) {
|
||||
return
|
||||
if (this.pressedHotkey !== hotkey) {
|
||||
this.emitHotkeyOff(this.pressedHotkey)
|
||||
}
|
||||
this.emitHotkeyOff(this.pressedHotkey)
|
||||
}
|
||||
if (document.querySelectorAll('input:focus').length === 0) {
|
||||
console.debug('Matched hotkey', hotkey)
|
||||
|
@@ -2,8 +2,13 @@ import { Injectable } from '@angular/core'
|
||||
import { registerLocaleData } from '@angular/common'
|
||||
import { TranslateService } from '@ngx-translate/core'
|
||||
|
||||
import localeEN from '@angular/common/locales/en-GB'
|
||||
import localeEN from '@angular/common/locales/en'
|
||||
import localeDE from '@angular/common/locales/de'
|
||||
import localeES from '@angular/common/locales/es'
|
||||
import localeFR from '@angular/common/locales/fr'
|
||||
import localeHR from '@angular/common/locales/hr'
|
||||
import localePL from '@angular/common/locales/pl'
|
||||
import localeRU from '@angular/common/locales/ru'
|
||||
import localeZH from '@angular/common/locales/zh'
|
||||
import { Observable, Subject } from 'rxjs'
|
||||
import { distinctUntilChanged } from 'rxjs/operators'
|
||||
@@ -11,7 +16,12 @@ import { ConfigService } from './config.service'
|
||||
import { LogService, Logger } from './log.service'
|
||||
|
||||
registerLocaleData(localeEN)
|
||||
registerLocaleData(localeDE)
|
||||
registerLocaleData(localeES)
|
||||
registerLocaleData(localeFR)
|
||||
registerLocaleData(localeHR)
|
||||
registerLocaleData(localePL)
|
||||
registerLocaleData(localeRU)
|
||||
registerLocaleData(localeZH)
|
||||
|
||||
@Injectable({ providedIn: 'root' })
|
||||
@@ -27,7 +37,18 @@ export class TranslateServiceWrapper extends TranslateService {
|
||||
export class LocaleService {
|
||||
private logger: Logger
|
||||
|
||||
static readonly allLocales = ['en-US', 'hr-HR', 'zh-CN']
|
||||
static readonly allLocales = [
|
||||
'en-US',
|
||||
'de-DE',
|
||||
'es-ES',
|
||||
'fr-FR',
|
||||
'hr-HR',
|
||||
'pl-PL',
|
||||
'ru-RU',
|
||||
'zh-CN',
|
||||
'zh-TW',
|
||||
]
|
||||
|
||||
readonly allLanguages: { code: string, name: string }[]
|
||||
|
||||
get localeChanged$ (): Observable<string> {
|
||||
@@ -55,13 +76,37 @@ export class LocaleService {
|
||||
code: 'en-US',
|
||||
name: translate.instant('English'),
|
||||
},
|
||||
{
|
||||
code: 'zh-CN',
|
||||
name: translate.instant('Chinese (simplified)'),
|
||||
},
|
||||
{
|
||||
code: 'zh-TW',
|
||||
name: translate.instant('Chinese (traditional)'),
|
||||
},
|
||||
{
|
||||
code: 'hr-HR',
|
||||
name: translate.instant('Croatian'),
|
||||
},
|
||||
{
|
||||
code: 'zh-CN',
|
||||
name: translate.instant('Chinese (simplified)'),
|
||||
code: 'de-DE',
|
||||
name: translate.instant('German'),
|
||||
},
|
||||
{
|
||||
code: 'fr-FR',
|
||||
name: translate.instant('French'),
|
||||
},
|
||||
{
|
||||
code: 'pl-PL',
|
||||
name: translate.instant('Polish'),
|
||||
},
|
||||
{
|
||||
code: 'ru-RU',
|
||||
name: translate.instant('Russian'),
|
||||
},
|
||||
{
|
||||
code: 'es-ES',
|
||||
name: translate.instant('Spanish'),
|
||||
},
|
||||
]
|
||||
|
||||
|
@@ -37,9 +37,7 @@ export class ProfilesService {
|
||||
async openNewTabForProfile <P extends Profile> (profile: PartialProfile<P>): Promise<BaseTabComponent|null> {
|
||||
const params = await this.newTabParametersForProfile(profile)
|
||||
if (params) {
|
||||
const tab = this.app.openNewTab(params)
|
||||
;(this.app.getParentTab(tab) ?? tab).color = profile.color ?? null
|
||||
return tab
|
||||
return this.app.openNewTab(params)
|
||||
}
|
||||
return null
|
||||
}
|
||||
@@ -50,9 +48,12 @@ export class ProfilesService {
|
||||
if (params) {
|
||||
params.inputs ??= {}
|
||||
params.inputs['title'] = profile.name
|
||||
if (profile.disableDynamicTitle) {
|
||||
if (fullProfile.disableDynamicTitle) {
|
||||
params.inputs['disableDynamicTitle'] = true
|
||||
}
|
||||
if (fullProfile.color) {
|
||||
params.inputs['color'] = fullProfile.color
|
||||
}
|
||||
}
|
||||
return params
|
||||
}
|
||||
|
@@ -109,6 +109,7 @@ export class CommonOptionsContextMenu extends TabContextMenuItemProvider {
|
||||
async getItems (tab: BaseTabComponent, tabHeader?: TabHeaderComponent): Promise<MenuItemOptions[]> {
|
||||
let items: MenuItemOptions[] = []
|
||||
if (tabHeader) {
|
||||
const currentColor = TAB_COLORS.find(x => x.value === tab.color)?.name
|
||||
items = [
|
||||
...items,
|
||||
{
|
||||
@@ -121,9 +122,9 @@ export class CommonOptionsContextMenu extends TabContextMenuItemProvider {
|
||||
},
|
||||
{
|
||||
label: this.translate.instant('Color'),
|
||||
sublabel: TAB_COLORS.find(x => x.value === tab.color)?.name,
|
||||
sublabel: currentColor ? this.translate.instant(currentColor) : undefined,
|
||||
submenu: TAB_COLORS.map(color => ({
|
||||
label: this.translate.instant(color.name),
|
||||
label: this.translate.instant(color.name) ?? color.name,
|
||||
type: 'radio',
|
||||
checked: tab.color === color.value,
|
||||
click: () => {
|
||||
|
@@ -117,15 +117,13 @@ window-controls {
|
||||
|
||||
$border-color: $base1;
|
||||
|
||||
body {
|
||||
app-root {
|
||||
background: $body-bg;
|
||||
|
||||
&.vibrant {
|
||||
background: rgba(255, 255, 255,.4) !important;
|
||||
}
|
||||
}
|
||||
|
||||
app-root {
|
||||
&> .content {
|
||||
.tab-bar {
|
||||
.btn-tab-bar {
|
||||
@@ -382,11 +380,11 @@ start-page footer {
|
||||
background: $white !important;
|
||||
}
|
||||
|
||||
.terminal-toolbar {
|
||||
terminal-toolbar {
|
||||
background: #ffffff4a !important;
|
||||
border-bottom: 1px solid #00000026 !important;
|
||||
}
|
||||
|
||||
.bg-dark{
|
||||
background-color: $base2 !important;
|
||||
}
|
||||
}
|
||||
|
@@ -25,15 +25,13 @@ window-controls {
|
||||
|
||||
$border-color: #111;
|
||||
|
||||
body {
|
||||
app-root {
|
||||
background: $body-bg;
|
||||
|
||||
&.vibrant {
|
||||
background: rgba(0,0,0,.65);
|
||||
}
|
||||
}
|
||||
|
||||
app-root {
|
||||
&.no-tabs {
|
||||
background: rgba(0,0,0,.5);
|
||||
}
|
||||
@@ -138,7 +136,7 @@ app-root {
|
||||
tab-body {
|
||||
background: $content-bg;
|
||||
|
||||
.terminal-toolbar .btn, .toolbar-pin-button {
|
||||
terminal-toolbar .btn, .toolbar-pin-button {
|
||||
font-weight: bold;
|
||||
}
|
||||
}
|
||||
|
@@ -31,11 +31,7 @@ export class StandardCompactTheme extends Theme {
|
||||
/** @hidden */
|
||||
@Injectable()
|
||||
export class PaperTheme extends Theme {
|
||||
name = this.translate.instant('Paper')
|
||||
name = 'Paper'
|
||||
css = require('./theme.paper.scss')
|
||||
terminalBackground = '#f7f1e0'
|
||||
|
||||
constructor (private translate: TranslateService) {
|
||||
super()
|
||||
}
|
||||
}
|
||||
|
@@ -1,7 +1,8 @@
|
||||
import { NgModule } from '@angular/core'
|
||||
import { PlatformService, LogService, UpdaterService, DockingService, HostAppService, ThemesService, Platform, AppService, ConfigService, WIN_BUILD_FLUENT_BG_SUPPORTED, isWindowsBuild, HostWindowService, HotkeyProvider, ConfigProvider, FileProvider } from 'tabby-core'
|
||||
import { TerminalColorSchemeProvider } from 'tabby-terminal'
|
||||
import { SFTPContextMenuItemProvider } from 'tabby-ssh'
|
||||
import { SFTPContextMenuItemProvider, SSHProfileImporter } from 'tabby-ssh'
|
||||
import { auditTime } from 'rxjs'
|
||||
|
||||
import { HyperColorSchemes } from './colorSchemes'
|
||||
import { ElectronPlatformService } from './services/platform.service'
|
||||
@@ -16,6 +17,7 @@ import { ElectronService } from './services/electron.service'
|
||||
import { ElectronHotkeyProvider } from './hotkeys'
|
||||
import { ElectronConfigProvider } from './config'
|
||||
import { EditSFTPContextMenu } from './sftpContextMenu'
|
||||
import { OpenSSHImporter } from './openSSHImport'
|
||||
|
||||
@NgModule({
|
||||
providers: [
|
||||
@@ -30,6 +32,7 @@ import { EditSFTPContextMenu } from './sftpContextMenu'
|
||||
{ provide: ConfigProvider, useClass: ElectronConfigProvider, multi: true },
|
||||
{ provide: FileProvider, useClass: ElectronFileProvider, multi: true },
|
||||
{ provide: SFTPContextMenuItemProvider, useClass: EditSFTPContextMenu, multi: true },
|
||||
{ provide: SSHProfileImporter, useClass: OpenSSHImporter, multi: true },
|
||||
],
|
||||
})
|
||||
export default class ElectronModule {
|
||||
@@ -68,7 +71,7 @@ export default class ElectronModule {
|
||||
|
||||
let lastProgress: number|null = null
|
||||
app.tabOpened$.subscribe(tab => {
|
||||
tab.progress$.subscribe(progress => {
|
||||
tab.progress$.pipe(auditTime(250)).subscribe(progress => {
|
||||
if (lastProgress === progress) {
|
||||
return
|
||||
}
|
||||
@@ -113,7 +116,6 @@ export default class ElectronModule {
|
||||
if (this.hostApp.platform === Platform.Windows && !isWindowsBuild(WIN_BUILD_FLUENT_BG_SUPPORTED)) {
|
||||
vibrancyType = null
|
||||
}
|
||||
document.body.classList.toggle('vibrant', this.config.store.appearance.vibrancy)
|
||||
this.electron.ipcRenderer.send('window-set-vibrancy', this.config.store.appearance.vibrancy, vibrancyType)
|
||||
|
||||
this.hostWindow.setOpacity(this.config.store.appearance.opacity)
|
||||
|
129
tabby-electron/src/openSSHImport.ts
Normal file
129
tabby-electron/src/openSSHImport.ts
Normal file
@@ -0,0 +1,129 @@
|
||||
import * as fs from 'fs/promises'
|
||||
import * as path from 'path'
|
||||
import slugify from 'slugify'
|
||||
import { PartialProfile } from 'tabby-core'
|
||||
import { SSHProfileImporter, PortForwardType, SSHProfile, SSHProfileOptions } from 'tabby-ssh'
|
||||
|
||||
function deriveID (name: string): string {
|
||||
return 'openssh-config:' + slugify(name)
|
||||
}
|
||||
|
||||
export class OpenSSHImporter extends SSHProfileImporter {
|
||||
async getProfiles (): Promise<PartialProfile<SSHProfile>[]> {
|
||||
const results: PartialProfile<SSHProfile>[] = []
|
||||
const configPath = path.join(process.env.HOME ?? '~', '.ssh', 'config')
|
||||
try {
|
||||
const lines = (await fs.readFile(configPath, 'utf8')).split('\n')
|
||||
const globalOptions: Partial<SSHProfileOptions> = {}
|
||||
let currentProfile: PartialProfile<SSHProfile>|null = null
|
||||
for (let line of lines) {
|
||||
if (line.trim().startsWith('#') || !line.trim()) {
|
||||
continue
|
||||
}
|
||||
if (line.startsWith('Host ')) {
|
||||
if (currentProfile) {
|
||||
results.push(currentProfile)
|
||||
}
|
||||
const name = line.substr(5).trim()
|
||||
currentProfile = {
|
||||
id: deriveID(name),
|
||||
name: `${name} (.ssh/config)`,
|
||||
type: 'ssh',
|
||||
group: 'Imported from .ssh/config',
|
||||
options: {
|
||||
...globalOptions,
|
||||
host: name,
|
||||
},
|
||||
}
|
||||
} else {
|
||||
const target: Partial<SSHProfileOptions> = currentProfile?.options ?? globalOptions
|
||||
line = line.trim()
|
||||
const idx = /\s/.exec(line)?.index ?? -1
|
||||
if (idx === -1) {
|
||||
continue
|
||||
}
|
||||
const key = line.substr(0, idx).trim()
|
||||
const value = line.substr(idx + 1).trim()
|
||||
|
||||
if (key === 'IdentityFile') {
|
||||
target.privateKeys = value.split(',').map(s => s.trim()).map(s => {
|
||||
if (s.startsWith('~')) {
|
||||
s = path.join(process.env.HOME ?? '~', s.slice(2))
|
||||
}
|
||||
return s
|
||||
})
|
||||
} else if (key === 'RemoteForward') {
|
||||
const bind = value.split(/\s/)[0].trim()
|
||||
const tgt = value.split(/\s/)[1].trim()
|
||||
target.forwardedPorts ??= []
|
||||
target.forwardedPorts.push({
|
||||
type: PortForwardType.Remote,
|
||||
description: value,
|
||||
host: bind.split(':')[0] ?? '127.0.0.1',
|
||||
port: parseInt(bind.split(':')[1] ?? bind),
|
||||
targetAddress: tgt.split(':')[0],
|
||||
targetPort: parseInt(tgt.split(':')[1]),
|
||||
})
|
||||
} else if (key === 'LocalForward') {
|
||||
const bind = value.split(/\s/)[0].trim()
|
||||
const tgt = value.split(/\s/)[1].trim()
|
||||
target.forwardedPorts ??= []
|
||||
target.forwardedPorts.push({
|
||||
type: PortForwardType.Local,
|
||||
description: value,
|
||||
host: bind.split(':')[0] ?? '127.0.0.1',
|
||||
port: parseInt(bind.split(':')[1] ?? bind),
|
||||
targetAddress: tgt.split(':')[0],
|
||||
targetPort: parseInt(tgt.split(':')[1]),
|
||||
})
|
||||
} else if (key === 'DynamicForward') {
|
||||
const bind = value.trim()
|
||||
target.forwardedPorts ??= []
|
||||
target.forwardedPorts.push({
|
||||
type: PortForwardType.Dynamic,
|
||||
description: value,
|
||||
host: bind.split(':')[0] ?? '127.0.0.1',
|
||||
port: parseInt(bind.split(':')[1] ?? bind),
|
||||
targetAddress: '',
|
||||
targetPort: 22,
|
||||
})
|
||||
} else {
|
||||
const mappedKey = {
|
||||
hostname: 'host',
|
||||
host: 'host',
|
||||
port: 'port',
|
||||
user: 'user',
|
||||
forwardx11: 'x11',
|
||||
serveraliveinterval: 'keepaliveInterval',
|
||||
serveralivecountmax: 'keepaliveCountMax',
|
||||
proxycommand: 'proxyCommand',
|
||||
proxyjump: 'jumpHost',
|
||||
}[key.toLowerCase()]
|
||||
if (mappedKey) {
|
||||
target[mappedKey] = value
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (currentProfile) {
|
||||
results.push(currentProfile)
|
||||
}
|
||||
for (const p of results) {
|
||||
if (p.options?.proxyCommand) {
|
||||
p.options.proxyCommand = p.options.proxyCommand
|
||||
.replace('%h', p.options.host ?? '')
|
||||
.replace('%p', (p.options.port ?? 22).toString())
|
||||
}
|
||||
if (p.options?.jumpHost) {
|
||||
p.options.jumpHost = deriveID(p.options.jumpHost)
|
||||
}
|
||||
}
|
||||
return results
|
||||
} catch (e) {
|
||||
if (e.code === 'ENOENT') {
|
||||
return []
|
||||
}
|
||||
throw e
|
||||
}
|
||||
}
|
||||
}
|
@@ -15,6 +15,7 @@ export class ElectronHostWindow extends HostWindowService {
|
||||
get isFullscreen (): boolean { return this._isFullscreen }
|
||||
|
||||
private _isFullscreen = false
|
||||
private _isMaximized = false
|
||||
|
||||
constructor (
|
||||
zone: NgZone,
|
||||
@@ -47,6 +48,16 @@ export class ElectronHostWindow extends HostWindowService {
|
||||
electron.ipcRenderer.on('host:became-main-window', () => zone.run(() => {
|
||||
this.bootstrapData.isMainWindow = true
|
||||
}))
|
||||
|
||||
electron.ipcRenderer.on('host:window-maximized', () => zone.run(() => {
|
||||
this._isMaximized = true
|
||||
}))
|
||||
|
||||
electron.ipcRenderer.on('host:window-unmaximized', () => zone.run(() => {
|
||||
this._isMaximized = false
|
||||
}))
|
||||
|
||||
this._isMaximized = this.getWindow().isMaximized()
|
||||
}
|
||||
|
||||
getWindow (): BrowserWindow {
|
||||
@@ -74,7 +85,7 @@ export class ElectronHostWindow extends HostWindowService {
|
||||
}
|
||||
|
||||
isMaximized (): boolean {
|
||||
return this.getWindow().isMaximized()
|
||||
return this._isMaximized
|
||||
}
|
||||
|
||||
toggleMaximize (): void {
|
||||
|
@@ -11,7 +11,8 @@ import { LinkHandler } from './api'
|
||||
@Injectable()
|
||||
export class URLHandler extends LinkHandler {
|
||||
// From https://urlregex.com/
|
||||
regex = /((([A-Za-z]{3,9}:(?:\/\/)?)(?:[\-;:&=\+\$,\w]+@)?[A-Za-z0-9\.\-]+|(?:www\.|[\-;:&=\+\$,\w]+@)[A-Za-z0-9\.\-]+)((:((6553[0-5])|(655[0-2][0-9])|(65[0-4][0-9]{2})|(6[0-4][0-9]{3})|([1-5][0-9]{4})|([0-5]{1,5})|([0-9]{1,4})))?(?:\/[\+~%\/\.\w\-_]*)?\??(?:[\-\+=&;%@\.\w_]*)#?(?:[\.\!\/\\\w]*))?)/
|
||||
// with "-" added to last group (https://github.com/Eugeny/tabby/issues/5611)
|
||||
regex = /((([A-Za-z]{3,9}:(?:\/\/)?)(?:[\-;:&=\+\$,\w]+@)?[A-Za-z0-9\.\-]+|(?:www\.|[\-;:&=\+\$,\w]+@)[A-Za-z0-9\.\-]+)((:((6553[0-5])|(655[0-2][0-9])|(65[0-4][0-9]{2})|(6[0-4][0-9]{3})|([1-5][0-9]{4})|([0-5]{1,5})|([0-9]{1,4})))?(?:\/[\+~%\/\.\w\-_]*)?\??(?:[\-\+=&;%@\.\w_]*)#?(?:[\.\!\/\\\w-]*))?)/
|
||||
|
||||
priority = 5
|
||||
|
||||
|
@@ -1,7 +1,4 @@
|
||||
.terminal-toolbar(
|
||||
(mouseenter)='showToolbar()',
|
||||
(mouseleave)='hideToolbar()'
|
||||
)
|
||||
terminal-toolbar([tab]='this')
|
||||
i.fas.fa-xs.fa-circle.text-success.mr-2(*ngIf='session && session.open')
|
||||
i.fas.fa-xs.fa-circle.text-danger.mr-2(*ngIf='!session || !session.open')
|
||||
strong {{profile.options.port}} ({{profile.options.baudrate}})
|
||||
|
@@ -10,7 +10,7 @@ h3.mb-3(translate) Hotkeys
|
||||
ng-container(*ngFor='let hotkey of hotkeyDescriptions')
|
||||
.row.align-items-center(*ngIf='!hotkeyFilter || hotkeyFilterFn(hotkey, hotkeyFilter)')
|
||||
.col-8.py-2
|
||||
span {{hotkey.name}}
|
||||
span {{hotkey.name|translate}}
|
||||
span.ml-2.text-muted ({{hotkey.id}})
|
||||
.col-4.pr-5
|
||||
multi-hotkey-input(
|
||||
|
@@ -69,7 +69,7 @@
|
||||
.form-line
|
||||
.header
|
||||
.title(translate) Language
|
||||
select.form-control([(ngModel)]='config.store.language', (ngModelChange)='saveConfiguration()')
|
||||
select.form-control([(ngModel)]='config.store.language', (ngModelChange)='saveConfiguration(true)')
|
||||
option([ngValue]='null', translate) Automatic
|
||||
option(
|
||||
[value]='lang.code',
|
||||
|
6
tabby-ssh/src/api/importer.ts
Normal file
6
tabby-ssh/src/api/importer.ts
Normal file
@@ -0,0 +1,6 @@
|
||||
import { PartialProfile } from 'tabby-core'
|
||||
import { SSHProfile } from './interfaces'
|
||||
|
||||
export abstract class SSHProfileImporter {
|
||||
abstract getProfiles (): Promise<PartialProfile<SSHProfile>[]>
|
||||
}
|
@@ -1,2 +1,3 @@
|
||||
export * from './contextMenu'
|
||||
export * from './interfaces'
|
||||
export * from './importer'
|
||||
|
37
tabby-ssh/src/components/hostKeyPromptModal.component.pug
Normal file
37
tabby-ssh/src/components/hostKeyPromptModal.component.pug
Normal file
@@ -0,0 +1,37 @@
|
||||
.modal-header
|
||||
h3.m-0(translate) Host key verification
|
||||
|
||||
.modal-body.pt-0
|
||||
.alert.alert-danger(*ngIf='isMismatched')
|
||||
strong(translate) Warning: remote host's key has suddenly changed!
|
||||
div(translate) You could be under a man-in-the-middle attack right now, or the host key could have just been changed.
|
||||
|
||||
.form-group(*ngIf='isMismatched')
|
||||
.d-flex.align-items-center
|
||||
label(translate) Last known host key fingerprint
|
||||
.badge.badge-danger.ml-auto {{ selector.type }}
|
||||
code {{knownHost.digest}}
|
||||
|
||||
.form-group
|
||||
.d-flex.align-items-center
|
||||
label(translate) Current host key fingerprint
|
||||
.badge.badge-success.ml-auto {{ selector.type }}
|
||||
code {{digest}}
|
||||
|
||||
.modal-footer
|
||||
.w-100
|
||||
button.d-block.w-100.mb-3.btn.btn-primary(
|
||||
(click)='acceptAndSave()',
|
||||
[class.btn-danger]='isMismatched',
|
||||
translate
|
||||
) Accept and remember key
|
||||
button.d-block.w-100.mb-3.btn.btn-secondary(
|
||||
(click)='accept()',
|
||||
[class.btn-warning]='isMismatched',
|
||||
translate
|
||||
) Accept just this once
|
||||
button.d-block.w-100.btn.btn-secondary(
|
||||
[class.btn-danger]='!isMismatched',
|
||||
(click)='cancel()',
|
||||
translate
|
||||
) Disconnect
|
43
tabby-ssh/src/components/hostKeyPromptModal.component.ts
Normal file
43
tabby-ssh/src/components/hostKeyPromptModal.component.ts
Normal file
@@ -0,0 +1,43 @@
|
||||
/* eslint-disable @typescript-eslint/explicit-module-boundary-types */
|
||||
import { Component, Input } from '@angular/core'
|
||||
import { NgbActiveModal } from '@ng-bootstrap/ng-bootstrap'
|
||||
import { KnownHost, KnownHostSelector, SSHKnownHostsService } from '../services/sshKnownHosts.service'
|
||||
|
||||
/** @hidden */
|
||||
@Component({
|
||||
template: require('./hostKeyPromptModal.component.pug'),
|
||||
})
|
||||
export class HostKeyPromptModalComponent {
|
||||
@Input() selector: KnownHostSelector
|
||||
@Input() digest: string
|
||||
knownHost: KnownHost|null
|
||||
isMismatched = false
|
||||
isUnknown = false
|
||||
|
||||
constructor (
|
||||
private knownHosts: SSHKnownHostsService,
|
||||
private modalInstance: NgbActiveModal,
|
||||
) { }
|
||||
|
||||
ngOnInit () {
|
||||
this.knownHost = this.knownHosts.getFor(this.selector)
|
||||
if (!this.knownHost) {
|
||||
this.isUnknown = true
|
||||
} else if (this.knownHost.digest !== this.digest) {
|
||||
this.isMismatched = true
|
||||
}
|
||||
}
|
||||
|
||||
accept () {
|
||||
this.modalInstance.close(true)
|
||||
}
|
||||
|
||||
acceptAndSave () {
|
||||
this.knownHosts.store(this.selector, this.digest)
|
||||
this.accept()
|
||||
}
|
||||
|
||||
cancel () {
|
||||
this.modalInstance.close(false)
|
||||
}
|
||||
}
|
@@ -13,7 +13,7 @@
|
||||
button.btn.btn-link.hover-reveal.ml-auto((click)='remove(fw)')
|
||||
i.fas.fa-trash-alt
|
||||
|
||||
h5 Add a port forward
|
||||
h5(translate) Add a port forward
|
||||
|
||||
.input-group.mb-2(*ngIf='newForward.type === PortForwardType.Dynamic')
|
||||
input.form-control(type='text', [(ngModel)]='newForward.host')
|
||||
|
@@ -8,6 +8,14 @@ h3 SSH
|
||||
(ngModelChange)='config.save()',
|
||||
)
|
||||
|
||||
.form-line
|
||||
.header
|
||||
.title(translate) Verify host keys when connecting
|
||||
toggle(
|
||||
[(ngModel)]='config.store.ssh.verifyHostKeys',
|
||||
(ngModelChange)='config.save()',
|
||||
)
|
||||
|
||||
.form-line(*ngIf='hostApp.platform === Platform.Windows')
|
||||
.header
|
||||
.title(translate) WinSCP path
|
||||
@@ -29,7 +37,7 @@ h3 SSH
|
||||
)
|
||||
option(value='auto', translate) Automatic
|
||||
option(value='pageant') Pageant
|
||||
option(value='pipe', translate) Named pipe
|
||||
option(value='pipe') Named pipe
|
||||
|
||||
.form-line(*ngIf='config.store.ssh.agentType === "pipe"')
|
||||
.header
|
||||
@@ -53,4 +61,4 @@ h3 SSH
|
||||
(ngModelChange)='config.save()'
|
||||
)
|
||||
|
||||
.alert.alert-info(translate) SSH connection management is now done through the #[strong Profiles & connections] tab
|
||||
.alert.alert-info(translate) SSH connection management is now done through the "Profiles & connections" tab
|
||||
|
@@ -1,7 +1,4 @@
|
||||
.terminal-toolbar(
|
||||
(mouseenter)='showToolbar()',
|
||||
(mouseleave)='hideToolbar()'
|
||||
)
|
||||
terminal-toolbar([tab]='this')
|
||||
i.fas.fa-xs.fa-circle.text-success.mr-2(*ngIf='session && session.open')
|
||||
i.fas.fa-xs.fa-circle.text-danger.mr-2(*ngIf='!session || !session.open')
|
||||
strong.mr-auto {{profile.options.user}}@{{profile.options.host}}:{{profile.options.port}}
|
||||
@@ -10,10 +7,10 @@
|
||||
ngbDropdown,
|
||||
container='body',
|
||||
*ngIf='session && !session.supportsWorkingDirectory()',
|
||||
placement='bottom-right'
|
||||
placement='bottom-right bottom-left bottom'
|
||||
)
|
||||
button.btn.btn-sm.btn-link(ngbDropdownToggle)
|
||||
i.far.fa-lightbulb
|
||||
i.far.fa-lightbulb.text-primary
|
||||
.bg-dark(ngbDropdownMenu)
|
||||
a.d-flex.align-items-center(ngbDropdownItem, (click)='platform.openExternal("https://tabby.sh/go/cwd-detection")')
|
||||
.mr-auto
|
||||
@@ -27,7 +24,7 @@
|
||||
|
||||
button.btn.btn-sm.btn-link.mr-2((click)='openSFTP()', *ngIf='session && session.open')
|
||||
i.far.fa-folder-open
|
||||
span(translate) SFTP
|
||||
span SFTP
|
||||
|
||||
button.btn.btn-sm.btn-link(
|
||||
*ngIf='session && session.open && hostApp.platform !== Platform.Web',
|
||||
|
@@ -9,6 +9,8 @@ export class SSHConfigProvider extends ConfigProvider {
|
||||
agentType: 'auto',
|
||||
agentPath: null,
|
||||
x11Display: null,
|
||||
knownHosts: [],
|
||||
verifyHostKeys: true,
|
||||
},
|
||||
hotkeys: {
|
||||
'restart-ssh-session': [],
|
||||
|
@@ -16,6 +16,7 @@ import { SSHTabComponent } from './components/sshTab.component'
|
||||
import { SFTPPanelComponent } from './components/sftpPanel.component'
|
||||
import { SFTPDeleteModalComponent } from './components/sftpDeleteModal.component'
|
||||
import { KeyboardInteractiveAuthComponent } from './components/keyboardInteractiveAuthPanel.component'
|
||||
import { HostKeyPromptModalComponent } from './components/hostKeyPromptModal.component'
|
||||
|
||||
import { SSHConfigProvider } from './config'
|
||||
import { SSHSettingsTabProvider } from './settings'
|
||||
@@ -52,6 +53,7 @@ import { CommonSFTPContextMenu } from './sftpContextMenu'
|
||||
SSHPortForwardingModalComponent,
|
||||
SSHSettingsTabComponent,
|
||||
SSHTabComponent,
|
||||
HostKeyPromptModalComponent,
|
||||
],
|
||||
declarations: [
|
||||
SSHProfileSettingsComponent,
|
||||
@@ -62,6 +64,7 @@ import { CommonSFTPContextMenu } from './sftpContextMenu'
|
||||
SSHTabComponent,
|
||||
SFTPPanelComponent,
|
||||
KeyboardInteractiveAuthComponent,
|
||||
HostKeyPromptModalComponent,
|
||||
],
|
||||
})
|
||||
// eslint-disable-next-line @typescript-eslint/no-extraneous-class
|
||||
|
@@ -1,121 +0,0 @@
|
||||
import * as fs from 'fs/promises'
|
||||
import * as path from 'path'
|
||||
import slugify from 'slugify'
|
||||
import { PortForwardType, SSHProfile, SSHProfileOptions } from './api/interfaces'
|
||||
import { PartialProfile } from 'tabby-core'
|
||||
|
||||
function deriveID (name: string): string {
|
||||
return 'openssh-config:' + slugify(name)
|
||||
}
|
||||
|
||||
export async function parseOpenSSHProfiles (): Promise<PartialProfile<SSHProfile>[]> {
|
||||
const results: PartialProfile<SSHProfile>[] = []
|
||||
const configPath = path.join(process.env.HOME ?? '~', '.ssh', 'config')
|
||||
try {
|
||||
const lines = (await fs.readFile(configPath, 'utf8')).split('\n')
|
||||
const globalOptions: Partial<SSHProfileOptions> = {}
|
||||
let currentProfile: PartialProfile<SSHProfile>|null = null
|
||||
for (let line of lines) {
|
||||
if (line.trim().startsWith('#') || !line.trim()) {
|
||||
continue
|
||||
}
|
||||
if (line.startsWith('Host ')) {
|
||||
if (currentProfile) {
|
||||
results.push(currentProfile)
|
||||
}
|
||||
const name = line.substr(5).trim()
|
||||
currentProfile = {
|
||||
id: deriveID(name),
|
||||
name,
|
||||
type: 'ssh',
|
||||
group: 'Imported from .ssh/config',
|
||||
options: {
|
||||
...globalOptions,
|
||||
host: name,
|
||||
},
|
||||
}
|
||||
} else {
|
||||
const target: Partial<SSHProfileOptions> = currentProfile?.options ?? globalOptions
|
||||
line = line.trim()
|
||||
const idx = /\s/.exec(line)?.index ?? -1
|
||||
if (idx === -1) {
|
||||
continue
|
||||
}
|
||||
const key = line.substr(0, idx).trim()
|
||||
const value = line.substr(idx + 1).trim()
|
||||
|
||||
if (key === 'IdentityFile') {
|
||||
target.privateKeys = value.split(',').map(s => s.trim())
|
||||
} else if (key === 'RemoteForward') {
|
||||
const bind = value.split(/\s/)[0].trim()
|
||||
const tgt = value.split(/\s/)[1].trim()
|
||||
target.forwardedPorts ??= []
|
||||
target.forwardedPorts.push({
|
||||
type: PortForwardType.Remote,
|
||||
description: value,
|
||||
host: bind.split(':')[0] ?? '127.0.0.1',
|
||||
port: parseInt(bind.split(':')[1] ?? bind),
|
||||
targetAddress: tgt.split(':')[0],
|
||||
targetPort: parseInt(tgt.split(':')[1]),
|
||||
})
|
||||
} else if (key === 'LocalForward') {
|
||||
const bind = value.split(/\s/)[0].trim()
|
||||
const tgt = value.split(/\s/)[1].trim()
|
||||
target.forwardedPorts ??= []
|
||||
target.forwardedPorts.push({
|
||||
type: PortForwardType.Local,
|
||||
description: value,
|
||||
host: bind.split(':')[0] ?? '127.0.0.1',
|
||||
port: parseInt(bind.split(':')[1] ?? bind),
|
||||
targetAddress: tgt.split(':')[0],
|
||||
targetPort: parseInt(tgt.split(':')[1]),
|
||||
})
|
||||
} else if (key === 'DynamicForward') {
|
||||
const bind = value.trim()
|
||||
target.forwardedPorts ??= []
|
||||
target.forwardedPorts.push({
|
||||
type: PortForwardType.Dynamic,
|
||||
description: value,
|
||||
host: bind.split(':')[0] ?? '127.0.0.1',
|
||||
port: parseInt(bind.split(':')[1] ?? bind),
|
||||
targetAddress: '',
|
||||
targetPort: 22,
|
||||
})
|
||||
} else {
|
||||
const mappedKey = {
|
||||
Hostname: 'host',
|
||||
Port: 'port',
|
||||
User: 'user',
|
||||
ForwardX11: 'x11',
|
||||
ServerAliveInterval: 'keepaliveInterval',
|
||||
ServerAliveCountMax: 'keepaliveCountMax',
|
||||
ProxyCommand: 'proxyCommand',
|
||||
ProxyJump: 'jumpHost',
|
||||
}[key]
|
||||
if (mappedKey) {
|
||||
target[mappedKey] = value
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (currentProfile) {
|
||||
results.push(currentProfile)
|
||||
}
|
||||
for (const p of results) {
|
||||
if (p.options?.proxyCommand) {
|
||||
p.options.proxyCommand = p.options.proxyCommand
|
||||
.replace('%h', p.options.host ?? '')
|
||||
.replace('%p', (p.options.port ?? 22).toString())
|
||||
}
|
||||
if (p.options?.jumpHost) {
|
||||
p.options.jumpHost = deriveID(p.options.jumpHost)
|
||||
}
|
||||
}
|
||||
return results
|
||||
} catch (e) {
|
||||
if (e.code === 'ENOENT') {
|
||||
return []
|
||||
}
|
||||
throw e
|
||||
}
|
||||
}
|
@@ -1,11 +1,11 @@
|
||||
import { Injectable } from '@angular/core'
|
||||
import { Inject, Injectable, Optional } from '@angular/core'
|
||||
import { ProfileProvider, NewTabParameters, PartialProfile, TranslateService } from 'tabby-core'
|
||||
import * as ALGORITHMS from 'ssh2/lib/protocol/constants'
|
||||
import { SSHProfileSettingsComponent } from './components/sshProfileSettings.component'
|
||||
import { SSHTabComponent } from './components/sshTab.component'
|
||||
import { PasswordStorageService } from './services/passwordStorage.service'
|
||||
import { ALGORITHM_BLACKLIST, SSHAlgorithmType, SSHProfile } from './api'
|
||||
import { parseOpenSSHProfiles } from './openSSHImport'
|
||||
import { SSHProfileImporter } from './api/importer'
|
||||
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class SSHProfilesService extends ProfileProvider<SSHProfile> {
|
||||
@@ -40,13 +40,14 @@ export class SSHProfilesService extends ProfileProvider<SSHProfile> {
|
||||
scripts: [],
|
||||
socksProxyHost: null,
|
||||
socksProxyPort: null,
|
||||
reuseSession: false,
|
||||
reuseSession: true,
|
||||
},
|
||||
}
|
||||
|
||||
constructor (
|
||||
private passwordStorage: PasswordStorageService,
|
||||
private translate: TranslateService,
|
||||
@Inject(SSHProfileImporter) @Optional() private importers: SSHProfileImporter[]|null,
|
||||
) {
|
||||
super()
|
||||
for (const k of Object.values(SSHAlgorithmType)) {
|
||||
@@ -63,10 +64,12 @@ export class SSHProfilesService extends ProfileProvider<SSHProfile> {
|
||||
|
||||
async getBuiltinProfiles (): Promise<PartialProfile<SSHProfile>[]> {
|
||||
let imported: PartialProfile<SSHProfile>[] = []
|
||||
try {
|
||||
imported = await parseOpenSSHProfiles()
|
||||
} catch (e) {
|
||||
console.warn('Could not parse OpenSSH config:', e)
|
||||
for (const importer of this.importers ?? []) {
|
||||
try {
|
||||
imported = imported.concat(await importer.getProfiles())
|
||||
} catch (e) {
|
||||
console.warn('Could not parse OpenSSH config:', e)
|
||||
}
|
||||
}
|
||||
return [
|
||||
{
|
||||
@@ -85,7 +88,6 @@ export class SSHProfilesService extends ProfileProvider<SSHProfile> {
|
||||
},
|
||||
...imported.map(p => ({
|
||||
...p,
|
||||
name: p.name + ' (.ssh/config)',
|
||||
isBuiltin: true,
|
||||
})),
|
||||
]
|
||||
|
@@ -74,7 +74,9 @@ export class SocksProxyStream extends Duplex {
|
||||
}, s => {
|
||||
resolve(s)
|
||||
this.header = s.read()
|
||||
this.push(this.header)
|
||||
if (this.header) {
|
||||
this.push(this.header)
|
||||
}
|
||||
})
|
||||
connector.on('error', (err) => {
|
||||
reject(err)
|
||||
@@ -82,7 +84,7 @@ export class SocksProxyStream extends Duplex {
|
||||
})
|
||||
})
|
||||
this.client?.on('data', data => {
|
||||
if (data !== this.header) {
|
||||
if (!this.header || data !== this.header) {
|
||||
// socksv5 doesn't reliably emit the first data event
|
||||
this.push(data)
|
||||
this.header = null
|
||||
|
32
tabby-ssh/src/services/sshKnownHosts.service.ts
Normal file
32
tabby-ssh/src/services/sshKnownHosts.service.ts
Normal file
@@ -0,0 +1,32 @@
|
||||
import { Injectable } from '@angular/core'
|
||||
import { ConfigService } from 'tabby-core'
|
||||
|
||||
export interface KnownHostSelector {
|
||||
host: string
|
||||
port: number
|
||||
type: string
|
||||
}
|
||||
|
||||
export interface KnownHost extends KnownHostSelector {
|
||||
digest: string
|
||||
}
|
||||
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class SSHKnownHostsService {
|
||||
constructor (
|
||||
private config: ConfigService,
|
||||
) { }
|
||||
|
||||
getFor (selector: KnownHostSelector): KnownHost|null {
|
||||
return this.config.store.ssh.knownHosts.find(x => x.host === selector.host && x.port === selector.port && x.type === selector.type) ?? null
|
||||
}
|
||||
|
||||
store (selector: KnownHostSelector, digest: string): void {
|
||||
const existing = this.getFor(selector)
|
||||
if (existing) {
|
||||
existing.digest = digest
|
||||
} else {
|
||||
this.config.store.ssh.knownHosts.push({ ...selector, digest })
|
||||
}
|
||||
}
|
||||
}
|
@@ -11,8 +11,10 @@ import { ConfigService, FileProvidersService, HostAppService, NotificationsServi
|
||||
import { Socket } from 'net'
|
||||
import { Client, ClientChannel, SFTPWrapper } from 'ssh2'
|
||||
import { Subject, Observable } from 'rxjs'
|
||||
import { HostKeyPromptModalComponent } from '../components/hostKeyPromptModal.component'
|
||||
import { ProxyCommandStream, SocksProxyStream } from '../services/ssh.service'
|
||||
import { PasswordStorageService } from '../services/passwordStorage.service'
|
||||
import { SSHKnownHostsService } from '../services/sshKnownHosts.service'
|
||||
import { promisify } from 'util'
|
||||
import { SFTPSession } from './sftp'
|
||||
import { ALGORITHM_BLACKLIST, SSHAlgorithmType, PortForwardType, SSHProfile } from '../api'
|
||||
@@ -32,6 +34,11 @@ interface AuthMethod {
|
||||
contents?: Buffer
|
||||
}
|
||||
|
||||
interface Handshake {
|
||||
kex: string
|
||||
serverHostKey: string
|
||||
}
|
||||
|
||||
export class KeyboardInteractivePrompt {
|
||||
responses: string[] = []
|
||||
|
||||
@@ -40,7 +47,9 @@ export class KeyboardInteractivePrompt {
|
||||
public instruction: string,
|
||||
public prompts: Prompt[],
|
||||
private callback: (_: string[]) => void,
|
||||
) { }
|
||||
) {
|
||||
this.responses = new Array(this.prompts.length).fill('')
|
||||
}
|
||||
|
||||
respond (): void {
|
||||
this.callback(this.responses)
|
||||
@@ -73,6 +82,7 @@ export class SSHSession {
|
||||
private keyboardInteractivePrompt = new Subject<KeyboardInteractivePrompt>()
|
||||
private willDestroy = new Subject<void>()
|
||||
private keychainPasswordUsed = false
|
||||
private hostKeyDigest = ''
|
||||
|
||||
private passwordStorage: PasswordStorageService
|
||||
private ngbModal: NgbModal
|
||||
@@ -83,6 +93,7 @@ export class SSHSession {
|
||||
private fileProviders: FileProvidersService
|
||||
private config: ConfigService
|
||||
private translate: TranslateService
|
||||
private knownHosts: SSHKnownHostsService
|
||||
|
||||
constructor (
|
||||
private injector: Injector,
|
||||
@@ -99,6 +110,7 @@ export class SSHSession {
|
||||
this.fileProviders = injector.get(FileProvidersService)
|
||||
this.config = injector.get(ConfigService)
|
||||
this.translate = injector.get(TranslateService)
|
||||
this.knownHosts = injector.get(SSHKnownHostsService)
|
||||
|
||||
this.willDestroy$.subscribe(() => {
|
||||
for (const port of this.forwardedPorts) {
|
||||
@@ -184,6 +196,18 @@ export class SSHSession {
|
||||
algorithms[key] = this.profile.options.algorithms![key].filter(x => !ALGORITHM_BLACKLIST.includes(x))
|
||||
}
|
||||
|
||||
const hostVerifiedPromise: Promise<void> = new Promise((resolve, reject) => {
|
||||
ssh.on('handshake', async handshake => {
|
||||
if (!await this.verifyHostKey(handshake)) {
|
||||
this.ssh.end()
|
||||
reject(new Error('Host key verification failed'))
|
||||
return
|
||||
}
|
||||
this.logger.info('Handshake complete:', handshake)
|
||||
resolve()
|
||||
})
|
||||
})
|
||||
|
||||
const resultPromise: Promise<void> = new Promise(async (resolve, reject) => {
|
||||
ssh.on('ready', () => {
|
||||
connected = true
|
||||
@@ -191,15 +215,8 @@ export class SSHSession {
|
||||
this.passwordStorage.savePassword(this.profile, this.savedPassword)
|
||||
}
|
||||
|
||||
for (const fw of this.profile.options.forwardedPorts ?? []) {
|
||||
this.addPortForward(Object.assign(new ForwardedPort(), fw))
|
||||
}
|
||||
|
||||
this.zone.run(resolve)
|
||||
})
|
||||
ssh.on('handshake', negotiated => {
|
||||
this.logger.info('Handshake complete:', negotiated)
|
||||
})
|
||||
ssh.on('error', error => {
|
||||
if (error.message === 'All configured authentication methods failed') {
|
||||
this.passwordStorage.deletePassword(this.profile)
|
||||
@@ -286,12 +303,10 @@ export class SSHSession {
|
||||
keepaliveInterval: this.profile.options.keepaliveInterval ?? 15000,
|
||||
keepaliveCountMax: this.profile.options.keepaliveCountMax,
|
||||
readyTimeout: this.profile.options.readyTimeout,
|
||||
hostVerifier: (digest: string) => {
|
||||
log('Host key fingerprint:')
|
||||
log(colors.white.bgBlack(' SHA256 ') + colors.bgBlackBright(' ' + digest + ' '))
|
||||
hostVerifier: (key: any) => {
|
||||
this.hostKeyDigest = crypto.createHash('sha256').update(key).digest('base64')
|
||||
return true
|
||||
},
|
||||
hostHash: 'sha256' as any,
|
||||
algorithms,
|
||||
authHandler: (methodsLeft, partialSuccess, callback) => {
|
||||
this.zone.run(async () => {
|
||||
@@ -305,6 +320,11 @@ export class SSHSession {
|
||||
}
|
||||
|
||||
await resultPromise
|
||||
await hostVerifiedPromise
|
||||
|
||||
for (const fw of this.profile.options.forwardedPorts ?? []) {
|
||||
this.addPortForward(Object.assign(new ForwardedPort(), fw))
|
||||
}
|
||||
|
||||
this.open = true
|
||||
|
||||
@@ -369,6 +389,31 @@ export class SSHSession {
|
||||
})
|
||||
}
|
||||
|
||||
private async verifyHostKey (handshake: Handshake): Promise<boolean> {
|
||||
this.emitServiceMessage('Host key fingerprint:')
|
||||
this.emitServiceMessage(colors.white.bgBlack(` ${handshake.serverHostKey} `) + colors.bgBlackBright(' ' + this.hostKeyDigest + ' '))
|
||||
if (!this.config.store.ssh.verifyHostKeys) {
|
||||
return true
|
||||
}
|
||||
const selector = {
|
||||
host: this.profile.options.host,
|
||||
port: this.profile.options.port ?? 22,
|
||||
type: handshake.serverHostKey,
|
||||
}
|
||||
const knownHost = this.knownHosts.getFor(selector)
|
||||
if (!knownHost || knownHost.digest !== this.hostKeyDigest) {
|
||||
const modal = this.ngbModal.open(HostKeyPromptModalComponent)
|
||||
modal.componentInstance.selector = selector
|
||||
modal.componentInstance.digest = this.hostKeyDigest
|
||||
try {
|
||||
return await modal.result
|
||||
} catch {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
emitServiceMessage (msg: string): void {
|
||||
this.serviceMessage.next(msg)
|
||||
this.logger.info(stripAnsi(msg))
|
||||
|
@@ -22,9 +22,9 @@
|
||||
"@types/node" "*"
|
||||
|
||||
"@types/ssh2@^0.5.46":
|
||||
version "0.5.50"
|
||||
resolved "https://registry.yarnpkg.com/@types/ssh2/-/ssh2-0.5.50.tgz#2ae2a250efd07b9432ee6a70de870cd1fb67ab40"
|
||||
integrity sha512-Eu/rzX4L+GhWIKEFQbaeWKECdy8VRdIYOqjMlFp+v4v7tBhvcl30m34BZzVALn/dNXvcB6dmcMtspIW7iPOlPg==
|
||||
version "0.5.51"
|
||||
resolved "https://registry.yarnpkg.com/@types/ssh2/-/ssh2-0.5.51.tgz#8fd9f9d7d3e8973b5227878f8f1e2b4eda1716b3"
|
||||
integrity sha512-aIq7ownezauW/+VWYaeXwd5J1Evnn4EXyeKi7bT3H6ZLBLoqsmhdvkHYPLpnZPM6unKKKsxTHIyQAVOZnPiJBw==
|
||||
dependencies:
|
||||
"@types/node" "*"
|
||||
"@types/ssh2-streams" "*"
|
||||
|
@@ -1,7 +1,4 @@
|
||||
.terminal-toolbar(
|
||||
(mouseenter)='showToolbar()',
|
||||
(mouseleave)='hideToolbar()'
|
||||
)
|
||||
terminal-toolbar([tab]='this')
|
||||
i.fas.fa-xs.fa-circle.text-success.mr-2(*ngIf='session && session.open')
|
||||
i.fas.fa-xs.fa-circle.text-danger.mr-2(*ngIf='!session || !session.open')
|
||||
strong.mr-auto {{profile.options.host}}:{{profile.options.port}}
|
||||
|
@@ -7,7 +7,7 @@ import { TelnetProfile } from './session'
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class TelnetProfilesService extends ProfileProvider<TelnetProfile> {
|
||||
id = 'telnet'
|
||||
name = this.translate.instant('Telnet')
|
||||
name = 'Telnet'
|
||||
supportsQuickConnect = false
|
||||
settingsComponent = TelnetProfileSettingsComponent
|
||||
configDefaults = {
|
||||
|
@@ -35,7 +35,8 @@
|
||||
"zmodem.js": "^0.1.9"
|
||||
},
|
||||
"resolutions": {
|
||||
"**/font-ligatures": "^1.4.1"
|
||||
"**/font-ligatures": "^1.4.1",
|
||||
"**/opentype.js": "^1.3.1"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@angular/animations": "^9.1.9",
|
||||
|
@@ -1,4 +1,4 @@
|
||||
import { Observable, Subject, Subscription, first } from 'rxjs'
|
||||
import { Observable, Subject, Subscription, first, auditTime } from 'rxjs'
|
||||
import { Spinner } from 'cli-spinner'
|
||||
import colors from 'ansi-colors'
|
||||
import { NgZone, OnInit, OnDestroy, Injector, ViewChild, HostBinding, Input, ElementRef, InjectFlags } from '@angular/core'
|
||||
@@ -71,9 +71,6 @@ export class BaseTerminalTabComponent extends BaseTabComponent implements OnInit
|
||||
/** @hidden */
|
||||
@HostBinding('style.background-color') backgroundColor: string|null = null
|
||||
|
||||
/** @hidden */
|
||||
@HostBinding('class.top-padded') topPadded: boolean
|
||||
|
||||
/** @hidden */
|
||||
@HostBinding('class.toolbar-enabled') enableToolbar = false
|
||||
|
||||
@@ -478,10 +475,6 @@ export class BaseTerminalTabComponent extends BaseTabComponent implements OnInit
|
||||
configure (): void {
|
||||
this.frontend?.configure()
|
||||
|
||||
this.topPadded = this.hostApp.platform === Platform.macOS
|
||||
&& this.config.store.appearance.frame === 'thin'
|
||||
&& this.config.store.appearance.tabsLocation !== 'top'
|
||||
|
||||
if (this.config.store.terminal.background === 'colorScheme') {
|
||||
if (this.config.store.terminal.colorScheme.background) {
|
||||
this.backgroundColor = this.config.store.terminal.colorScheme.background
|
||||
@@ -671,7 +664,7 @@ export class BaseTerminalTabComponent extends BaseTabComponent implements OnInit
|
||||
this.sendInput(data)
|
||||
})
|
||||
|
||||
this.termContainerSubscriptions.subscribe(this.frontend.resize$, ({ columns, rows }) => {
|
||||
this.termContainerSubscriptions.subscribe(this.frontend.resize$.pipe(auditTime(100)), ({ columns, rows }) => {
|
||||
this.logger.debug(`Resizing to ${columns}x${rows}`)
|
||||
this.size = { columns, rows }
|
||||
this.zone.run(() => {
|
||||
@@ -714,6 +707,10 @@ export class BaseTerminalTabComponent extends BaseTabComponent implements OnInit
|
||||
window.localStorage.pinTerminalToolbar = this.pinToolbar
|
||||
}
|
||||
|
||||
@HostBinding('class.with-title-inset') get hasTitleInset (): boolean {
|
||||
return this.hostApp.platform === Platform.macOS && this.config.store.appearance.tabsLocation !== 'top' && this.config.store.appearance.frame === 'thin'
|
||||
}
|
||||
|
||||
protected attachSessionHandler <T> (observable: Observable<T>, handler: (v: T) => void): void {
|
||||
this.sessionHandlers.subscribe(observable, handler)
|
||||
}
|
||||
|
@@ -8,12 +8,9 @@ search-panel(
|
||||
)
|
||||
|
||||
button.btn.btn-sm.btn-link.toolbar-pin-button(
|
||||
*ngIf='enableToolbar',
|
||||
*ngIf='enableToolbar && !pinToolbar',
|
||||
(click)='togglePinToolbar()',
|
||||
(mouseenter)='showToolbar()',
|
||||
(mouseleave)='hideToolbar()'
|
||||
)
|
||||
i.fas.fa-thumbtack(*ngIf='revealToolbar || pinToolbar')
|
||||
i.fas.fa-wrench.mr-3(*ngIf='!revealToolbar && !pinToolbar')
|
||||
span(*ngIf='pinToolbar', translate) Unpin
|
||||
span(*ngIf='!pinToolbar && revealToolbar', translate) Pin
|
||||
i.fas.fa-wrench
|
||||
|
@@ -5,10 +5,6 @@
|
||||
overflow: hidden;
|
||||
position: relative;
|
||||
|
||||
&.top-padded {
|
||||
padding-top: 20px;
|
||||
}
|
||||
|
||||
&> .content {
|
||||
flex: auto;
|
||||
position: relative;
|
||||
@@ -26,45 +22,34 @@
|
||||
|
||||
$toolbarHeight: 40px;
|
||||
|
||||
&>.terminal-toolbar {
|
||||
> terminal-toolbar {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 4;
|
||||
height: $toolbarHeight;
|
||||
|
||||
opacity: 0;
|
||||
background: rgba(0, 0, 0, .75);
|
||||
padding: 5px 85px 5px 15px;
|
||||
transition: 0.25s opacity;
|
||||
|
||||
display: flex;
|
||||
align-items: center;
|
||||
z-index: 3;
|
||||
will-change: transform;
|
||||
transform: translate(0, -100px);
|
||||
transition: 0.25s transform ease-out;
|
||||
|
||||
> .btn {
|
||||
white-space: nowrap;
|
||||
text-overflow: ellipsis;
|
||||
overflow: hidden;
|
||||
}
|
||||
height: $toolbarHeight;
|
||||
}
|
||||
|
||||
&.toolbar-revealed, &.toolbar-pinned {
|
||||
> .terminal-toolbar {
|
||||
> terminal-toolbar {
|
||||
opacity: 1;
|
||||
transform: translate(0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
&>.toolbar-pin-button {
|
||||
> .toolbar-pin-button {
|
||||
position: absolute;
|
||||
right: 10px;
|
||||
top: 2px;
|
||||
right: 34px;
|
||||
top: 5px;
|
||||
z-index: 4;
|
||||
background: #00000047;
|
||||
}
|
||||
|
||||
&.toolbar-pinned > .terminal-toolbar-spacer {
|
||||
@@ -73,6 +58,10 @@
|
||||
}
|
||||
}
|
||||
|
||||
:host-context(.platform-darwin) .terminal-toolbar {
|
||||
padding-left: 90px;
|
||||
:host-context(.with-title-inset) {
|
||||
padding-top: 20px;
|
||||
|
||||
terminal-toolbar {
|
||||
padding-left: 90px;
|
||||
}
|
||||
}
|
||||
|
@@ -107,8 +107,8 @@ div.mt-4
|
||||
[(ngModel)]='config.store.clickableLinks.modifier',
|
||||
(ngModelChange)='config.save()',
|
||||
)
|
||||
option([value]='null', translate) No modifier
|
||||
option(value='ctrlKey') Ctrl
|
||||
option([ngValue]='null', translate) No modifier
|
||||
option(value='ctrlKey', *ngIf='hostApp.platform !== Platform.macOS') Ctrl
|
||||
option(value='altKey') {{altKeyName}}
|
||||
option(value='shiftKey') Shift
|
||||
option(value='metaKey') {{metaKeyName}}
|
||||
|
23
tabby-terminal/src/components/terminalToolbar.component.pug
Normal file
23
tabby-terminal/src/components/terminalToolbar.component.pug
Normal file
@@ -0,0 +1,23 @@
|
||||
.content(
|
||||
cdkDropList
|
||||
cdkAutoDropGroup='app-tabs'
|
||||
)
|
||||
i.fas.fa-grip-vertical.drag-handle(
|
||||
*ngIf='shouldShowDragHandle',
|
||||
cdkDrag,
|
||||
[cdkDragData]='tab',
|
||||
(cdkDragStarted)='onTabDragStart()',
|
||||
(cdkDragEnded)='onTabDragEnd()'
|
||||
)
|
||||
|
||||
ng-content
|
||||
|
||||
button.btn.btn-sm.btn-link(
|
||||
*ngIf='tab.enableToolbar',
|
||||
(click)='tab.togglePinToolbar()',
|
||||
(mouseenter)='tab.showToolbar()',
|
||||
(mouseleave)='tab.hideToolbar()'
|
||||
)
|
||||
i.fas.fa-thumbtack
|
||||
span(*ngIf='tab.pinToolbar', translate) Unpin
|
||||
span(*ngIf='!tab.pinToolbar', translate) Pin
|
24
tabby-terminal/src/components/terminalToolbar.component.scss
Normal file
24
tabby-terminal/src/components/terminalToolbar.component.scss
Normal file
@@ -0,0 +1,24 @@
|
||||
:host {
|
||||
background: #000000bf;
|
||||
padding: 5px 15px 5px 15px;
|
||||
display: flex;
|
||||
z-index: 3;
|
||||
}
|
||||
|
||||
.content {
|
||||
flex-grow: 1;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.drag-handle {
|
||||
margin: 0 10px 0 0;
|
||||
cursor: move;
|
||||
opacity: .3;
|
||||
}
|
||||
|
||||
::ng-deep .btn {
|
||||
white-space: nowrap;
|
||||
text-overflow: ellipsis;
|
||||
overflow: hidden;
|
||||
}
|
42
tabby-terminal/src/components/terminalToolbar.component.ts
Normal file
42
tabby-terminal/src/components/terminalToolbar.component.ts
Normal file
@@ -0,0 +1,42 @@
|
||||
/* eslint-disable @typescript-eslint/explicit-module-boundary-types */
|
||||
import { Component, HostListener, Input } from '@angular/core'
|
||||
import { AppService, SplitTabComponent } from 'tabby-core'
|
||||
import { BaseTerminalTabComponent } from '../api/baseTerminalTab.component'
|
||||
|
||||
/** @hidden */
|
||||
@Component({
|
||||
selector: 'terminal-toolbar',
|
||||
template: require('./terminalToolbar.component.pug'),
|
||||
styles: [require('./terminalToolbar.component.scss')],
|
||||
})
|
||||
export class TerminalToolbarComponent {
|
||||
@Input() tab: BaseTerminalTabComponent
|
||||
|
||||
// eslint-disable-next-line @typescript-eslint/no-useless-constructor
|
||||
constructor (
|
||||
private app: AppService,
|
||||
) { }
|
||||
|
||||
onTabDragStart (): void {
|
||||
this.app.emitTabDragStarted(this.tab)
|
||||
}
|
||||
|
||||
onTabDragEnd (): void {
|
||||
setTimeout(() => {
|
||||
this.app.emitTabDragEnded()
|
||||
this.app.emitTabsChanged()
|
||||
})
|
||||
}
|
||||
|
||||
get shouldShowDragHandle (): boolean {
|
||||
return this.tab.parent instanceof SplitTabComponent && this.tab.parent.getAllTabs().length > 1
|
||||
}
|
||||
|
||||
@HostListener('mouseenter') onMouseEnter () {
|
||||
this.tab.showToolbar()
|
||||
}
|
||||
|
||||
@HostListener('mouseleave') onMouseLeave () {
|
||||
this.tab.hideToolbar()
|
||||
}
|
||||
}
|
@@ -15,6 +15,7 @@ import { ColorSchemePreviewComponent } from './components/colorSchemePreview.com
|
||||
import { SearchPanelComponent } from './components/searchPanel.component'
|
||||
import { StreamProcessingSettingsComponent } from './components/streamProcessingSettings.component'
|
||||
import { LoginScriptsSettingsComponent } from './components/loginScriptsSettings.component'
|
||||
import { TerminalToolbarComponent } from './components/terminalToolbar.component'
|
||||
|
||||
import { TerminalDecorator } from './api/decorator'
|
||||
import { TerminalContextMenuItemProvider } from './api/contextMenuProvider'
|
||||
@@ -71,12 +72,14 @@ import { TerminalCLIHandler } from './cli'
|
||||
SearchPanelComponent,
|
||||
StreamProcessingSettingsComponent,
|
||||
LoginScriptsSettingsComponent,
|
||||
TerminalToolbarComponent,
|
||||
],
|
||||
exports: [
|
||||
ColorPickerComponent,
|
||||
SearchPanelComponent,
|
||||
StreamProcessingSettingsComponent,
|
||||
LoginScriptsSettingsComponent,
|
||||
TerminalToolbarComponent,
|
||||
],
|
||||
})
|
||||
export default class TerminalModule { } // eslint-disable-line @typescript-eslint/no-extraneous-class
|
||||
|
@@ -20,7 +20,7 @@ export interface StreamProcessingOptions {
|
||||
|
||||
export class TerminalStreamProcessor extends SessionMiddleware {
|
||||
forceEcho = false
|
||||
private inputReadline: ReadLine
|
||||
private inputReadline: ReadLine|null = null
|
||||
private inputPromptVisible = false
|
||||
private inputReadlineInStream: Readable & Writable
|
||||
private inputReadlineOutStream: Readable & Writable
|
||||
@@ -99,7 +99,7 @@ export class TerminalStreamProcessor extends SessionMiddleware {
|
||||
}
|
||||
|
||||
close (): void {
|
||||
this.inputReadline.close()
|
||||
this.inputReadline?.close()
|
||||
super.close()
|
||||
}
|
||||
|
||||
@@ -126,7 +126,7 @@ export class TerminalStreamProcessor extends SessionMiddleware {
|
||||
|
||||
private resetInputPrompt () {
|
||||
this.outputToTerminal.next(Buffer.from('\r\n'))
|
||||
this.inputReadline.prompt(true)
|
||||
this.inputReadline?.prompt(true)
|
||||
this.inputPromptVisible = true
|
||||
}
|
||||
|
||||
|
@@ -94,12 +94,13 @@ minimist@^1.1.0:
|
||||
resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.5.tgz#67d66014b66a6a8aaa0c083c5fd58df4e4e97602"
|
||||
integrity sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==
|
||||
|
||||
opentype.js@^0.8.0:
|
||||
version "0.8.0"
|
||||
resolved "https://registry.yarnpkg.com/opentype.js/-/opentype.js-0.8.0.tgz#acabcfa1642fbe894a3e4d759e43ba694e02bd35"
|
||||
integrity sha1-rKvPoWQvvolKPk11nkO6aU4CvTU=
|
||||
opentype.js@^0.8.0, opentype.js@^1.3.1:
|
||||
version "1.3.4"
|
||||
resolved "https://registry.yarnpkg.com/opentype.js/-/opentype.js-1.3.4.tgz#1c0e72e46288473cc4a4c6a2dc60fd7fe6020d77"
|
||||
integrity sha512-d2JE9RP/6uagpQAVtJoF0pJJA/fgai89Cc50Yp0EJHk+eLp6QQ7gBoblsnubRULNY132I0J1QKMJ+JTbMqz4sw==
|
||||
dependencies:
|
||||
tiny-inflate "^1.0.2"
|
||||
string.prototype.codepointat "^0.2.1"
|
||||
tiny-inflate "^1.0.3"
|
||||
|
||||
printj@~1.1.0:
|
||||
version "1.1.2"
|
||||
@@ -128,6 +129,11 @@ runes@^0.4.2:
|
||||
resolved "https://registry.yarnpkg.com/runes/-/runes-0.4.3.tgz#32f7738844bc767b65cc68171528e3373c7bb355"
|
||||
integrity sha512-K6p9y4ZyL9wPzA+PMDloNQPfoDGTiFYDvdlXznyGKgD10BJpcAosvATKrExRKOrNLgD8E7Um7WGW0lxsnOuNLg==
|
||||
|
||||
string.prototype.codepointat@^0.2.1:
|
||||
version "0.2.1"
|
||||
resolved "https://registry.yarnpkg.com/string.prototype.codepointat/-/string.prototype.codepointat-0.2.1.tgz#004ad44c8afc727527b108cd462b4d971cd469bc"
|
||||
integrity sha512-2cBVCj6I4IOvEnjgO/hWqXjqBGsY+zwPmHl12Srk9IXSZ56Jwwmy+66XO5Iut/oQVR7t5ihYdLB0GMa4alEUcg==
|
||||
|
||||
table-parser@^0.1.3:
|
||||
version "0.1.3"
|
||||
resolved "https://registry.yarnpkg.com/table-parser/-/table-parser-0.1.3.tgz#0441cfce16a59481684c27d1b5a67ff15a43c7b0"
|
||||
@@ -135,7 +141,7 @@ table-parser@^0.1.3:
|
||||
dependencies:
|
||||
connected-domain "^1.0.0"
|
||||
|
||||
tiny-inflate@^1.0.2:
|
||||
tiny-inflate@^1.0.3:
|
||||
version "1.0.3"
|
||||
resolved "https://registry.yarnpkg.com/tiny-inflate/-/tiny-inflate-1.0.3.tgz#122715494913a1805166aaf7c93467933eea26c4"
|
||||
integrity sha512-pkY1fj1cKHb2seWDy0B16HeWyczlJA9/WW3u3c4z/NiWDsO3DOU5D7nhTLE9CF0yXv/QZFY7sEJmj24dK+Rrqw==
|
||||
|
360
yarn.lock
360
yarn.lock
@@ -818,22 +818,22 @@
|
||||
"@webassemblyjs/ast" "1.11.1"
|
||||
"@xtuc/long" "4.2.2"
|
||||
|
||||
"@webpack-cli/configtest@^1.1.0":
|
||||
version "1.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@webpack-cli/configtest/-/configtest-1.1.0.tgz#8342bef0badfb7dfd3b576f2574ab80c725be043"
|
||||
integrity sha512-ttOkEkoalEHa7RaFYpM0ErK1xc4twg3Am9hfHhL7MVqlHebnkYd2wuI/ZqTDj0cVzZho6PdinY0phFZV3O0Mzg==
|
||||
"@webpack-cli/configtest@^1.1.1":
|
||||
version "1.1.1"
|
||||
resolved "https://registry.yarnpkg.com/@webpack-cli/configtest/-/configtest-1.1.1.tgz#9f53b1b7946a6efc2a749095a4f450e2932e8356"
|
||||
integrity sha512-1FBc1f9G4P/AxMqIgfZgeOTuRnwZMten8E7zap5zgpPInnCrP8D4Q81+4CWIch8i/Nf7nXjP0v6CjjbHOrXhKg==
|
||||
|
||||
"@webpack-cli/info@^1.4.0":
|
||||
version "1.4.0"
|
||||
resolved "https://registry.yarnpkg.com/@webpack-cli/info/-/info-1.4.0.tgz#b9179c3227ab09cbbb149aa733475fcf99430223"
|
||||
integrity sha512-F6b+Man0rwE4n0409FyAJHStYA5OIZERxmnUfLVwv0mc0V1wLad3V7jqRlMkgKBeAq07jUvglacNaa6g9lOpuw==
|
||||
"@webpack-cli/info@^1.4.1":
|
||||
version "1.4.1"
|
||||
resolved "https://registry.yarnpkg.com/@webpack-cli/info/-/info-1.4.1.tgz#2360ea1710cbbb97ff156a3f0f24556e0fc1ebea"
|
||||
integrity sha512-PKVGmazEq3oAo46Q63tpMr4HipI3OPfP7LiNOEJg963RMgT0rqheag28NCML0o3GIzA3DmxP1ZIAv9oTX1CUIA==
|
||||
dependencies:
|
||||
envinfo "^7.7.3"
|
||||
|
||||
"@webpack-cli/serve@^1.6.0":
|
||||
version "1.6.0"
|
||||
resolved "https://registry.yarnpkg.com/@webpack-cli/serve/-/serve-1.6.0.tgz#2c275aa05c895eccebbfc34cfb223c6e8bd591a2"
|
||||
integrity sha512-ZkVeqEmRpBV2GHvjjUZqEai2PpUbuq8Bqd//vEYsp63J8WyexI8ppCqVS3Zs0QADf6aWuPdU+0XsPI647PVlQA==
|
||||
"@webpack-cli/serve@^1.6.1":
|
||||
version "1.6.1"
|
||||
resolved "https://registry.yarnpkg.com/@webpack-cli/serve/-/serve-1.6.1.tgz#0de2875ac31b46b6c5bb1ae0a7d7f0ba5678dffe"
|
||||
integrity sha512-gNGTiTrjEVQ0OcVnzsRSqTxaBSr+dmTfm+qJsCDluky8uhdLWep7Gcr62QsAKHTMxjCS/8nEITsmFAhfIx+QSw==
|
||||
|
||||
"@xtuc/ieee754@^1.2.0":
|
||||
version "1.2.0"
|
||||
@@ -1182,6 +1182,16 @@ asar@^3.0.0, asar@^3.0.3:
|
||||
optionalDependencies:
|
||||
"@types/glob" "^7.1.1"
|
||||
|
||||
asn1.js@^5.2.0:
|
||||
version "5.4.1"
|
||||
resolved "https://registry.yarnpkg.com/asn1.js/-/asn1.js-5.4.1.tgz#11a980b84ebb91781ce35b0fdc2ee294e3783f07"
|
||||
integrity sha512-+I//4cYPccV8LdmBLiX8CYvf9Sp3vQsrqu2QNXRcrbiWvcx/UdlFiqUJJzxRQxgsZmvhXhn4cSKeSmoFjVdupA==
|
||||
dependencies:
|
||||
bn.js "^4.0.0"
|
||||
inherits "^2.0.1"
|
||||
minimalistic-assert "^1.0.0"
|
||||
safer-buffer "^2.1.0"
|
||||
|
||||
asn1@^0.2.4, asn1@~0.2.3:
|
||||
version "0.2.4"
|
||||
resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.4.tgz#8d2475dfab553bb33e77b54e59e880bb8ce23136"
|
||||
@@ -1355,6 +1365,16 @@ bluebird@^3.5.5:
|
||||
resolved "https://registry.npmjs.org/bluebird/-/bluebird-3.7.2.tgz"
|
||||
integrity sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg==
|
||||
|
||||
bn.js@^4.0.0, bn.js@^4.11.9:
|
||||
version "4.12.0"
|
||||
resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.12.0.tgz#775b3f278efbb9718eec7361f483fb36fbbfea88"
|
||||
integrity sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==
|
||||
|
||||
bn.js@^5.0.0, bn.js@^5.1.1:
|
||||
version "5.2.0"
|
||||
resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-5.2.0.tgz#358860674396c6997771a9d051fcc1b57d4ae002"
|
||||
integrity sha512-D7iWRBvnZE8ecXiLj/9wbxH7Tk79fAh8IHaTNq1RWRixsS02W+5qS+iE9yq6RYl0asXx5tw0bLhmT5pIfbSquw==
|
||||
|
||||
boolean@^3.0.1:
|
||||
version "3.0.2"
|
||||
resolved "https://registry.npmjs.org/boolean/-/boolean-3.0.2.tgz"
|
||||
@@ -1436,6 +1456,46 @@ braces@^3.0.1:
|
||||
dependencies:
|
||||
fill-range "^7.0.1"
|
||||
|
||||
brorand@^1.1.0:
|
||||
version "1.1.0"
|
||||
resolved "https://registry.yarnpkg.com/brorand/-/brorand-1.1.0.tgz#12c25efe40a45e3c323eb8675a0a0ce57b22371f"
|
||||
integrity sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=
|
||||
|
||||
browserify-aes@^1.0.0:
|
||||
version "1.2.0"
|
||||
resolved "https://registry.yarnpkg.com/browserify-aes/-/browserify-aes-1.2.0.tgz#326734642f403dabc3003209853bb70ad428ef48"
|
||||
integrity sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA==
|
||||
dependencies:
|
||||
buffer-xor "^1.0.3"
|
||||
cipher-base "^1.0.0"
|
||||
create-hash "^1.1.0"
|
||||
evp_bytestokey "^1.0.3"
|
||||
inherits "^2.0.1"
|
||||
safe-buffer "^5.0.1"
|
||||
|
||||
browserify-rsa@^4.0.1:
|
||||
version "4.1.0"
|
||||
resolved "https://registry.yarnpkg.com/browserify-rsa/-/browserify-rsa-4.1.0.tgz#b2fd06b5b75ae297f7ce2dc651f918f5be158c8d"
|
||||
integrity sha512-AdEER0Hkspgno2aR97SAf6vi0y0k8NuOpGnVH3O99rcA5Q6sh8QxcngtHuJ6uXwnfAXNM4Gn1Gb7/MV1+Ymbog==
|
||||
dependencies:
|
||||
bn.js "^5.0.0"
|
||||
randombytes "^2.0.1"
|
||||
|
||||
browserify-sign@^4.2.1:
|
||||
version "4.2.1"
|
||||
resolved "https://registry.yarnpkg.com/browserify-sign/-/browserify-sign-4.2.1.tgz#eaf4add46dd54be3bb3b36c0cf15abbeba7956c3"
|
||||
integrity sha512-/vrA5fguVAKKAVTNJjgSm1tRQDHUU6DbwO9IROu/0WAzC8PKhucDSh18J0RMvVeHAn5puMd+QHC2erPRNf8lmg==
|
||||
dependencies:
|
||||
bn.js "^5.1.1"
|
||||
browserify-rsa "^4.0.1"
|
||||
create-hash "^1.2.0"
|
||||
create-hmac "^1.1.7"
|
||||
elliptic "^6.5.3"
|
||||
inherits "^2.0.4"
|
||||
parse-asn1 "^5.1.5"
|
||||
readable-stream "^3.6.0"
|
||||
safe-buffer "^5.2.0"
|
||||
|
||||
browserslist@^4.14.5:
|
||||
version "4.16.6"
|
||||
resolved "https://registry.yarnpkg.com/browserslist/-/browserslist-4.16.6.tgz#d7901277a5a88e554ed305b183ec9b0c08f66fa2"
|
||||
@@ -1480,6 +1540,11 @@ buffer-from@^1.0.0:
|
||||
resolved "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz"
|
||||
integrity sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==
|
||||
|
||||
buffer-xor@^1.0.3:
|
||||
version "1.0.3"
|
||||
resolved "https://registry.yarnpkg.com/buffer-xor/-/buffer-xor-1.0.3.tgz#26e61ed1422fb70dd42e6e36729ed51d855fe8d9"
|
||||
integrity sha1-JuYe0UIvtw3ULm42cp7VHYVf6Nk=
|
||||
|
||||
buffer@^5.1.0:
|
||||
version "5.7.1"
|
||||
resolved "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz"
|
||||
@@ -1756,6 +1821,14 @@ ci-info@^3.1.1:
|
||||
resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-3.2.0.tgz#2876cb948a498797b5236f0095bc057d0dca38b6"
|
||||
integrity sha512-dVqRX7fLUm8J6FgHJ418XuIgDLZDkYcDFTeL6TA2gt5WlIZUQrrH6EZrNClwT/H0FateUsZkGIOPRrLbP+PR9A==
|
||||
|
||||
cipher-base@^1.0.0, cipher-base@^1.0.1, cipher-base@^1.0.3:
|
||||
version "1.0.4"
|
||||
resolved "https://registry.yarnpkg.com/cipher-base/-/cipher-base-1.0.4.tgz#8760e4ecc272f4c363532f926d874aae2c1397de"
|
||||
integrity sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q==
|
||||
dependencies:
|
||||
inherits "^2.0.1"
|
||||
safe-buffer "^5.0.1"
|
||||
|
||||
clean-css@^4.2.3:
|
||||
version "4.2.3"
|
||||
resolved "https://registry.npmjs.org/clean-css/-/clean-css-4.2.3.tgz"
|
||||
@@ -1908,11 +1981,6 @@ colors@1.0.3:
|
||||
resolved "https://registry.yarnpkg.com/colors/-/colors-1.0.3.tgz#0433f44d809680fdeb60ed260f1b0c262e82a40b"
|
||||
integrity sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs=
|
||||
|
||||
colors@^1.3.3:
|
||||
version "1.4.0"
|
||||
resolved "https://registry.npmjs.org/colors/-/colors-1.4.0.tgz"
|
||||
integrity sha512-a+UqTh4kgZg/SlGvfbzDHpgRu7AAQOmmqRHJnxhRZICKFUT91brVhNNt58CMWU9PsBbv3PDCZUHbVxuDiH2mtA==
|
||||
|
||||
columnify@~1.5.4:
|
||||
version "1.5.4"
|
||||
resolved "https://registry.npmjs.org/columnify/-/columnify-1.5.4.tgz"
|
||||
@@ -2121,6 +2189,29 @@ create-error-class@^3.0.0:
|
||||
dependencies:
|
||||
capture-stack-trace "^1.0.0"
|
||||
|
||||
create-hash@^1.1.0, create-hash@^1.1.2, create-hash@^1.2.0:
|
||||
version "1.2.0"
|
||||
resolved "https://registry.yarnpkg.com/create-hash/-/create-hash-1.2.0.tgz#889078af11a63756bcfb59bd221996be3a9ef196"
|
||||
integrity sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg==
|
||||
dependencies:
|
||||
cipher-base "^1.0.1"
|
||||
inherits "^2.0.1"
|
||||
md5.js "^1.3.4"
|
||||
ripemd160 "^2.0.1"
|
||||
sha.js "^2.4.0"
|
||||
|
||||
create-hmac@^1.1.4, create-hmac@^1.1.7:
|
||||
version "1.1.7"
|
||||
resolved "https://registry.yarnpkg.com/create-hmac/-/create-hmac-1.1.7.tgz#69170c78b3ab957147b2b8b04572e47ead2243ff"
|
||||
integrity sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg==
|
||||
dependencies:
|
||||
cipher-base "^1.0.3"
|
||||
create-hash "^1.1.0"
|
||||
inherits "^2.0.1"
|
||||
ripemd160 "^2.0.0"
|
||||
safe-buffer "^5.0.1"
|
||||
sha.js "^2.4.8"
|
||||
|
||||
cross-env@7.0.3:
|
||||
version "7.0.3"
|
||||
resolved "https://registry.yarnpkg.com/cross-env/-/cross-env-7.0.3.tgz#865264b29677dc015ba8418918965dd232fc54cf"
|
||||
@@ -2647,18 +2738,18 @@ electron-publish@22.14.5:
|
||||
lazy-val "^1.0.5"
|
||||
mime "^2.5.2"
|
||||
|
||||
electron-rebuild@^3.2.5:
|
||||
version "3.2.5"
|
||||
resolved "https://registry.yarnpkg.com/electron-rebuild/-/electron-rebuild-3.2.5.tgz#a9e82b4259aac33ad449f6959de68ded2c5679f8"
|
||||
integrity sha512-U9dKi10V9w/BdIVB8a8dTKYLK3Q1d2WZ+Yo5qfM3XX/O4jI7KpnwgvWgGoVv0jTWPC2NlebF00ffWS/8NfUAtA==
|
||||
electron-rebuild@^3.2.7:
|
||||
version "3.2.7"
|
||||
resolved "https://registry.yarnpkg.com/electron-rebuild/-/electron-rebuild-3.2.7.tgz#0f56c1cc99a6fec0a5b990532283c2a8c838c19b"
|
||||
integrity sha512-WvaW1EgRinDQ61khHFZfx30rkPQG5ItaOT0wrI7iJv9A3SbghriQGfZQfHZs25fWLBe6/vkv05LOqg6aDw6Wzw==
|
||||
dependencies:
|
||||
"@malept/cross-spawn-promise" "^2.0.0"
|
||||
colors "^1.3.3"
|
||||
chalk "^4.0.0"
|
||||
debug "^4.1.1"
|
||||
detect-libc "^1.0.3"
|
||||
fs-extra "^10.0.0"
|
||||
got "^11.7.0"
|
||||
lzma-native "^8.0.1"
|
||||
lzma-native "^8.0.5"
|
||||
node-abi "^3.0.0"
|
||||
node-api-version "^0.1.4"
|
||||
node-gyp "^8.4.0"
|
||||
@@ -2672,15 +2763,28 @@ electron-to-chromium@^1.3.723:
|
||||
resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.3.736.tgz#f632d900a1f788dab22fec9c62ec5c9c8f0c4052"
|
||||
integrity sha512-DY8dA7gR51MSo66DqitEQoUMQ0Z+A2DSXFi7tK304bdTVqczCAfUuyQw6Wdg8hIoo5zIxkU1L24RQtUce1Ioig==
|
||||
|
||||
electron@16.0.6:
|
||||
version "16.0.6"
|
||||
resolved "https://registry.yarnpkg.com/electron/-/electron-16.0.6.tgz#d7a420ef2cb39d7d0a4d8760c03d72b137a033d5"
|
||||
integrity sha512-Xs9dYLYhcJf3wXn8m2gDqFTb1L862KEhMxOx9swfFBHj6NoUPPtUgw/RyPQ0tXN1XPxG9vnBkoI0BdcKwrLKuQ==
|
||||
electron@16.0.8:
|
||||
version "16.0.8"
|
||||
resolved "https://registry.yarnpkg.com/electron/-/electron-16.0.8.tgz#7ebd3e23c4883c239f53d8b7af1100f455ac8a02"
|
||||
integrity sha512-znTVkl8LaGcPNdfc6SRr+6LYg2GtSCKXln/nW/PC+urBfAFnOYIuDock8QyGVFfzr5PuAa+g8YQQAboHV77D7g==
|
||||
dependencies:
|
||||
"@electron/get" "^1.13.0"
|
||||
"@types/node" "^14.6.2"
|
||||
extract-zip "^1.0.3"
|
||||
|
||||
elliptic@^6.5.3:
|
||||
version "6.5.4"
|
||||
resolved "https://registry.yarnpkg.com/elliptic/-/elliptic-6.5.4.tgz#da37cebd31e79a1367e941b592ed1fbebd58abbb"
|
||||
integrity sha512-iLhC6ULemrljPZb+QutR5TQGB+pdW6KGD5RSegS+8sorOZT+rdQFbsQFJgvN3eRqNALqJer4oQ16YvJHlU8hzQ==
|
||||
dependencies:
|
||||
bn.js "^4.11.9"
|
||||
brorand "^1.1.0"
|
||||
hash.js "^1.0.0"
|
||||
hmac-drbg "^1.0.1"
|
||||
inherits "^2.0.4"
|
||||
minimalistic-assert "^1.0.1"
|
||||
minimalistic-crypto-utils "^1.0.1"
|
||||
|
||||
emoji-regex@^7.0.1:
|
||||
version "7.0.3"
|
||||
resolved "https://registry.npmjs.org/emoji-regex/-/emoji-regex-7.0.3.tgz"
|
||||
@@ -3002,6 +3106,14 @@ events@^3.2.0:
|
||||
resolved "https://registry.npmjs.org/events/-/events-3.2.0.tgz"
|
||||
integrity sha512-/46HWwbfCX2xTawVfkKLGxMifJYQBWMwY1mjywRtb4c9x8l5NP3KoJtnIOiL1hfdRkIuYhETxQlo62IF8tcnlg==
|
||||
|
||||
evp_bytestokey@^1.0.0, evp_bytestokey@^1.0.3:
|
||||
version "1.0.3"
|
||||
resolved "https://registry.yarnpkg.com/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz#7fcbdb198dc71959432efe13842684e0525acb02"
|
||||
integrity sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA==
|
||||
dependencies:
|
||||
md5.js "^1.3.4"
|
||||
safe-buffer "^5.1.1"
|
||||
|
||||
execa@^0.4.0:
|
||||
version "0.4.0"
|
||||
resolved "https://registry.npmjs.org/execa/-/execa-0.4.0.tgz"
|
||||
@@ -3216,9 +3328,9 @@ flush-write-stream@^1.0.0:
|
||||
readable-stream "^2.0.4"
|
||||
|
||||
follow-redirects@^1.14.0:
|
||||
version "1.14.5"
|
||||
resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.14.5.tgz#f09a5848981d3c772b5392309778523f8d85c381"
|
||||
integrity sha512-wtphSXy7d4/OR+MvIFbCVBDzZ5520qV8XfPklSN5QtxuMUJZ+b0Wnst1e1lCDocfzuCkHqj8k0FpZqO+UIaKNA==
|
||||
version "1.14.7"
|
||||
resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.14.7.tgz#2004c02eb9436eee9a21446a6477debf17e81685"
|
||||
integrity sha512-+hbxoLbFMbRKDwohX8GkTataGqO6Jb7jGwpAlwgy2bIz25XtRm7KEzJM76R1WiNT5SwZkX4Y75SwBolkpmE7iQ==
|
||||
|
||||
foreach@^2.0.5:
|
||||
version "2.0.5"
|
||||
@@ -3670,10 +3782,10 @@ got@^9.6.0:
|
||||
to-readable-stream "^1.0.0"
|
||||
url-parse-lax "^3.0.0"
|
||||
|
||||
graceful-fs@^4.1.11, graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.2.0, graceful-fs@^4.2.4, graceful-fs@^4.2.6, graceful-fs@^4.2.8, graceful-fs@~4.1.11:
|
||||
version "4.2.8"
|
||||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.8.tgz#e412b8d33f5e006593cbd3cee6df9f2cebbe802a"
|
||||
integrity sha512-qkIilPUYcNhJpd33n0GBXTB1MMPp14TxEsEs0pTrsSVucApsYzW5V+Q8Qxhik6KU3evy+qkAAowTByymK0avdg==
|
||||
graceful-fs@^4.1.11, graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.2.0, graceful-fs@^4.2.4, graceful-fs@^4.2.6, graceful-fs@^4.2.9, graceful-fs@~4.1.11:
|
||||
version "4.2.9"
|
||||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.9.tgz#041b05df45755e587a24942279b9d113146e1c96"
|
||||
integrity sha512-NtNxqUcXgpW2iMrfqSfR73Glt39K+BLwWsPs94yR63v45T0Wbej7eRmL5cWfwEgqXnmjQp3zaJTshdRW/qC2ZQ==
|
||||
|
||||
"graceful-readlink@>= 1.0.0":
|
||||
version "1.0.1"
|
||||
@@ -3774,6 +3886,23 @@ has@^1.0.3:
|
||||
dependencies:
|
||||
function-bind "^1.1.1"
|
||||
|
||||
hash-base@^3.0.0:
|
||||
version "3.1.0"
|
||||
resolved "https://registry.yarnpkg.com/hash-base/-/hash-base-3.1.0.tgz#55c381d9e06e1d2997a883b4a3fddfe7f0d3af33"
|
||||
integrity sha512-1nmYp/rhMDiE7AYkDw+lLwlAzz0AntGIe51F3RfFfEqyQ3feY2eI/NcwC6umIQVOASPMsWJLJScWKSSvzL9IVA==
|
||||
dependencies:
|
||||
inherits "^2.0.4"
|
||||
readable-stream "^3.6.0"
|
||||
safe-buffer "^5.2.0"
|
||||
|
||||
hash.js@^1.0.0, hash.js@^1.0.3:
|
||||
version "1.1.7"
|
||||
resolved "https://registry.yarnpkg.com/hash.js/-/hash.js-1.1.7.tgz#0babca538e8d4ee4a0f8988d68866537a003cf42"
|
||||
integrity sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==
|
||||
dependencies:
|
||||
inherits "^2.0.3"
|
||||
minimalistic-assert "^1.0.1"
|
||||
|
||||
hawk@~3.1.3:
|
||||
version "3.1.3"
|
||||
resolved "https://registry.yarnpkg.com/hawk/-/hawk-3.1.3.tgz#078444bd7c1640b0fe540d2c9b73d59678e8e1c4"
|
||||
@@ -3789,6 +3918,15 @@ he@^1.2.0:
|
||||
resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f"
|
||||
integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==
|
||||
|
||||
hmac-drbg@^1.0.1:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/hmac-drbg/-/hmac-drbg-1.0.1.tgz#d2745701025a6c775a6c545793ed502fc0c649a1"
|
||||
integrity sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=
|
||||
dependencies:
|
||||
hash.js "^1.0.3"
|
||||
minimalistic-assert "^1.0.0"
|
||||
minimalistic-crypto-utils "^1.0.1"
|
||||
|
||||
hoek@2.x.x:
|
||||
version "2.16.3"
|
||||
resolved "https://registry.yarnpkg.com/hoek/-/hoek-2.16.3.tgz#20bb7403d3cea398e91dc4710a8ff1b8274a25ed"
|
||||
@@ -4026,7 +4164,7 @@ inflight@^1.0.4, inflight@~1.0.6:
|
||||
once "^1.3.0"
|
||||
wrappy "1"
|
||||
|
||||
inherits@2, inherits@^2.0.1, inherits@^2.0.3, inherits@~2.0.0, inherits@~2.0.1, inherits@~2.0.3:
|
||||
inherits@2, inherits@^2.0.1, inherits@^2.0.3, inherits@^2.0.4, inherits@~2.0.0, inherits@~2.0.1, inherits@~2.0.3:
|
||||
version "2.0.4"
|
||||
resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c"
|
||||
integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==
|
||||
@@ -4961,7 +5099,7 @@ lunr@^2.3.9:
|
||||
resolved "https://registry.yarnpkg.com/lunr/-/lunr-2.3.9.tgz#18b123142832337dd6e964df1a5a7707b25d35e1"
|
||||
integrity sha512-zTU3DaZaF3Rt9rhN3uBMGQD3dD2/vFQqnvZCDv4dl5iOzq2IZQqTxu90r4E5J+nP70J3ilqVCrbho2eWaeW8Ow==
|
||||
|
||||
lzma-native@^8.0.0, lzma-native@^8.0.1:
|
||||
lzma-native@^8.0.0, lzma-native@^8.0.5:
|
||||
version "8.0.1"
|
||||
resolved "https://registry.yarnpkg.com/lzma-native/-/lzma-native-8.0.1.tgz#8569e2f88de461a9a2469ac9d8183637c387d682"
|
||||
integrity sha512-Ryr9X3yDVZhRYOxR8QhUBCNe6GdEfy9BvFDIFtUvEkocvSvnrYt9lRm6FR1z0eQn0QSMenrgrDIJRMgUf9zsKQ==
|
||||
@@ -5057,6 +5195,15 @@ matcher@^3.0.0:
|
||||
dependencies:
|
||||
escape-string-regexp "^4.0.0"
|
||||
|
||||
md5.js@^1.3.4:
|
||||
version "1.3.5"
|
||||
resolved "https://registry.yarnpkg.com/md5.js/-/md5.js-1.3.5.tgz#b5d07b8e3216e3e27cd728d72f70d1e6a342005f"
|
||||
integrity sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg==
|
||||
dependencies:
|
||||
hash-base "^3.0.0"
|
||||
inherits "^2.0.1"
|
||||
safe-buffer "^5.1.2"
|
||||
|
||||
mem@^4.0.0:
|
||||
version "4.3.0"
|
||||
resolved "https://registry.npmjs.org/mem/-/mem-4.3.0.tgz"
|
||||
@@ -5155,6 +5302,16 @@ min-indent@^1.0.0:
|
||||
resolved "https://registry.yarnpkg.com/min-indent/-/min-indent-1.0.1.tgz#a63f681673b30571fbe8bc25686ae746eefa9869"
|
||||
integrity sha512-I9jwMn07Sy/IwOj3zVkVik2JTvgpaykDZEigL6Rx6N9LbMywwUSMtxET+7lVoDLLd3O3IXwJwvuuns8UB/HeAg==
|
||||
|
||||
minimalistic-assert@^1.0.0, minimalistic-assert@^1.0.1:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz#2e194de044626d4a10e7f7fbc00ce73e83e4d5c7"
|
||||
integrity sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==
|
||||
|
||||
minimalistic-crypto-utils@^1.0.1:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz#f6c00c1c0b082246e5c4d99dfb8c7c083b2b582a"
|
||||
integrity sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=
|
||||
|
||||
minimatch@3.0.4, minimatch@^3.0.0, minimatch@^3.0.2, minimatch@^3.0.3, minimatch@^3.0.4, minimatch@~3.0.2:
|
||||
version "3.0.4"
|
||||
resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083"
|
||||
@@ -5301,9 +5458,9 @@ nan@^2.13.2, nan@^2.14.1, nan@^2.15.0:
|
||||
integrity sha512-8ZtvEnA2c5aYCZYd1cvgdnU6cqwixRoYg70xPLWUws5ORTa/lnw+u4amixRS/Ac5U5mQVgp9pnlSUnbNWFaWZQ==
|
||||
|
||||
nanoid@^3.1.23:
|
||||
version "3.1.23"
|
||||
resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.1.23.tgz#f744086ce7c2bc47ee0a8472574d5c78e4183a81"
|
||||
integrity sha512-FiB0kzdP0FFVGDKlRLEQ1BgDzU87dy5NnzjeW9YZNt+/c3+q82EQDUwniSAUxp/F0gFNI1ZhKU1FqYsMuqZVnw==
|
||||
version "3.2.0"
|
||||
resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.2.0.tgz#62667522da6673971cca916a6d3eff3f415ff80c"
|
||||
integrity sha512-fmsZYa9lpn69Ad5eDn7FMcnnSR+8R34W9qJEijxYhTbfOWzr22n1QxCMzXLK+ODyW2973V3Fux959iQoUxzUIA==
|
||||
|
||||
natural-compare@^1.4.0:
|
||||
version "1.4.0"
|
||||
@@ -5381,9 +5538,11 @@ node-fetch-npm@^2.0.1:
|
||||
safe-buffer "^5.0.1"
|
||||
|
||||
node-fetch@^2.6.0:
|
||||
version "2.6.1"
|
||||
resolved "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.1.tgz"
|
||||
integrity sha512-V4aYg89jEoVRxRb2fJdAg8FHvI7cEyYdVAh94HH0UIK8oJxUfkjlDQN9RbMx+bEjP7+ggMiFRprSti032Oipxw==
|
||||
version "2.6.7"
|
||||
resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.7.tgz#24de9fba827e3b4ae44dc8b20256a379160052ad"
|
||||
integrity sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==
|
||||
dependencies:
|
||||
whatwg-url "^5.0.0"
|
||||
|
||||
node-gyp-build@^4.2.1:
|
||||
version "4.2.3"
|
||||
@@ -6043,6 +6202,17 @@ parent-module@^1.0.0:
|
||||
dependencies:
|
||||
callsites "^3.0.0"
|
||||
|
||||
parse-asn1@^5.1.5:
|
||||
version "5.1.6"
|
||||
resolved "https://registry.yarnpkg.com/parse-asn1/-/parse-asn1-5.1.6.tgz#385080a3ec13cb62a62d39409cb3e88844cdaed4"
|
||||
integrity sha512-RnZRo1EPU6JBnra2vGHj0yhp6ebyjBZpmUCLHWiFhxlzvBCCpAuZ7elsBp1PVAbQN0/04VD/19rfzlBSwLstMw==
|
||||
dependencies:
|
||||
asn1.js "^5.2.0"
|
||||
browserify-aes "^1.0.0"
|
||||
evp_bytestokey "^1.0.0"
|
||||
pbkdf2 "^3.0.3"
|
||||
safe-buffer "^5.1.1"
|
||||
|
||||
parse-author@^2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.npmjs.org/parse-author/-/parse-author-2.0.0.tgz"
|
||||
@@ -6168,6 +6338,17 @@ path@^0.12.7:
|
||||
process "^0.11.1"
|
||||
util "^0.10.3"
|
||||
|
||||
pbkdf2@^3.0.3:
|
||||
version "3.1.2"
|
||||
resolved "https://registry.yarnpkg.com/pbkdf2/-/pbkdf2-3.1.2.tgz#dd822aa0887580e52f1a039dc3eda108efae3075"
|
||||
integrity sha512-iuh7L6jA7JEGu2WxDwtQP1ddOpaJNC4KlDEFfdQajSGgGPNi4OyDc2R7QnbY2bR9QjBVGwgvTdNJZoE7RaxUMA==
|
||||
dependencies:
|
||||
create-hash "^1.1.2"
|
||||
create-hmac "^1.1.4"
|
||||
ripemd160 "^2.0.1"
|
||||
safe-buffer "^5.0.1"
|
||||
sha.js "^2.4.8"
|
||||
|
||||
pend@~1.2.0:
|
||||
version "1.2.0"
|
||||
resolved "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz"
|
||||
@@ -6660,7 +6841,7 @@ quick-lru@^5.1.1:
|
||||
resolved "https://registry.npmjs.org/quick-lru/-/quick-lru-5.1.1.tgz"
|
||||
integrity sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==
|
||||
|
||||
randombytes@^2.1.0:
|
||||
randombytes@^2.0.1, randombytes@^2.1.0:
|
||||
version "2.1.0"
|
||||
resolved "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz"
|
||||
integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==
|
||||
@@ -7084,6 +7265,14 @@ rimraf@~2.6.1:
|
||||
dependencies:
|
||||
glob "^7.0.5"
|
||||
|
||||
ripemd160@^2.0.0, ripemd160@^2.0.1:
|
||||
version "2.0.2"
|
||||
resolved "https://registry.yarnpkg.com/ripemd160/-/ripemd160-2.0.2.tgz#a1c1a6f624751577ba5d07914cbc92850585890c"
|
||||
integrity sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA==
|
||||
dependencies:
|
||||
hash-base "^3.0.0"
|
||||
inherits "^2.0.1"
|
||||
|
||||
roarr@^2.15.3:
|
||||
version "2.15.4"
|
||||
resolved "https://registry.npmjs.org/roarr/-/roarr-2.15.4.tgz"
|
||||
@@ -7110,7 +7299,7 @@ run-queue@^1.0.0, run-queue@^1.0.3:
|
||||
dependencies:
|
||||
aproba "^1.1.1"
|
||||
|
||||
safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@^5.2.1, safe-buffer@~5.2.0:
|
||||
safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@^5.2.0, safe-buffer@^5.2.1, safe-buffer@~5.2.0:
|
||||
version "5.2.1"
|
||||
resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6"
|
||||
integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==
|
||||
@@ -7232,6 +7421,14 @@ set-blocking@^2.0.0, set-blocking@~2.0.0:
|
||||
resolved "https://registry.yarnpkg.com/set-blocking/-/set-blocking-2.0.0.tgz#045f9782d011ae9a6803ddd382b24392b3d890f7"
|
||||
integrity sha1-BF+XgtARrppoA93TgrJDkrPYkPc=
|
||||
|
||||
sha.js@^2.4.0, sha.js@^2.4.8:
|
||||
version "2.4.11"
|
||||
resolved "https://registry.yarnpkg.com/sha.js/-/sha.js-2.4.11.tgz#37a5cf0b81ecbc6943de109ba2960d1b26584ae7"
|
||||
integrity sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ==
|
||||
dependencies:
|
||||
inherits "^2.0.1"
|
||||
safe-buffer "^5.0.1"
|
||||
|
||||
sha@~2.0.1:
|
||||
version "2.0.1"
|
||||
resolved "https://registry.npmjs.org/sha/-/sha-2.0.1.tgz"
|
||||
@@ -7276,10 +7473,10 @@ shell-quote@^1.7.3:
|
||||
resolved "https://registry.yarnpkg.com/shell-quote/-/shell-quote-1.7.3.tgz#aa40edac170445b9a431e17bb62c0b881b9c4123"
|
||||
integrity sha512-Vpfqwm4EnqGdlsBFNmHhxhElJYrdfcxPThu+ryKS5J8L/fhAwLazFZtq+S+TWZ9ANj2piSQLGj6NQg+lKPmxrw==
|
||||
|
||||
shelljs@0.8.4:
|
||||
version "0.8.4"
|
||||
resolved "https://registry.npmjs.org/shelljs/-/shelljs-0.8.4.tgz"
|
||||
integrity sha512-7gk3UZ9kOfPLIAbslLzyWeGiEqx9e3rxwZM0KE6EL8GlGwjym9Mrlx5/p33bWTu9YG6vcS4MBxYZDHYr5lr8BQ==
|
||||
shelljs@0.8.5:
|
||||
version "0.8.5"
|
||||
resolved "https://registry.yarnpkg.com/shelljs/-/shelljs-0.8.5.tgz#de055408d8361bed66c669d2f000538ced8ee20c"
|
||||
integrity sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==
|
||||
dependencies:
|
||||
glob "^7.0.0"
|
||||
interpret "^1.0.0"
|
||||
@@ -8091,6 +8288,11 @@ tough-cookie@~2.5.0:
|
||||
psl "^1.1.28"
|
||||
punycode "^2.1.1"
|
||||
|
||||
tr46@~0.0.3:
|
||||
version "0.0.3"
|
||||
resolved "https://registry.yarnpkg.com/tr46/-/tr46-0.0.3.tgz#8184fd347dac9cdc185992f3a6622e14b9d9ab6a"
|
||||
integrity sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=
|
||||
|
||||
trim-newlines@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.npmjs.org/trim-newlines/-/trim-newlines-1.0.0.tgz"
|
||||
@@ -8473,6 +8675,11 @@ wcwidth@^1.0.0, wcwidth@^1.0.1:
|
||||
dependencies:
|
||||
defaults "^1.0.3"
|
||||
|
||||
webidl-conversions@^3.0.0:
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/webidl-conversions/-/webidl-conversions-3.0.1.tgz#24534275e2a7bc6be7bc86611cc16ae0a5654871"
|
||||
integrity sha1-JFNCdeKnvGvnvIZhHMFq4KVlSHE=
|
||||
|
||||
webpack-bundle-analyzer@^4.5.0:
|
||||
version "4.5.0"
|
||||
resolved "https://registry.yarnpkg.com/webpack-bundle-analyzer/-/webpack-bundle-analyzer-4.5.0.tgz#1b0eea2947e73528754a6f9af3e91b2b6e0f79d5"
|
||||
@@ -8488,15 +8695,15 @@ webpack-bundle-analyzer@^4.5.0:
|
||||
sirv "^1.0.7"
|
||||
ws "^7.3.1"
|
||||
|
||||
webpack-cli@^4.9.1:
|
||||
version "4.9.1"
|
||||
resolved "https://registry.yarnpkg.com/webpack-cli/-/webpack-cli-4.9.1.tgz#b64be825e2d1b130f285c314caa3b1ba9a4632b3"
|
||||
integrity sha512-JYRFVuyFpzDxMDB+v/nanUdQYcZtqFPGzmlW4s+UkPMFhSpfRNmf1z4AwYcHJVdvEFAM7FFCQdNTpsBYhDLusQ==
|
||||
webpack-cli@^4.9.2:
|
||||
version "4.9.2"
|
||||
resolved "https://registry.yarnpkg.com/webpack-cli/-/webpack-cli-4.9.2.tgz#77c1adaea020c3f9e2db8aad8ea78d235c83659d"
|
||||
integrity sha512-m3/AACnBBzK/kMTcxWHcZFPrw/eQuY4Df1TxvIWfWM2x7mRqBQCqKEd96oCUa9jkapLBaFfRce33eGDb4Pr7YQ==
|
||||
dependencies:
|
||||
"@discoveryjs/json-ext" "^0.5.0"
|
||||
"@webpack-cli/configtest" "^1.1.0"
|
||||
"@webpack-cli/info" "^1.4.0"
|
||||
"@webpack-cli/serve" "^1.6.0"
|
||||
"@webpack-cli/configtest" "^1.1.1"
|
||||
"@webpack-cli/info" "^1.4.1"
|
||||
"@webpack-cli/serve" "^1.6.1"
|
||||
colorette "^2.0.14"
|
||||
commander "^7.0.0"
|
||||
execa "^5.0.0"
|
||||
@@ -8514,15 +8721,15 @@ webpack-merge@^5.7.3:
|
||||
clone-deep "^4.0.1"
|
||||
wildcard "^2.0.0"
|
||||
|
||||
webpack-sources@^3.2.2:
|
||||
version "3.2.2"
|
||||
resolved "https://registry.yarnpkg.com/webpack-sources/-/webpack-sources-3.2.2.tgz#d88e3741833efec57c4c789b6010db9977545260"
|
||||
integrity sha512-cp5qdmHnu5T8wRg2G3vZZHoJPN14aqQ89SyQ11NpGH5zEMDCclt49rzo+MaRazk7/UeILhAI+/sEtcM+7Fr0nw==
|
||||
webpack-sources@^3.2.3:
|
||||
version "3.2.3"
|
||||
resolved "https://registry.yarnpkg.com/webpack-sources/-/webpack-sources-3.2.3.tgz#2d4daab8451fd4b240cc27055ff6a0c2ccea0cde"
|
||||
integrity sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==
|
||||
|
||||
webpack@^5.65.0:
|
||||
version "5.65.0"
|
||||
resolved "https://registry.yarnpkg.com/webpack/-/webpack-5.65.0.tgz#ed2891d9145ba1f0d318e4ea4f89c3fa18e6f9be"
|
||||
integrity sha512-Q5or2o6EKs7+oKmJo7LaqZaMOlDWQse9Tm5l1WAfU/ujLGN5Pb0SqGeVkN/4bpPmEqEP5RnVhiqsOtWtUVwGRw==
|
||||
webpack@^5.67.0:
|
||||
version "5.67.0"
|
||||
resolved "https://registry.yarnpkg.com/webpack/-/webpack-5.67.0.tgz#cb43ca2aad5f7cc81c4cd36b626e6b819805dbfd"
|
||||
integrity sha512-LjFbfMh89xBDpUMgA1W9Ur6Rn/gnr2Cq1jjHFPo4v6a79/ypznSYbAyPgGhwsxBtMIaEmDD1oJoA7BEYw/Fbrw==
|
||||
dependencies:
|
||||
"@types/eslint-scope" "^3.7.0"
|
||||
"@types/estree" "^0.0.50"
|
||||
@@ -8538,7 +8745,7 @@ webpack@^5.65.0:
|
||||
eslint-scope "5.1.1"
|
||||
events "^3.2.0"
|
||||
glob-to-regexp "^0.4.1"
|
||||
graceful-fs "^4.2.4"
|
||||
graceful-fs "^4.2.9"
|
||||
json-parse-better-errors "^1.0.2"
|
||||
loader-runner "^4.2.0"
|
||||
mime-types "^2.1.27"
|
||||
@@ -8547,7 +8754,15 @@ webpack@^5.65.0:
|
||||
tapable "^2.1.1"
|
||||
terser-webpack-plugin "^5.1.3"
|
||||
watchpack "^2.3.1"
|
||||
webpack-sources "^3.2.2"
|
||||
webpack-sources "^3.2.3"
|
||||
|
||||
whatwg-url@^5.0.0:
|
||||
version "5.0.0"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-url/-/whatwg-url-5.0.0.tgz#966454e8765462e37644d3626f6742ce8b70965d"
|
||||
integrity sha1-lmRU6HZUYuN2RNNib2dCzotwll0=
|
||||
dependencies:
|
||||
tr46 "~0.0.3"
|
||||
webidl-conversions "^3.0.0"
|
||||
|
||||
which-boxed-primitive@^1.0.1, which-boxed-primitive@^1.0.2:
|
||||
version "1.0.2"
|
||||
@@ -8891,20 +9106,7 @@ yargs@^16.2.0:
|
||||
y18n "^5.0.5"
|
||||
yargs-parser "^20.2.2"
|
||||
|
||||
yargs@^17.0.1:
|
||||
version "17.1.0"
|
||||
resolved "https://registry.yarnpkg.com/yargs/-/yargs-17.1.0.tgz#0cd9827a0572c9a1795361c4d1530e53ada168cf"
|
||||
integrity sha512-SQr7qqmQ2sNijjJGHL4u7t8vyDZdZ3Ahkmo4sc1w5xI9TBX0QDdG/g4SFnxtWOsGLjwHQue57eFALfwFCnixgg==
|
||||
dependencies:
|
||||
cliui "^7.0.2"
|
||||
escalade "^3.1.1"
|
||||
get-caller-file "^2.0.5"
|
||||
require-directory "^2.1.1"
|
||||
string-width "^4.2.0"
|
||||
y18n "^5.0.5"
|
||||
yargs-parser "^20.2.2"
|
||||
|
||||
yargs@^17.2.1:
|
||||
yargs@^17.0.1, yargs@^17.2.1:
|
||||
version "17.3.1"
|
||||
resolved "https://registry.yarnpkg.com/yargs/-/yargs-17.3.1.tgz#da56b28f32e2fd45aefb402ed9c26f42be4c07b9"
|
||||
integrity sha512-WUANQeVgjLbNsEmGk20f+nlHgOqzRFpiGWVaBrYGYIGANIIu3lWjoyi0fNlFmJkvfhCZ6BXINe7/W2O2bV4iaA==
|
||||
|
Reference in New Issue
Block a user