Відновити Zsh-термінал (OS X Lion)


17

OS X Lion має функцію "Відновити", тобто, коли ви знову відкриваєте додаток, він відновлює всі вікна та їх вміст. Це працює і для Терміналу. Але якщо ви використовуєте Zsh замість Bash, він не відновлює відкритий каталог. Як я можу це виправити?


Пов’язані з відповідями нижче: інформування terminal.app про каталог також корисно для відкриття нових терміналів у тому самому каталозі, що й поточний
nhooyr

Відповіді:


18

ОНОВЛЕННЯ : Це не зовсім правильно, з причин, зазначених у коментарях. Скористайтеся нижченаведеною відповіддю . Дякуємо @ChrisPage, що пройшов зайву милю :)

Відповідь можна знайти за допомогою зворотної інженерії, як це робиться /etc/bashrc. Я спробував багато підходів з усієї мережі, але спосіб Apple, здається, найкраще працює (зрозумійте).

У вашому .zshrcоном наступному

# Set Apple Terminal.app resume directory
if [[ $TERM_PROGRAM == "Apple_Terminal" ]] && [[ -z "$INSIDE_EMACS" ]] {
  function chpwd {
    local SEARCH=' '
    local REPLACE='%20'
    local PWD_URL="file://$HOSTNAME${PWD//$SEARCH/$REPLACE}"
    printf '\e]7;%s\a' "$PWD_URL"
  }

  chpwd
}

Щасливе відновлення.

Для уточнення, ця відповідь стосується загадкового повідомлення в налаштуваннях OS X Lion's Terminal.app:

** Програми повідомляють про термінал поточного робочого каталогу за допомогою послідовностей евакуації. Можливо, вам знадобиться налаштувати оболонку чи інші програми, щоб увімкнути цю поведінку. *

Ця відповідь працює, коли ви використовуєте zsh як оболонку. Термінальне резюме для bash вже було впроваджено Apple.


1
Напевно, це не велика річ на практиці, але я бачу, що акція / etc / bashrc має останній рядок chpwdяк printf '\e]7;%s\a' "$PWD_URL"з подвійними котируваннями. Дякую за пораду.
Ryan McCuaig

Тепер це пробивається в о- мі-зш (див. Github.com/robbyrussell/oh-my-zsh/pull/522 ). Вам потрібно переконатися, що ви увімкнули плагін osx у своєму zshrc.
Ryan McCuaig

2
Також зауважте, що цей код кодує лише відсотки пробілів. Для бонусних очок зробіть це відсотковим кодуванням усіх незаконних символів URL-адреси (і подивіться, чи можна це зробити, не викликаючи жодної програми). Це важливо, якщо ви хочете, щоб він працював з усіма дійсними іменами шляхів. Крім того, деякі символи навіть не вважаються частиною послідовностей евакуації, тому для перенесення їх до терміналу потрібно відсоткове кодування. Я зміг це зробити для bash, але я не намагався перевірити це на zsh.
Кріс Пейдж

1
Цитати навколо "$ PWD_URL" необхідні для запобігання зміні імені шляху. EDIT: Це потрібно в bash, але необов’язково в zsh. Я вважаю за краще використовувати цитати послідовно, щоб вони були портативними.
Кріс Пейдж

Дякую, Райан, Кріс. Я оновив сценарій, щоб використовувати подвійні лапки для послідовності.
капітан

27

Ось моя адаптація / etc / bashrc для zsh. Я включив відсоткове кодування всіх символів URL, які цього потребують, що важливо, якщо ви хочете, щоб це працювало з усіма дійсними іменами файлів та каталогів.

Це реєструє precmdгак, який дозволяє реєструвати більше однієї функції в інших скриптах та файлах конфігурації.

ОНОВЛЕНО березень 2019: Встановіть LC_ALLпорожнє, щоб воно не перекривало LC_CTYPE. Використовуйте precmdдля оновлення робочого каталогу в кожному запиті, а не chpwdдля оновлення кожного разу, коли він змінюється - командні конвеєри можуть тимчасово змінювати його, а термінал не повинен їх відображати. Також може бути корисним кожне оперативне оновлення стану терміналу у випадку, якщо воно було змінено під час попередньої команди. Використовуйте printf -vдля явного запису до змінної замість використання синтаксису нижньої оболонки.

# Tell the terminal about the working directory whenever it changes.

if [[ "$TERM_PROGRAM" == "Apple_Terminal" ]] && [[ -z "$INSIDE_EMACS" ]]; then

    update_terminal_cwd() {
        # Identify the directory using a "file:" scheme URL, including
        # the host name to disambiguate local vs. remote paths.

        # Percent-encode the pathname.
        local url_path=''
        {
            # Use LC_CTYPE=C to process text byte-by-byte. Ensure that
            # LC_ALL isn't set, so it doesn't interfere.
            local i ch hexch LC_CTYPE=C LC_ALL=
            for ((i = 1; i <= ${#PWD}; ++i)); do
                ch="$PWD[i]"
                if [[ "$ch" =~ [/._~A-Za-z0-9-] ]]; then
                    url_path+="$ch"
                else
                    printf -v hexch "%02X" "'$ch"
                    url_path+="%$hexch"
                fi
            done
        }

        printf '\e]7;%s\a' "file://$HOST$url_path"
    }

    # Register the function so it is called at each prompt.
    autoload add-zsh-hook
    add-zsh-hook precmd update_terminal_cwd
fi

Дякую, прийняте рішення не працювало для мене, але це все одно.
eelco

Цей працює і для мене.
sikachu

4
Слід також зазначити, що це рішення вже є в ой-мі-зш , просто активуйте terminalappплагін.
Симон

1
Щоб зрозуміти, @Simon означає, що це зараз в о- мі-зш , додане з моменту написання цієї відповіді.
Кріс Пейдж

Це правильно @ChrisPage, я вибачаюся за неоднозначне фразування (англійська мова не є моєю рідною мовою). Те , що я хотів сказати тільки , що вам не потрібно , щоб вставити це в вашому .zprofileабо що - то, як я зробив , перш ніж зрозумів , що це насправді доступні в oh-my-zsh. Саме в цьому рішенні саме таке рішення, і ти заслуговуєш усієї заслуги.
Саймон
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.