Quantcast
Channel: SanRin舎 » Vim
Viewing all 10 articles
Browse latest View live

Vimであるディレクトリ以下でファイルの保存したら、あるディレクトリ以下にコピーする

$
0
0

/hoge/piyoと~/piyoが同じディレクトリ構造していて、/hoge/piyo/fuga/hogera.htmlを保存したら、~/piyo/fuga/hogera.htmlにコピーするみたいな。

" vimrc全体で使うaugroup
augroup MyVimrc
    autocmd!
augroup END

" from以下でファイルの保存したら、to以下にディレクトリ構成を保ってコピーする
autocmd MyVimrc BufWritePost * call AutoCopy()
function! AutoCopy()
    let l:dir_list = [
                \    {
                \      'from' : '/hoge/piyo',
                \      'to'   : expand('~/piyo'),
                \    },
                \    {
                \      'from' : expand('~/git/fuga'),
                \      'to'   : '/usr/local/www/apache22/fuga',
                \    },
                \]

    for l:dir in l:dir_list
        " g:from以下のファイルなら
        if stridx(expand("%:p"), l:dir['from']) == 0
            " ファイル名を除いたフルパスからfrom部分を削除して、toにつなげる。
            " バックスラッシュをエスケープする必要あり
            let l:target_dir = l:dir['to'] . substitute(expand("%:p:h"), escape(l:dir['from'],'\'), '' , '')

            if !isdirectory(l:target_dir)
                call mkdir(l:target_dir, "p")
            endif

            let l:target_file = l:dir['to'] . substitute(expand("%:p"), escape(l:dir['from'],'\'), '' , '')
            call writefile(readfile(expand('%:p'), 'b'), l:target_file, 'b')
        endif
    endfor
endfunction

  • fromとtoを設定する。
  • 設定は絶対パスで。~を使う場合はexpandしてやる
  • /homeが/usr/homeのシンボリックリンクだったりするので~をexpandで展開してやるほうが無難。
  • windowsの場合はC:などから始める。set shellslashしている場合はスラッシュ、してない場合はバックスラッシュでディレクトリを区切る

てな感じで。

関連


Vimで四則演算+αする

$
0
0

1 + (10 % 3) * log(2)\=

と打ったら

1 + (10 % 3) * log(2) = 1.693147

こうなるようにmapする。

設定こちら。

inoremap <Leader>= <Esc>^y$A<Space>=<Space><C-r>=<C-r>"<CR>

<Leader>はデフォルトだと\。

<Esc>でノーマルモードになって、^でインデントを除いた先頭に移動。
y$で行末までヤンク。Aで行末でインサートモード。
<Space>=<Space>は単なる入力。
<C-r>=はその後に入力されたものが式として評価され、結果が挿入されるので、<C-r>”でヤンクした内容をペーストしてEnter。

式については:h eval、関数一覧は:h function-listで見れる。

終わり。

Vimの外部コマンド実行でaliasを使う

$
0
0

.bashrcや.zshrcなどにaliasを書いても、その設定はログインシェルやインタラクティブシェルでしか読み込まれないので、vimで :!{cmd} したときは適用されない。

:set shellcmdflag=-ic として、インタラクティブシェルとして起動して、外部コマンドを実行することもできるけど、vimに戻るとき $ fg しなくてならなくて面倒。

常に使いたい設定は、bashなら .bashrcに

export BASH_ENV='~/.bashenv'
source ~/.bashenv

などとしておいて、.bashenvに設定を書く。さらにaliasを展開したい場合は.bashenvに shopt -s expand_aliases と書いておく。

zshの場合は$ZDOTDIR/.zshenv ($ZDOTDIRは指定してない場合は$HOME) に書く。

ただ、そこで書いた設定はbashやzshのシェルスクリプト実行時にも適用されてしまうので、aliasが悪さをしてしまうことがあるかもしれない(zshのシェルスクリプトの心配までしなくていいと思うけど)。

そこで$BASH_ENVの設定はvimrc内で設定( let $BASH_ENV=expand('~/.bashenv') )するようにするとか、~/.vim/.zshenvに設定しておいて、 let $ZDOTDIR=expand('~/.vim') して、シェルスクリプト実行時は読み込まないようにしたほうがいいかもしれない。

参考にしたサイト

Vimでwordpressに投稿する

$
0
0

VimRepressというvimプラグインを使う。

インストール

neobundleを使ってvimプラグインをインストールする。
本家のbitbucketリポジトリ(pentie / vimrepress — Bitbucket)からインストールしたい場合はmercurialが必要。macだと

$ brew install mercurial

でインストールできる。

NeoBundleLazy 'https://bitbucket.org/pentie/vimrepress', {
               'autoload' : { 'commands' : [
                   'BlogList', 'BlogNew', 'BlogSave', 'BlogPreview'
               ]}
            }
" markdownで各人はシンタックスファイルも。いろいろあるのでどれがいいかわらない
NeoBundle 'tpope/vim-markdown'

fork版のsousu/VimRepress · GitHub だと、投稿前の原稿を保存できる。

設定

~/.vimrepressに

[Blog0]
blog_url = http://a-blog.com/
username = admin
password = 123456

みたいな感じに書く。passwordは設定せずに毎回入力することもできる。blog_urlはxmlrpc.phpがあるパスに設定する。

GitでWordPressにPostしたいと思ったけど結局VimRepress導入した «
haya14busa
にも書いてあるように、EditFomat: markdownにすると、markdownがvimrepressによってHTMLに変換され投稿されるけどそうせずに、EditFomat: HTMLにして変換せずに投稿、WordpressのプラグインMarkdown on save Improvedで変換するようにした。

EditFormat: markdownにして変換したい場合はmarkdown2をインストールするのと、vimが+pythonでコンパイルされている必要がある。MacVim Kaoriya版だと+python/dynでインストールされているけど、macに標準でインストールされる/usr/bin/pythonの方をつかうらしい。なので、homebrewでインストールするとうまくいかなかった。/usr/bin/easy_installを使う。

$ sudo easy_install markdown2

その辺の話題

YAMLを書くときのVimの設定

$
0
0

YAMLが長くなると、どこにいるかわからなくなるので設定した。

リンク先のfoldCCというプラグインを使うと、折りたたみの表示が改善され、折りたたまれた部分のインデントがわかりやすくなる。
また、:echo foldC#navi()をやると、カーソル位置の折りたたみの階層を表示してくれる。

例えば、こんな風に設定をする。

set foldtext=foldCC#foldtext()
set fillchars=vert:\|
let g:foldCCtext_head = ''
let g:foldCCtext_tail = 'printf(" %4d lines Lv%-2d", v:foldend-v:foldstart+1, v:foldlevel)'

nnoremap <Leader><C-g> :echo foldCC#navi()<CR>

上の部分が折りたたみの表示の設定部分で、下がカーソル位置の折り畳みの階層表示のキーマッピング。

あとは、yamlのfoldingの設定。

オリジナルのコードだと、yamlのシンタックスハイライトが何も効かなくなってしまったので、やっつけだけど修正した。

インストールして、YAMLファイル開いたらfoldmethodをsyntaxにするように設定すればおk。

augroup MyVimrc
    autocmd!
augroup END
autocmd MyVimrc FileType yaml setlocal foldmethod=syntax

例えば、YAML – Wikipedia, the free encyclopediaにあるサンプルを使うと

---
receipt:     Oz-Ware Purchase Invoice
date:        2012-08-06
customer:
    given:   Dorothy
    family:  Gale

items:
    - part_no:   A4786
      descrip:   Water Bucket (Filled)
      price:     1.47
      quantity:  4

    - part_no:   E1628
      descrip:   High Heeled "Ruby" Slippers
      size:      8
      price:     100.27
      quantity:  1

bill-to:  &id001
    street: |
            123 Tornado Alley
            Suite 16
    city:   East Centerville
    state:  KS

ship-to:  *id001

specialDelivery:  >
    Follow the Yellow Brick
    Road to the Emerald City.
    Pay no attention to the
    man behind the curtain.
...

が最大限折りたためれると、

---                                                              34 lines Lv1

一つ広げると

---
receipt:     Oz-Ware Purchase Invoice
date:        2012-08-06
customer:                                                         4 lines Lv2
items:                                                           12 lines Lv2
bill-to:  &id001                                                  7 lines Lv2
ship-to:  *id001                                                  2 lines Lv2
specialDelivery:  >                                               5 lines Lv2
...

さらに広げると

---
receipt:     Oz-Ware Purchase Invoice
date:        2012-08-06
customer:
    given:   Dorothy
    family:  Gale                                                 2 lines Lv3
items:
    - part_no:   A4786                                            5 lines Lv3
    - part_no:   E1628                                            6 lines Lv3
bill-to:  &id001
    street: |                                                     3 lines Lv3
    city:   East Centerville
    state:  KS                                                    2 lines Lv3
ship-to:  *id001

specialDelivery:  >
    Follow the Yellow Brick
    Road to the Emerald City.
    Pay no attention to the
    man behind the curtain.
...

な風になって、

items:
    - part_no:   A4786
      descrip:   Water Bucket (Filled)
    #

#上にカーソルがあるときに<Leader><C-g>を打つと

--- > items: > - part_no: A4786

と表示される。

GUIのMacVimでsudoを使う

$
0
0

GUIのMacVimでsudoを使おうとすると

sudo: no tty present and no askpass program specified

と出てきて、sudoに失敗する。ググってみるとsudo visudoして

Defaults visiblepw

を追記すると良いということがわかるので追記して実行してみると

:!sudo ls

みたいのはできるけど、以下のようなものはパスワード入力する隙を与えられず失敗する。

:w !sudo tee %
Password:Sorry, try again.
Password:Sorry, try again.
Password:Sorry, try again.
sudo: 3 incorrect password attempts

そこでaskpassを使う。
Kaoriya版MacVimなら/Applications/MacVim.app/Contents/MacOS/macvim-askpassというシェルスクリプトが入っている。

.gvimrcに以下のような設定を書く。

if has('gui_macvim')
    let $SUDO_ASKPASS="/Applications/MacVim.app/Contents/MacOS/macvim-askpass"
    let $DISPLAY=":0"
endif

そして、またもや失敗する。これはこのスクリプトが書かれた当時のダイアログの戻り値は

text returned:<入力値>, button returned:OK

みたい感じだったんだろうけど、現在はtext returnedとbutton returenedの順番が逆になっていて、sedして、<入力値>を取得しているところで、失敗しているため。

修正プルリクった(fix bug of macvim-askpass by tmsanrinsha · Pull Request #1 · splhack/macvim)けど、
markcarver/mac-ssh-askpassはちゃんと動くのでこちらを使ってもいいかも。

ちなみにsudoを何度も試すのにあたって、パスワードのキャッシュを消す必要があったが、sudo -kで消すことができる。

gmarik/sudo-gui.vimというのもあるが、こちらはダイアログにフォーカスしないし、パスワードのキャッシュをしないので使いにくい。

rmtrashだとごみ箱から戻せないのでmv2trashを使うことにした

$
0
0

rmtrashは単に~/.Trashにmvしているだけのようで、ゴミ箱のコンテキストメニューに「戻る」が出ない。
そこで小飼弾氏が作った mv2trashを使うことにした。

こちらを使うとAppleScriptからFinderでゴミ箱に移動しているので、コンテキストメニューに「戻る」が出るし、Finderでcmd+zして戻すこともできる。
これをrmtrashにリネームして、

$ curl -L https://raw.githubusercontent.com/dankogai/osx-mv2trash/master/bin/mv2trash > ~/bin/rmtrash
$ chmod a+x ~/bin/rmtrash

エイリアスを設定する。

alias rm=rmtrash

rmtrashにリネームしているのは、vimfilerやunite.vimでは、rmtrash(Mac)やtrashcli(Linux)といったコマンドがあると、ファイル・ディレクトリを削除するときにそれらを使うので(:h vimfiler)。

ちなみにunite.vimでファイルを削除するには

call unite#custom#alias('file', 'delete', 'vimfiler__delete')

と設定しておく。これでdで削除できるようになる(:h unite.vim

GitのhookでCtagsを実行する

$
0
0

Ctagsを使って、クラス名や関数名のインデックスを記述したtagsファイルを作っておくと、vimでキーワード上にカーソルをおいて、<C-]>を打つと、そのキーワードが定義された場所に飛んでくれて便利。

しかし、新たにキーワードが増えるたびにctagsを手動で実行するは面倒なのでGitのhookを使うことにする。
また、複数のプロジェクトがあるとき、各プロジェクトごとにtagsファイルを分けておくと、余計な候補が出なくてよいが、うまくやらないとプロジェクトを変えるたびに:set tagsでtagsファイルの指定を変更なくてはならないし、tagsファイルをGitのディレクトリ以下に置くと、.gitignoreで無視してやらなくてはならなかったりするので、その辺を解決させる。

まぁ、vimプラグインで有名なtpopeのtbaggery – Effortless Ctags with Git設定をほぼ訳した感じで、Vim – ctagsと連携するように環境を構築する – Qiitaでかなりまとめられている話しであるが…。

hookをつくる

まず、gitのバージョンが1.7.1以上であれは、git initやcloneした時に、templatedirで指定したディレクトリ以下のファイルを.git以下にコピーしてくれるのでそれを作る。

git config --global init.templatedir '~/.git_template'
mkdir -p ~/.git_template/hooks

次にctagsを実行するシェルスクリプトを~/.git_template/hooks/ctagsというファイル名で作る。

#!/usr/bin/env bash
set -e
PATH="$HOME/local/bin:/usr/local/bin:$PATH"
cd "$(dirname "${BASH_SOURCE:-$0}")"; cd ../../
trap "rm -f .git/tags.$$" EXIT
ctags --tag-relative -R -f .git/tags.$$ --exclude=.git
mv .git/tags.$$ .git/tags

$PATHはお好みで。
cdの部分で、gitのルートディレクトリに移動している( bash/zshでsourceされたスクリプト内で、ファイル自身の絶対パスをとるシンプルな記法 – Qiita)。hookで使われる場合は実行ディレクトリはgitのルートディレクトリなので必要ないが、それ以外でも実行したい場合に必要。
trapの部分は、このシェルスクリプトが終了時したときにtags.$$という一時ファイルを消すという意味。
$$はこのシェルスクリプトのPID。同時にシェルスクリプトが実行された時のことを考慮してる?
5行目でctagsを実行している。
–tag-relativeは生成するtagsファイルに記すパスをtagsファイルからの相対パスにするオプション。これをつけないと、ctagsを実行したディレクトリからの相対パスになってしまい、うまく扱えなくなる。ちなみにこのオプションを使う代わりにctagsの引数に` pwd`をつけるとtagsファイル内のパスが絶対パスになり、tagsファイルを移動させても、問題がなくなる。
-Rはディレクトリ以下から再帰的にインデックスを作るオプション
-fは作るtagsファイルの名前の指定。指定しないとtagsというファイル名になる
–exclude=.gitは.gitディレクトリ以下のファイルをインデックスの対象外にするオプション。
最後に一時ファイルを.git/tagsにリネームしている。.git以下にtagsファイルを置くことで.gitignoreで無視する手間を省いている。

gitディレクトリ以下だけでなく、他のディレクトリのファイルのインデックスを加えたいなら、このシェルスクリプトに-a(–apend=yes)のオプションをつけておき、さらに手動で

ctags --tags-relative -aR -f <gitディレクトリ>/.git/tags <他のディレクトリ>

みたいに実行する。

スクリプトを手動で実行するには

git config --global alias.ctags '!.git/hooks/ctags'

とaliasを設定しておくと、git ctags で実行できる。

で、このスクリプトを実行する hookを作る。

.git_template/hooks以下にpost-checkout, post-commit, post-mergeをいうファイルを作り、それぞれに

#!/bin/sh
.git/hooks/ctags >/dev/null 2>&1 &

と書いておく。post-rewriteはgit commit –amendとgit rebaseを行った時に発火されるが、前者はpost-commitでカバーされているので、rebase 使用時に限定する。

#!/bin/sh
case "$1" in
  rebase) exec .git/hooks/post-merge ;;
esac

あとは、ファイルに実行権限を付けて、git cloneするか、すでにリポジトリがあるなら、git initすれば、.git/hooks以下にファイルがコピーされる。

set tagsの設定

デフォルトだと

:set tags
  tags=./tags,tags

なので、カレントバッファのファイルがあるディレクトリにtagsファイルがあるかを探して、なければカレントディレクトリ(変更しなければvimを立ち上げたディレクトリ)のtagsファイルを探す。

例えば、

:set tags+=.git/tags

とすると、カレントディレクトリがgitのルートディレクトリでないとtagsファイルと見つけてくれない。

tpope作のGitを扱うvimプラグイン、fugitiveをいれると、かってにtagsのパスを設定してくれる(Why does fugitive modify my tags variable? · Issue #104 · tpope/vim-fugitive)。

:verbose set tags
  tags=~/git/tmsanrinsha/dotfiles/.git/vim.tags,~/git/tmsanrinsha/dotfiles/.git/tags,./tags,tags
        Last set from ~/.vim/bundle/vim-fugitive/plugin/fugitive.vim

これは自分のdotfilesリポジトリの.vimrcを開いた状態での設定例だが、.git以下の$lt;filetype$gt;.tagsとtagsを絶対パスで指定しているので、カレントディレクトリを気にする必要がない。(実はこのverbose set tagsでfugitiveが設定していることを知り、上のisuueからtpopeのブログに辿り着いた)

ファイルを保存した時もCtagsを実行する

tpopeのブログのコメント欄に書いてあるが、fugitiveをインストールしているなら、b:git_dirという変数が設定されるので

autocmd BufWritePost *
      \ if exists('b:git_dir') && executable(b:git_dir.'/hooks/ctags') |
      \   call system('"'.b:git_dir.'/hooks/ctags" &') |
      \ endif

と.vimrcに書いてやると良い。

補足

unite-tagを使うと、タグを絞り込めなかった時にuniteインターフェースで絞れて良い。

ctagsは開発がずっと止まっていたので、フォークされたb4n/ctagsのリポジトリの各ブランチを使うと、機能が追加されているのでよい。

PHPブランチの変更点や、インストールの仕方が、vimのPHPのomni補完をを向上させるプラグイン、phpcomplete.vimのWiki(Patched ctags · shawncplus/phpcomplete.vim Wiki )に書いてあるので参考にすると良い。

古いものを使う場合は、PHPのクラス定数などがインデックスされないので。.ctagsに以下のように正規表現で指定してやると、インデックスすることができる。

--append=yes
--tag-relative
--recurse=yes
--php-kinds=cidfv
--exclude=.svn
--exclude=.git
--langmap=PHP:+.inc.tpl
--regex-php=/^[ \t]*const[ \t]+([a-z0-9_]+)/\1/d/i
--regex-php=/abstract class ([^ ]*)/\1/c/
--regex-php=/interface ([^ ]*)/\1/c/
--regex-php=/(public |static |abstract |protected |private )+function ([^ (]*)/\2/f/


リモートサーバからクリップボードコピー&ブラウザを開く

$
0
0

ssh接続したリモートサーバの出力を手元Macのクリップボードに送る – Glide Note – グライドノートssh先screenのペーストバッファをクリップボードに貼り付ける – Keep It Simple, StupidでRemoteForwardを使って、リモートのテキストをローカルに送って、クリップボードにコピーする方法が紹介されているが、リモートのURLをブラウザで開きたいことがよくあるので、それもできるようにしてみた。

Macでの話だけど、pbcopyの部分や、サーバを立ち上げるために使っているLaunchAgentsの部分を変更すれば、windowsでもいけるはず。

仕組み

ローカルにPHPのビルトインサーバを使って、2224ポートでサーバを立ち上げる。(2224ポートは参照先に従った)
サーバにapacheを使うとpbcopyが権限などの理由?でうまく行かなかったので、PHPのビルトインサーバをLaunchAgentsで立ち上げることにした。
次にRemoteForwardを使って、リモートサーバにsshする。

$ ssh -R 2224:127.0.0.1:2224 remote.com

こうすると、リモートサーバの2224ポート(前の2224)への接続がローカルの2224ポート(後ろの2224)につながる。
リモート上で自分自身に向かって

$ curl -n -d "url=http://example.com" "http://localhost:2224/browser"

などのリクエストを送る。-nはBasic認証。
するとローカルサーバにリクエストが来るので、ローカル側でexample.comをブラウザで立ち上げる処理を書いておく。
pbcopyの場合も同じような感じ。

使い方

git cloneする。
Library/LaunchAgents/rfrouter.plistというファイルを~/Library/LaunchAgents/に絶対パスでシンボリックリンクを貼る。
~/src/github.com/tmsanrinsha/remote2localにgit cloneした場合はこんな感じ。

ln -s ~/src/github.com/tmsanrinsha/remote2local/router.php ~/Library/LaunchAgents

launchctl load ~/Library/LaunchAgents/rfrouter.plistでサーバを立ち上げる。次回からはログイン時に自動的に立ち上がるようになる。
止めたい場合はlanchctl unloadする。設定を変更した時はlanchctl unloadしてからlanchctl loadする。

gitのルートディレクトリに移動して、Basic認証用のファイルを作る

$ htpasswd -mc .htpasswd 
$ chmod 600 .htpasswd

-mは暗号化にMD5を使うオプション(version 2.2.18からはこれがデフォルト)。-cは新規にファイルを作るときのオプション。(htpasswd – Manage user files for basic authentication – Apache HTTP Server Version 2.4)
パスワード用のランダムな文字列がほしいなら

$ brew install pwgen
$ pwgen -y 8 1

などと打つと記号入り(-yオプション)のランダムな8文字が1つ手に入る。

素のpbcopyは日本語のコピーがうまくいかないことがあるので、router.phpからは、付属のbin/pbcopyを参照している。内部でnkfを使っているのでインストールする

$ brew install nkf

コードはUTF-8でpbcopyできるようにする – by edvakf in hatenaを元にした。

ローカルからローカルへのリクエストがうまくいくか試してみる。~/.netrcにhtpasswdで設定した値を書く。

machine localhost login  password 

パーミッションも600に変更しておく。
付属のbin以下のファイルにPATHが通った状態にして、

$ date | rfpbcopy

としてコピーできているか

$ rfbrowser 'http://t.co'

でブラウザが開くかを確かめる。

ローカルで確認ができたら、次はリモート。
毎回-Rで指定するのは面倒なので、~/.ssh/configに

Host remote.com
    RemoteForward 2224 127.0.0.1:2224

のような感じで設定する。sshで接続

$ ssh remote.com

して、.netrcに設定。ローカルでした確認を行ってみて、

$ date | rfpbcopy
$ rfbrowser 'http://t.co'

成功すればOK。

連携

vim-fakeclip

クリップボードがないときにpbcopyとかxclipとかなど駆使してクリップボードにコピーするVimプラグイン。
そのままだと、任意のコピー用のコマンドを設定できなかったので、フォークしてg:fakeclip_write_clipboard_commandをという設定を加えてみた。

こんな風に設定しておく

" clipboardが使えない、もしくはsshで接続している時にvim-fakeclipを使う。
if !has('clipboard') || $SSH_CLIENT != ''
    NeoBundle 'tmsanrinsha/vim-fakeclip'
endif
" +clipboardでもfakeclipのキーマッピングを使う
let g:fakeclip_provide_provide_key_mapping = 1
" クリップボードコピーのコマンドにrfpbcopyを使う
let g:fakeclip_write_clipboard_command = 'rfpbcopy'

open-browser.vim

url上で、gxと打つと、そのURLをブラウザで開いてくれたり、検索してくれたりするプラグイン。
以下のように設定しておく。

NeoBundleLazy 'tyru/open-browser.vim', {
    \   'autoload':{
    \       'mappings':[
    \            '(openbrowser-'
    \        ]
    \   }
    \ }
let g:netrw_nogx = 1 " disable netrw's gx mapping.
if $SSH_CLIENT != ''
    let g:openbrowser_browser_commands = [
        \   {
        \       "name": "rfbrowser",
        \       "args": "rfbrowser {uri}"
        \   }
        \ ]
endif

nmap gx (openbrowser-smart-search)
vmap gx (openbrowser-smart-search)

vim-fugitive

gitを扱うプラグイン。
:Gbrowseとうつと、開いているファイルをgit-web–browseを使って、Github上で開くとhelpに書いてあるけど、ソース見るとgit-web–browseは使ってないような気がする。実際.gitconfig

[web]
    browser = rfbrowser
[browser "rfbrowser"]
    cmd = rfbrowser

のように設定して

git web--browse http://github.com

とうつと、ブラウザを開いてくれるが、:Gbrowseでは開いてくれない。ソース見ると

if a:bang
  if has('clipboard')
    let @* = url
  endif
  return 'echomsg '.string(url)
elseif exists(':Browse') == 2
  return 'echomsg a'.string(url).'|Browse '.url
else
  return 'echomsg '.string(url).'|call netrw#NetrwBrowseX('.string(url).', 0)'
endif

となっていて、:Browseコマンドはないので、次のnetrw#NetrwBrowseXが実行される。
.vimrc

let g:netrw_browsex_viewer = 'rfbrowser'

と書けば解決した。

補足

LaunchDaemons

以下が参考になった。

Salted md5

上によると単にパスワードをハッシュ値に変換して保存すると、あらかじめ作られた平文とハッシュ値の表から複合化されてしまう。そこで、パスワードにランダムな文字列(salt)を加えてからハッシュ化して、ハッシュ値とsaltの値を保存しておくと復号化されにくくなるとのこと。レインボーテーブル – Wikipediaも参照。

で、今回パスワードをsalted md5で.htpasswdに保存しているから、送信されてきたパスワードを.htpasswdにあるsaltを加えてからmd5で変換して、比較しなくてならない。Password Formats – Apache HTTP Server Version 2.4によると、1000回md5でハッシュ化しているらしい。ソースコードは[Apache-SVN] Contents of /apr/apr/trunk/crypto/apr_md5.cにある。 このアルゴリズムをPHPで書いたコードがapache – how to edit .htpasswd using php? – Stack Overflowにあるので、そのcrypt_apr1_md5()という関数をrouter.phpで使って、パスワードの比較を行っている。

vimでfoldmethod=indentとするとインデントレベルが同じものが折りたたまれるが、インデントが深くなる直前のものを見出しとして折りたたむ

$
0
0

例えば、YAML フォーマット (1_4) – SymfonyにあるYAML

"symfony 1.0":
  end_of_maintenance: 2010-01-01
  is_stable:           true
  release_manager:     "Gregoire Hubert"
  description: >
    This stable version is the right choice for projects
    that need to be maintained for a long period of time.
  latest_beta:         ~
  latest_minor:        1.0.20
  supported_orms:      [Propel]
  archives:            { source: [zip, tgz], sandbox: [zip, tgz] }

"symfony 1.2":
  end_of_maintenance: 2008-11-01
  is_stable:           true
  release_manager:     'Fabian Lange'
  description: >
    This stable version is the right choice
    if you start a new project today.
  latest_beta:         null
  latest_minor:        1.2.5
  supported_orms:
    - Propel
    - Doctrine
  archives:
    source:
      - zip
      - tgz
    sandbox:
      - zip
      - tgz

を例にするとfoldmethod=indentに設定している場合、折りたたみのレベルが1の場合

"symfony 1.0":
+-- 10 行: end_of_maintenance: 2010-01-01---------------------------
_
"symfony 1.2":
+-- 18 行: end_of_maintenance: 2008-11-01---------------------------

のようになり、レベル2の場合

"symfony 1.0":
  end_of_maintenance: 2010-01-01
  is_stable:           true
  release_manager:     "Gregoire Hubert"
  description: >
+---  2 行: This stable version is the right choice for projects----
  latest_beta:         ~
  latest_minor:        1.0.20
  supported_orms:      [Propel]
  archives:            { source: [zip, tgz], sandbox: [zip, tgz] }
_
"symfony 1.2":
  end_of_maintenance: 2008-11-01
  is_stable:           true
  release_manager:     'Fabian Lange'
  description: >
+---  2 行: This stable version is the right choice-----------------
  latest_beta:         null
  latest_minor:        1.2.5
  supported_orms:
+---  2 行: - Propel------------------------------------------------
  archives:
+---  6 行: source:-------------------------------------------------

のようになるが、これを、レベル1の場合

+-- 11 行: "symfony 1.0":-------------------------------------------
_
+-- 19 行: "symfony 1.2":-------------------------------------------

とし、レベル2の場合

"symfony 1.0":
  end_of_maintenance: 2010-01-01
  is_stable:           true
  release_manager:     "Gregoire Hubert"
+---  3 行: description: >------------------------------------------
  latest_beta:         ~
  latest_minor:        1.0.20
  supported_orms:      [Propel]
  archives:            { source: [zip, tgz], sandbox: [zip, tgz] }

"symfony 1.2":
  end_of_maintenance: 2008-11-01
  is_stable:           true
  release_manager:     'Fabian Lange'
+---  3 行: description: >------------------------------------------
  latest_beta:         null
  latest_minor:        1.2.5
+---  3 行: supported_orms:-----------------------------------------
+---  7 行: archives:-----------------------------------------------

のようにしたい。

Advanced Folding / Learn Vimscript the Hard Wayにそのようなfoldingをさせるためのfoldexprの方が載っている。
ただし、s:NextNoBlankLine()の処理の部分は組み込みのnextnonblank()に変更した。

以下のようなファイルを作成し、

function! s:IndentLevel(lnum)
    return indent(a:lnum) / &shiftwidth
endfunction

function! s:NextNonBlankLine(lnum)
    let lnum = nextnonblank(a:lnum)
    if lnum == 0
        return -2
    else
        return lnum
endifendfunction

function! fold#indent(lnum)
    if getline(a:lnum) =~? '\v^\s*$'
        return '-1'
    endif

    let this_indent = s:IndentLevel(a:lnum)
    let next_indent = s:IndentLevel(s:NextNonBlankLine(a:lnum))

    if next_indent == this_indent
        return this_indent
    elseif next_indent < this_indent
        return this_indent
    elseif next_indent > this_indent
        return '>' . next_indent
    endif
endfunction

たとえばYAMLで適応したい場合はftpluginとして、

if exists('b:did_my_after_ftplugin_yaml')
  finish
endif
let b:did_my_after_ftplugin_yaml = 1

setlocal foldmethod=expr foldexpr=fold#indent(v:lnum) softtabstop=2 shiftwidth=2

を作成する。softtabstop=2 shiftwidth=2はお好みで。

ただ、インデントのレベルを出すために、s:IndentLevelの中でshiftwidthの値を使っているため、自分の設定ファイルでは2にしていても、開いたファイルがスペース4のインデントになっていた場合うまくいかない。そこで、開いたファイルを解析して、自動的にshiftwidthを設定するプラグインを使う。

これをインストールしてファイルを開いたら自動的にコマンドを実行するようにvimrcに

augroup MyVimrc
    autocmd!
augroup END

autocmd MyVimrc BufWinEnter *
\   let g:detectindent_preferred_indent = &shiftwidth
\|  if &expandtab == 0
\|      unlet g:detectindent_preferred_expandtab
\|  else
\|      let g:detectindent_preferred_expandtab = 1
\|  endif
\|  DetectIndent

と書いておく。ftpluginをロードした後に実行したいので、autocmdにBufWinEnterを使う。
解析できなかった時のshiftwidthの値として、現在のshiftwidthを使うように6行目で設定、expandtabについても7行目から11行目で設定している。
そして12行目でコマンド実行。

これでよし。

Viewing all 10 articles
Browse latest View live