88171.net


Unisonマニュアル私的日本語訳

クールなファイルシンクロナイザ、Unisonのマニュアルのクールでない私的な日本語訳です。 対象のバージョンはだいぶ古めです。

内容は一切保証しません。 誤訳や解釈間違いなどありましたら教えてください。

概要

UnisonはUnix及びWindowsに対応したファイルシンクロナイザです。 異なるホスト(もしくは同じホスト上の異なるディスク)に別々に保存され変更されたレプリカ(訳注: ここでは同期の対象となるファイルやディレクトリ、もしくはそれら全体を指します)の間で、それらの内容を同期させることができます。

Unisonは、CVSPRCS等のリビジョン管理システム、Coda等の分散ファイルシステム、rsync等のミラーリングツール、そしてIntellisyncReconcile等の他のシンクロナイザと多くの共通した特徴を備えていますが、同時に以下のような違いもあります。

序文

人々

ライセンス

Unisonはフリーソフトウェアです。GNU GPLの下に変更や再配布をして構いません。 詳しくはUnisonのソースに含まれるCOPYINGを参照してください。

バグレポート

Unisonが思ったように動かない場合、いくつかの踏むべき手順があります。

支援

Unisonは開発者にとって片手間のプロジェクトです。 私たちは、自分たち自身やコミュニティにとって役に立つ何かを作ることが楽しくて開発を続けています。 が、私たちには他にもやらねばならない仕事があります。 もしあなたがUnisonを気に入り、開発に手を貸したいと思ったならば、私たちはいつでも歓迎します。 コードの体系などより詳しいことは、ソースに含まれる CONTRIB というファイルを参照してください。

もしハックする気がなくても、単にあなたがどのようにUnisonを好きなのかを教えてくれるだけでも私たちへの支援になります。 例えば「Unisonを使っています。しっかり動作してくれます」とか「使ってみましたが、欲しかったものとは少し違います。なぜなら‥‥」といったような短い文章でも、私たちにとっては有用な情報です。

インストール

Unisonのインストールは非常に簡単です。以下の手順に従うだけで、ものの数分でUnisonが利用可能になるでしょう。

Unisonは

の2つのユーザインタフェース(UI)を備えています。

ファイルを同期させたい全てのマシンにUnisonをインストールする必要があります。 ただ、GUIを使いたい場合には実際にUIを表示するマシン(つまりクライアントとして使うマシン)にのみGUIバージョンのUnisonをインストールするだけで構いません。 その場合も、サーバマシンにインストールされているのがCUIバージョンであるかGUIバージョンであるかに関係無く、きちんと動作します。

ダウンロード

もしマシンのアーキテクチャに合ったビルド済みのバイナリが手に入るなら、それをダウンロードして(コマンドラインから使うのであれば)パスの通ったディレクトリに放り込むか、(直接クリックして使いたいなら)デスクトップに置くだけでOKです。

GUIバージョンのバイナリ(これはファイル名に gtkui を含みます)は、実際には2種類のUIを提供します。 デフォルトではGUIで、コマンドラインで

unison -ui text

を指定するとCUIで動作します。 CUIバージョンのバイナリ(同様にファイル名に textui を含みます)はCUIのみを提供します。

アーキテクチャに合ったビルド済みバイナリが見つからないときは、自分でソースからビルドする必要があります。 数は少ないですが、有志による移植版も存在します。

本当に実行可能なファイルをインストール出来たか確認しましょう。 ファイルをクリックして実行してみるか、コマンドラインから

unison -version

と打ってみましょう。

Unisonはいろいろな場面で使うことが出来ます。

もしrshやssh越しで利用することを考えているなら、rshやsshを別途インストールする必要があります。

実行

Unisonのインストールが終わったら、マニュアルのチュートリアルを読むか、

unison -doc tutorial

と打ってみましょう。

アップグレード

アップグレードも簡単です。 古いバイナリを新しいバージョンのバイナリに置き換えるだけです。

アップグレードの前に一度古いバイナリで完全にファイルを同期させておいた方が良いでしょう。 Unisonは各レプリカの状態を記憶するためにアーカイブファイルを生成しますが、新しいバージョンではそのファイルのフォーマットが変わっていることがあります。 この場合、古いアーカイブファイルは単純に無視されます(が、古いアーカイブファイルは削除はされません。つまりUnisonを古いバージョンに戻せば、古いアーカイブファイルがそのまま利用可能なわけです)。 つまり、古いバージョンで同期させずに新しいバージョンを動作させた場合、全ての更新が衝突したと判断され、手作業で同期させねばならなくなるわけです。

移植版

何人かの人が特定のアーキテクチャ向けのビルド済みのバイナリや、インストールを容易にするスクリプトを提供してくれています。 私たちが管理しているわけではなく、その内容に保証はありませんし、必ずしも最新版に追随してはいませんが、きっと役に立つことでしょう。 現時点で手に入るものを挙げておきます。

ビルド

ビルド済みのバイナリが手に入らない場合は、ソースからコンパイルする必要があります。 ソースはバイナリと同じ場所から手に入ります。

基本的に、OCamlが移植され、Unixモジュールが完全に整った環境であればUnisonは動くはずです。 特に様々なバージョンのWindows(98、 NT、 2000)及びUnix(Solaris、 Linux、 FreeBSD、 MacOS X)、更に32bit及び64bit環境でテストされています。

UnisonはMacOS 8及び9では(恐らく今後も)動きません。

Unix

Objective Caml compiler(バージョン3.04以降)が必要です。 オフィシャルサイトから入手可能です。UnixシステムにOCamlをインストールするのは非常に簡単です(クイックスタート‥‥多くのシステムでは以下のコマンドでコンパイラをインストールできます。まず make world opt、次に su でrootになり、make install)。 ソースに含まれる手引きを参照してください。 バイトコードコンパイラに加えてネイティブコードコンパイラもビルドしたいと思うかも知れませんが、これは絶対必要な条件ではありません。

また、GNU makeが必要です。 make --version でGNUバージョンのmakeがインストールされていることを確認しましょう。

OCamlのインストールが終わったら、Unisonのソースを入手して展開しましょう。 展開してできたディレクトリに移動し

make UISTYLE=text

と打てばunisonという名前で実行可能ファイルが作成されるはずです。

./unison と打って実行できるか確認しましょう。 上手くいっていればusageが表示されるはずです。

GUIバージョンをコンパイルしたい場合は、以下の2つも用意しておく必要があります。

もしこの方法がうまくいかない場合でも心配は無用です。 UnisonはCUIでも十分に動作しますから。

Unisonの実行可能ファイルをパスが通ったディレクトリに入れるか、ファイルのあるディレクトリにパスを通すかしましょう。

Windows

どのバージョンのWindowsでも配布されているバイナリファイルは動作しますが、ソースからビルドしたいという人もいるでしょう。

バイトコードバージョン

Unisonをビルドするのに、シンプルですが遅い方法はバイトコードバージョンをビルドする方法です。 WindowsバージョンのOCamlコンパイラの3.04以上をインストールしましょう。 次にUnisonのソースを入手して

make UISTYLE=text NATIVE=false

とタイプすることで、バイトコードをコンパイルできます。 unison.exe というファイルができているはずです。

ネイティブコードバージョン

より効率的なネイティブバージョンのUnisonをコンパイルするには、2つの方法があります。 両方ともOCammlの3.04以降とCygwinが必要です。 これらの方法の違いはCコンパイラです。 MS Visual C++ を用いるかCygwinのGNU Cを用いるかです。

違いは何でしょうか。

INSTALL.win32-msvcINSTALL.win32-cygwin-gnuc というファイルに、それぞれの方法でビルドする手順が書かれています。

インストールオプション

ソースアーカイブの中の Makefile にUnisonがどのようにビルドされるかをコントロールできるスイッチが含まれています。 有用ないくつかを紹介します。

チュートリアル

下準備

UnisonはCUIとGUIの2種類のUIを提供します。 CUIは端末や、スクリプトから呼び出して使うのに適します。 GUIはよりインタラクティブな操作を可能にします。 このチュートリアルを読み進む上で、どちらのバージョンを使っても構いません。

コマンドラインオプションはそれぞれのバージョンで異なります。 GUIバージョンのUnisonは直接クリックするだけで使えますが、それにはちょっとした設定が必要です。 このチュートリアルでは、CUIバージョンを使うという前提で話を進めます。

Unisonは一つのマシン上の異なるディレクトリのファイルの同期を取ることも出来ますし、ネットワーク上の異なるマシンの間で同期を取ることも出来ます(この場合、両方のマシンでそれぞれ同じプログラムが走ります。それらの違いは、どちらがUIを表示するかだけです)。 一つのマシン上で同期を取る場合には、そのマシンをクライアントと呼びます。 2台のマシンの間で同期を取る場合には、それぞれクライアントサーバと呼ぶことにします。

ローカルで使う

まずクライアントで、2つのディレクトリのファイルの同期を取る設定をしましょう。

インストールは済んでいますか?済んでいないならインストールのセクションを参照してください。

テスト用に a.tmp というディレクトリを作りましょう。中には適当なファイルやディレクトリを作っておきます。例えば

mkdir a.tmp
touch a.tmp/a a.tmp/b
mkdir a.tmp/d
touch a.tmp/d/f

こんな感じです。次に a.tmpb.tmp にコピーしましょう。

cp -r a.tmp b.tmp

では、a.tmpb.tmp の同期を取ってみましょう。 ただし、今回はそれぞれ同じなので、Unisonは特に変更を行ないません。 しかしUnisonは現在の状態を記憶し、次回どのファイルやディレクトリが更新されたかを検知します。

unison a.tmp b.tmp

と打ってみましょう。

CUIモードの場合:

GUIモードの場合:

次に、a.tmpb.tmp にそれぞれ違う変更を加えましょう。例えば

rm a.tmp/a
echo "Hello" > a.tmp/b
echo "Hello" > b.tmp/b
date > b.tmp/c
echo "Hi there" > a.tmp/d/h
echo "Hello there" > b.tmp/d/h

もう一度Unisonを実行しましょう。

unison a.tmp b.tmp

今度は更新されたファイルが表示されるはずです。 どちらか一方のレプリカのみで変更されたファイルには、そのファイルがどちらに更新されるかを示す(新しい方から古い方への)矢印が表示されます。 例えば

                 <---  new file   c  [f]

この場合2番目のレプリカでのみ c という新しいファイルが作られ、デフォルトでは1番目のレプリカにファイルがコピーされることを示しています。 Unisonのデフォルトに従う(follow)には、プロンプトで f と打ちます。

もし両方のレプリカが更新され、その内容が異なる場合、その更新は衝突したと表現します。 更新が衝突した場合、Unisonは以下のようなプロンプトを表示して、どちらのレプリカで更新すべきか問い合わせます。

     new file  <-?->  new file   d/h  []

デフォルトでは、双方のレプリカは更新されず、そのまま保存されます。

(この例における b というファイルのように)双方のレプリカが更新されているが内容が同じである場合、更新は必要ないためUnisonは何も表示しません。 単にUnison内部で、双方のファイルが最新であると記憶されるだけです。

この更新状況の表示方法はCUIとGUIどちらのバージョンでも同様に用いられます。 唯一の違いは、ユーザがUnisonのデフォルトの動作に従うか否かを決定する操作方法のみです。

CUIの場合:

GUIの場合:

リモートで使う

次に、Unisonでネットワーク越しにレプリカの同期を同期させる方法を見てみましょう。

インストールのセクションを参考に、サーバにもUnisonをインストールしましょう(サーバにはCUIとGUIのどちらのバージョンをインストールしても構いません。サーバ側のUnisonはUIを表示する必要が無いからです)。 実行可能ファイルにパスが通っていることを確認してください。

サーバにインストールされたUnisonとクライアントのUnisonのバージョンが揃っていることが重要です。 しかしクライアントと同じバージョンのUnisonを

unison -addversionno

で呼び出すことも可能です。

Unisonをネットワーク越しに使うには2通りの方法がありますので、どちらの方法を使うか決めましょう。

リモートシェル越しに使う

Unixで使われる標準的なリモートシェルはrshです。 sshはrshと似ていますが、通信路を暗号化するという点で、より安全です。 rshやsshでサーバとクライアントの間のコネクションを確保するには設定が必要です。 rshやsshのドキュメントを参照してください。 ここでは例としてsshを使用しますが、必要があれば適宜sshをrshに読み替えてください。

まず、サーバ側のコマンドをクライアントから実行出来るか確認しましょう。

ssh remotehost unison -version

と打って表示された内容が、クライアントで

unison -version

と打った場合の内容と同じであることを確認してください。 もし実行出来ないのであれば、(permission denied等と表示される場合は)sshの設定を見直すか、(command not found等と表示される場合には)サーバでUnisonの実行可能ファイルにパスが通っているか確認してください。

クライアントのホームディレクトリにテスト用の a.tmp というディレクトリを作りましょう。

クライアントのUnisonがサーバに接続出来るか試してみましょう。

unison -testserver a.tmp ssh://remotehost/a.tmp

ではホームディレクトリに移動して

unison a.tmp ssh://remotehost/a.tmp

と打ってみましょう。クライアントの a.tmp がサーバに転送されるはずです。

最初の同期が終わったら、a.tmp の中にファイルを作ったりファイルを更新したりして、もう一度実行してみましょう。 ローカルで実行した場合と同じような表示が出るはずです。

クライアント上とサーバ上でユーザ名が異なる場合には、コマンドラインで指定する必要があります。

 unison a.tmp ssh://user@remotehost/a.tmp

注意:

ソケット越しに使う

Unisonをソケット越しに使うには、サーバで Unisonサーバプロセスを走らせておく必要があります。 このプロセスはバックグラウンドでクライアントのUnisonからの接続を待ち受けています。

Unisonをソケット越しで使う方法は安全ではありません。やり取りするファイルの内容が平文のままネットワーク上を流れるだけでなく、世界中からそのサーバプロセスに接続して、あなたのファイルシステムの内容を読み取ってしまうことも可能なのですから!(もちろんこれにはUnisonのクライアントとサーバの間でやり取りされるプロトコルを理解していなければなりませんが、それに必要なのはUnisonのソースだけです。)

デーモンを開始させるにはサーバ上で

unison -socket NNNN

と打ちます。NNNN にはポート番号を指定します。(他のアプリケーションに使われていない番号を指定します。指定したポートが既に使われていた場合には、Unisonはエラーを表示して終了します。) クライアントで指定された path はデーモンが開始されたディレクトリからの相対パスに変換されることに注意してください。 これはリモートシェルを用いた場合と異なります。 リモートシェルの場合、path はサーバ上のユーザのホームディレクトリからの相対パスとなります。

クライアントのホームディレクトリにテスト用の a.tmp というディレクトリを作り

unison a.tmp socket://remotehost:NNNN/a.tmp

と打って実行してみましょう。 a.tmp がサーバにコピーされるはずです(この場合、a.tmp はサーバ上の、デーモンを起動したディレクトリの中に作られます)。 最初の同期が終わったら、ファイルに変更を加えて再度実行してみましょう。 ローカルで実行した場合と同様の結果が得られるはずです。

ホームディレクトリのファイルをUnisonで同期させる

Unisonの基本的な操作に慣れたら、Unisonで普段使っているファイルを日常的に同期させたいと思うかもしれません。 これにはいくつかの方法があります。

1.(ignore で)無視するファイルを設定して一時ファイルや一方のホストのみに属するファイルを除外しながら、ホームディレクトリ全ての同期を取る。 2. 双方のマシンのホームディレクトリに shared(もしくは current でも何でも)というディレクトリを作り、同期を取りたいファイルは全てそのディレクトリに入れる。 3. 双方のマシンのホームディレクトリに(例えば)shared というディレクトリを作り、同期を取りたいファイルへのリンクをそのディレクトリに入れる。 シンボリックリンクがUnisonに透過的に扱われるように、follow 設定をする。 4. ホームディレクトリを同期を行なう基点として指定するが、Unisonにはその中の一部のサブディレクトリやファイルの同期を取るよう指定する。 これはコマンドラインで -path オプションによって指定することも出来ます。

ホームディレクトリ全体等、大きなレプリカに対して初めてUnisonを実行する際には、Unisonは全てのファイルをチェックして内部のデータ構造を記録するのに多くの時間を費します。 試しに実行してみるのであれば、コマンドラインで -path some/small/subdirectory というように小さなサブディレクトリのみを指定して、実行時間を節約するのも手です。 満足する結果が得られたら path オプションを外して実行し、Unisonがディレクトリを一生懸命漁っている間に、あなたはランチでも食べてきてください。

もしレプリカが大きく、しかもWindows上のレプリカが含まれている場合には、Unisonの実行速度が遅過ぎると感じるかもしれません(何故ならUnisonはWindows上では、実行する度に全てのファイルとディレクトリをスキャンするからです。というのもこれがWindows上で更新をチェックするのに最も安全な方法だからです)。 このような場合、fastcheck の設定を行なうのも一つの手です。

例えばラップトップとファイルサーバの間でファイルを同期させる場合のように、いつも決まったマシンからUnisonの操作をする場合、クライアント側だけの設定をするだけで済むことに気付くでしょう。 これは一方向性のミラーリングツール(例えばrdist等)を用いた場合に、常に最近レプリカに変更が加えられたマシンから操作をする必要があることと比べると、特徴的です。

もっと知る

様々な特徴について書かれたUnisonのオンラインマニュアルを手に入れるには、コマンドラインから

unison -doc topics

と打ち込むか、GUI画面のHelpメニューをクリックします。 オンラインマニュアルはこのマニュアルと基本的な内容は一緒です。

Unisonには2種類のメーリングリストがあります。詳しくはhttp://www.cis.upenn.edu/~bcpierce/unison/download.htmlを見てください。

リファレンス

ここではUnisonの詳細な特徴について触れます。

Unisonを実行する

Unisonを実行するにはいくつかの方法があります。

.unisonディレクトリ

Unisonはそれぞれのホストのディレクトリに、様々な情報を保存します。 環境変数 UNISON が設定されている場合、その値がそのディレクトリ名として使用されます。 設定されていない場合、使用しているOSによってディレクトリ名は異なります。 Unixでは $HOME/.unison、Windowsでは、環境変数 USERPROFILE が設定されていれば %USERPROFILE%\.unisonHOME が設定されていれば %HOME%\.unison、どちらも設定されていなければ C:\.unison が使われます。

アーカイブファイルはそのレプリカのあるホストの .unison ディレクトリに作られます。 プロファイル(後述)は常にクライアントの .unison ディレクトリから探し出されます。

Unisonはそれぞれのrootについて全く異なるアーカイブファイルを保持することに注意してください。

.unison ディレクトリを丸ごと同期させることはお薦めできません。巨大なアーカイブファイルを更新に含めることになるからです。 しかし、あなたがそれを望むならそうしても安全です(.unison ディレクトリ内のプロファイルを同期させること自体は何ら問題ありません)。

アーカイブファイル

各レプリカに対するアーカイブファイルは以下の情報から計算されます。

この方法はほとんどのユーザに対して有効に機能します。 しかし、アーカイブファイルの名前を生成する方法を変更することが役に立つ場合もあります。 Unisonは2つの方法を用意しています。

ローカルホストの正確なホスト名(これは例えばどのファイルが同期されたかという情報を保存するアーカイブファイルの名前を生成するのに使われます)を調べるために、Unisonは通常 gethostname() というシステムコールを使います。 しかし UNISONLOCALHOSTNAME という環境変数が設定されている場合、代わりにその変数の値が使用されます。 これにより、ホスト名が頻繁に変わる場合(例えばラップトップをあちこち持ち歩くような場合)でもより簡単にUnisonを利用することができます。

よりパワフルな方法として、rootalias 設定を用いることができます。その設定ファイルには以下の書式の複数の行を含みます。

rootalias = //hostnameA//path-to-replicaA -> //hostnameB//path-to-replicaB

ある一組のrootに対してアーカイブファイル名を計算する際、Unisonは rootalias 設定の左側の root 設定を右側の root 設定に置き換えます。

あるホスト上の root を置き換えたい場合、以下のように追加します。

rootalias = //new-hostname//new-path -> //old-hostname//old-path

注意: rootalias 設定は危険ですので、自己責任で使ってください。 特に、1)元の root と新しいエイリアスが同じファイル群を指していること、2)元のファイル名がもう使えなくなったためにファイル名を変え、これからもそのファイル名を絶対に使わないこと、のいずれかを満たす場合のみ使用してください(元の root とエイリアスが違うファイル群を指している場合、Unisonは混乱してしまいますから)。 新しい rootalias 設定を加えたら、Unisonを何度か(batch フラグを外す等して)実行してみることをお薦めします。 そして、特に変更の検知がうまく働いているかをチェックしてください。

オプション

Unisonの細かい動作はオプションで設定可能です。

いくつかのオプションはboolean値(しばしばフラグと呼ばれます)をとります。 その他のオプションは数値か文字列を値にとります。 リスト中では数値は n、文字列は xxx と表現します。 文字列をとるオプションのほとんどは複数回設定できます。 設定値はその度に累積されます。

オプションを設定するには2通りの方法があります。 一時的にはコマンドラインオプションとして実行時に指定します。 恒久的には、クライアントの .unison ディレクトリのプロファイルに追記します。 オプション・プロファイルに関わらず、オプションの順番は重要ではありません。

p というオプションをコマンドラインから設定するには、(boolean値の場合)-p、もしくは(数値か文字列の場合)-p n もしくは -p xxx と追加してください。 コマンドラインからboolean値を false にする方法は今のところありません。 しかし、全てのboolean値をとるオプションはデフォルトで false ですので、あなたがプロファイルであるオプションを true にセットしていて、それを一時的に false にしたいという時にだけ、この制限がかかります。

unison -help でオプションの一覧が取得できます。

では、それぞれのオプションについて詳しく見ていきましょう。多くはマニュアルの別のセクションにより深く解説されています。

プロファイル

プロファイルとは rootpathignore 等の設定を記述したテキストファイルです。 これを用意することで、実行する際にいちいちコマンドラインでオプションを打つ必要がなくなります。 プロファイルはクライアントマシンの .unison ディレクトリに置いておく必要があります。 Unisonが name という一つの引数だけで実行された場合、.unison ディレクトリの name.prf というファイルをプロファイルを読み込みます。 引数無しで実行された場合、(GUIでは).unison ディレクトリの .prf というファイルを全て探し出し、選択可能なメニューを表示します。 default.prf というファイルがある場合には、その設定がデフォルトで選択されます。

p というオプションを設定する場合、boolean値を取るオプションはプロファイルに

p = true

のように記述します。 他のタイプの値を取るオプションは

p = <value>

というように記述します。

pxxx の周りの空白は無視されます。 空行を含んでいても構いません。 また # で始まる行も空行と共に無視されます。

Unisonを実行すると、まずプロファイルを読んでからコマンドラインオプションを読みますので、プロファイルでの設定をコマンドラインオプションで上書きすることができます。

プロファイルには include name という行を含めることができます。 これにより name というファイル(もしくは .unison ディレクトリに name というファイルがなければ name.prf というファイル)の内容がinclude行の位置に記述されていると見なされます。 include行により、複数のプロファイルに共通の設定を一つのファイルにまとめておくことができます。

プロファイルには label = desc という行を含めることができます。 desc にはそのプロファイルの説明を書いておきます。 GUIで実行する際、プロファイル選択ダイアログでプロファイルと共に desc の内容が表示され、実行中のメインウィンドウの右上にも同様に desc の内容が表示されます。

GUIではまた、よく使うプロファイルにショートカットを登録しておくこともできます。 プロファイルに key = nn は一桁の整数)という行が含まれる場合、その数字のキーを叩くことで即座にプロファイルを切り替え、同期を開始することができます。 この場合、現在表示され選択されている内容は破棄されます。

プロファイルのサンプル

最小限のプロファイル

最小限のプロファイルのサンプルです。

root = /home/bcpierce
root = ssh://saul//home/bcpierce

path = current
path = common
path = .netscape/bookmarks.html
基本的なプロファイル

有用なオプションを含んだ、もう少し洗練されたサンプルです。

root = /home/bcpierce
root = ssh://saul//home/bcpierce

path = current
path = common
path = .netscape/bookmarks.html

ignore = Name temp.*
ignore = Name *~
ignore = Name .*~
ignore = Path */pilot/backup/Archive_*
ignore = Name *.o
ignore = Name *.tmp

height = 37

backup = Name *

diff = diff -y -W 79 --suppress-common-lines

log = true
パワーユーザ向けプロファイル

Unisonが巨大なレプリカに対して実行される時、しばしばレプリカの一部分のみを同期の対象として指定する方が(他の箇所の変更を調べる時間を節約できる分)便利です。 これはプロファイルをいくつかのパートに分けることで実現できます。 具体的には、基本的な設定を含んだパートと、同期させたいそれぞれのpathについてのトップレベルのパートです(include機能も同様に異なるrootに対して共通の設定を提供する目的で利用できます)。

この構想を実現するプロファイルは以下のようになります。 default.prf というファイルにはinclude行のみを含めます。

include common

共通のファイルの名前は common.prf ではなく common にしてください。 これにより、UnisonがGUIでプロファイルの選択肢に common を含むことを防ぎます。

common には実際の設定を書きます。

addprefsto = common

ignore = Name temp.*
ignore = Name *~
ignore = Name .*~
ignore = Path */pilot/backup/Archive_*
ignore = Name *.o
ignore = Name *.tmp

common にはpathの設定を書きません。 つまり、デフォルトのプロファイルでUnisonを実行した場合(つまり unison default もしくは単に unison のみで実行した場合)、レプリカ全体が同期されるということです(レプリカ全体を絶対に同期させたくない場合には、default.prf に同期させるpathを設定すべきです)。

レプリカの一部のpathのみを同期させるために、(例えば unison papers のように)別のプロファイルを指定して実行します。 papers.prf には以下のように記述します。

path = current/papers
path = older/papers
include common

これにより、Unisonは current/papersolder/papers のみを同期するようになります。

GUIで異なるpathの設定に素早く切り替えるために、key オプションが指定できます。 例えば、mail.prf には以下のように記述します。

path = Mail
batch = true
key = 2
include common

これにより、2を叩くだけで Mail というサブディレクトリのみを見るようになり、(batch フラグが立っているために)すぐに更新が実行されます。

バックアップをとる

更新を行なう際に、古いバージョンのファイルのバックアップを取ることができます。 この機能により、一般的なバックアップを行なうと同時に、外部のマージするためのプログラムを実行する際に一般的なバージョンを提供することもできます。

バックアップされたファイルは双方のホストの ~/.unison/backup ディレクトリに保存されます。 このディレクトリは UNISONBACKUPDIR という環境変数に値を設定することで変更することもできます。 Unisonがアーカイブを更新する際にファイルはバックアップディレクトリへと保存されます。 つまり

バックアップファイルを手動で削除(もしくはバックアップディレクトリごと削除)しても安全です。 Unisonはこれらのファイルを重要なことに使う前に、期待するファイルとフィンガープリントが一致することを確認します。

backup オプションはどのファイルが実際にバックアップされるかを設定します。 例えば、backup = Path * という指定をすると、全てのファイルがバックアップされます。 backupversions オプションは、いくつのバージョンまでがバックアップされるかを設定します。 デフォルトでは 2 です(つまり最後に同期されたバージョンともう一つ古いバージョンがバックアップされます)。 後方互換性のため backups オプションはいまだサポートされていますが、現在では backup を使うようにしてください。

更新をマージする

CUI・GUIの両方のUIは、インタラクティブに衝突をマージする merge コマンドを提供します。 これは衝突しているファイルを選択してmを叩くことで実行できます。

実際のマージ作業は、外部プログラムにより行なわれます。 merge オプションと merge2 オプションが、どのように外部プログラムが起動されるかを指定しています。 このファイルのバックアップファイルが存在する場合、merge オプションが使用されます。 そうでなければ merge2 オプションが使用されます。 いずれの場合も、オプションには外部プログラムを実行するためにシェルに渡されるコマンド名を指定します。 この文字列には CURRENT1CURRENT2NEW、そして OLD という特別な文字列を含めます。 Unisonはこれらの文字列を、コマンドの実行前に以下のように置き換えます。

例えば、Unixシステムで merge オプションを

merge = diff3 -m CURRENT1 OLD CURRENT2 > NEW

のように指定すると、Unisonはマージに diff3 というコマンドを使います。 外部のマージプログラムを複数指定することもできます。 例えば、Emacsユーザは以下のような設定が気に入るでしょう。

merge2 = emacs -q --eval '(ediff-merge-files "CURRENT1" "CURRENT2" nil "NEW")'
merge = emacs -q --eval '(ediff-merge-files-with-ancestor "CURRENT1" "CURRENT2" "OLD" nil "NEW")'

外部プログラムが NEW に対応するファイルを保存せずに終了した場合、Unisonはマージが失敗したと判断します。 マージプログラムが NEW というファイルを保存したが、終了コードが 0 以外の値を返した場合、マージは成功したが、同時に衝突も発生したと判断します。 この場合、外部のエディタを起動してユーザが衝突を解決できるようにします。 editor オプションはUnisonによって起動されるエディタを指定します。 デフォルトではEmacsです。

merge2merge の便利な設定を是非教えてください。マニュアルにもう少し例を載せたいのです。

ユーザインタフェース

CUIもGUIも、それ自身が一目瞭然に作られています。 少しだけトリックを紹介しておきます。

終了コード

テキストモードで実行する際、Unisonは終了コードを返します。 終了コードは同期が成功したかしなかったか、もしくはどこまで成功したのかを示します。 スクリプトからUnisonを利用する際に便利です。 Unisonが返し得る終了コードは4種類あります。

GUIでは有用な終了コードを返しません。

pathの仕様

いくつかのUnisonのオプション(ignore/ignorenotfollowsortfirst/sortlastbackup)にはある一つpathやpathのセットを指定する必要があります。 これらのオプションは正規表現をベースとしたシンタックスを共有しています。 それぞれのオプションのpathパターンのリストと関係しています。 特定のpathはpathパターンの一つにマッチします。

pathを無視する

Unisonのユーザは、一時ファイルや巨大なファイル、古いファイル、アーキテクチャに依存したバイナリファイル等、同期させたくないファイルがレプリカに多く含まれていることに気付くでしょう。 これらのファイルを同期させないよう、ignore オプションで無視すべきpathを指定することが出来ます。

例えば、以下のように指定することで CVS.cmo というファイルを同期させないよう設定することができます。

ignore = Name {CVS,*.cmo}

次のパターンは a/b というpathを無視させることができます。

ignore = Path a/b

このパターンは a/b で始まり .ml で終わるpathを無視させることができます。

ignore = Regex a/b/.*\.ml

正規表現によるpathの指定は固定されることに注意してください。 つまりpathの一部だけではなく、pathの全体がマッチする必要があります。

ignore オプションには他にもいくつかのポイントがあります。

シンボリックリンク

通常UnisonはUnixのレプリカの中のシンボリックリンクを非透過的に扱います。 つまりシンボリックリンクを、そのリンクが指し示す先を表わす文字列として扱い、その文字列を他のレプリカに更新します。

シンボリックリンクを、リンクがある場所に実際にファイルがあるかのように、つまり透過的に扱うことはしばしば有用です。 Unisonにシンボリックリンクをこのように扱うように指示するには、プロファイルに

follow = pathspec

というように追記します。 pathspec はpathパターンを表わします。

Windowsのファイルシステムはシンボリックリンクをサポートしていません。 UnisonはUnix上のシンボリックリンクをWindows上に非透過的に転送することができません。 そのpathはエラーがあるとしてフラグが立てられます。 Unix上のレプリカがWindows上のレプリカと同期される場合、全てのシンボリックリンクは ignore パターンか follow パターンのいずれかにマッチする必要があります。

パーミッション

二つの異なるファイルシステムの間(例えばWindowsのクライアントとUnixのサーバの間)でパーミッションのビットを同期させるのは些かトリッキーです。 以下に、その仕組みがどのようにして動作しているかを示します。

クロスプラットホームでの同期

WindowsとUnixの間でUnisonでファイルを同期させる場合、知っているべき問題がいくつかあります。

大文字・小文字の問題: Unixではファイル名の大文字と小文字は区別されます。 fooFOO は異なるファイルを指します。 一方Windowsでは大文字と小文字の違いは無視されます。 fooFOO は同じファイルを指します。 つまりこれはUnix上の fooFOO というファイルは、Windowsに転送できないということを意味します。 Windowsは同じ名前で異なるファイルの存在を許さないからです。 Unisonはこの問題を探知し、ファイルを同期できない旨を報告します。

ファイル名の大文字・小文字の問題を解決する方法はあります。 Windowsに両方のファイルを転送する必要がある場合、唯一の方法はUnix上で一つのファイル名を変更し、再度同期させることです。 Windowsにファイルを転送する必要がない場合は、単純にUnisonの警告を無視し、同期させる作業を続けてください。 Unisonはそれらのファイルには触れません。 同期させる度に警告を表示させるのが嫌ならば、ignore オプションを設定して無視させてください。

無効なファイル名: Unixでは有効なファイル名がWindowsでは無効なことがあります。 例えばコロン(:)はWindowsではファイル名として使えませんが、 Unixでは使うことができます。 これはUnix上の foo:bar というファイルがWindowsに転送できないことを意味します。 大文字・小文字の場合と同様、Unisonはその状況を探知し、報告します。 回避するのも同様に、Unixでファイル名を変えて再度同期させるか、単純に無視しましょう。

狭い帯域幅

Unisonは比較的遅いダイアルアップやDSLの回線でも十分に動作するように作られています。

UnisonはAndrew TridgellとPaul Mackerrasによってデザインされた、小さな変更を加えられた巨大なファイルの転送を最適化するrsyncプロトコルを利用しています。 rsyncプロトコルについてはrsyncのWebサイトを参照してください。

Unisonをssh越しに利用している場合、sshの圧縮機能を利用して転送速度を多少向上させることができます。 これにはコマンドラインで -rshargs -C と指定するか、プロファイルに rshargs = -C と追加します。

高速な変更検知

レプリカが巨大で且つどちらかが(もしくは両方が)Windowsシステムである場合、Unisonのデフォルトの変更検知プロセスが遅すぎると感じるかもしれません。 Unisonには fastcheck オプションがあります。 yes にセットすると、Unisonはファイルの変更をチェックする際、全てのファイルの内容をチェックする代わりにファイルの作成日時を似非inode番号として使うことで、変更をより速く検知することができます。

この方法を使うと、Windowsでは、作成日時・変更日時・ファイルサイズが更新で変更されなかった場合、更新に失敗する可能性があります。 しかしUnisonは常に更新を行なう前に安全に変更のチェックを行なっていますので、そのような変更を他のレプリカから上書きしてしまうことはありません。 ですので、Windowsではこのオプションを使うに値するでしょう。 但しそういった変更が見逃されている心配があるのであれば、時々 fattcheckfalse にして実行しましょう。

クリックで起動

Windows NTや2000のシステムでは、GUIバージョンのUnisonを直接クリックすることで起動することも可能です。 Windows 95や98では、sshを使わない限りはクリックして起動することもできます。 OCamlとWindows 95/98との相性問題は解決できていないので、sshを使いたい場合はDOSプロンプトから起動する必要があります。

Unisonのアイコンをクリックすると、2つのウィンドウが表示されます。 Unisonの通常のウィンドウと、sshのパスワードを入力するためだけのコンソールウィンドウです(sshを使わないのであれば無視して構いません)。 パスワードの入力が促されたら、入力する前にコンソールウィンドウに(クリックするなどして)フォーカスを当てる必要があります。 DOSプロンプトからUnisonを起動した場合は、パスワードはDOSプロンプトに入力してください。

このモードでUnisonを利用するには、前もってプロファイルを作っておく必要があります。 好きなエディタを使って作成してください。

仕様

Unisonはシンプルな仕様に基づいています。

root

レプリカの root とは、ローカルマシン及びリモートマシンにおいて、同期を取るべきファイル群の場所を表わします。 例えば

relative/path/of/root

はローカルマシンにおけるrootを、Unisonが実行されたディレクトリからの相対パスとして表わし、

/absolute/path/of/root

はどこでUnisonが実行されたかは関係無く、ローカルマシンのファイルシステムにおける絶対パスでrootを示しています。 リモートホストのrootは、接続に用いるプロトコルによって ssh://、もしくは rsh:// を先頭に付け加えます。

ssh://remotehost//absolute/path/of/root
rsh://user@remotehost/relative/path/of/root

リモートホストでUnisonサーバが動いているのであれば、

socket://remotehost:portnum//absolute/path/of/root
socket://remotehost:portnum/relative/path/of/root

このように書くことで、クライアントのUnisonが接続すべきリモートホストとポート番号を明示します。

rootの書式はURI(RFC 2396)の書式に基づきます。

pathにプロトコルを示すプレフィクスが付いていない場合、プロトコルは file: であると見なされます。 Windowsの場合、ファイル共有機能と file: プロトコルを用いてファイルの同期を取ることが出来ます。

unison foo //host/drive/bar

というように実行すると、ローカルの foo というディレクトリと、host というマシンの drive:\bar の同期を取ります(但しこの方法は、ホスト間が十分に速い回線で接続されている場合に限った方が良いでしょう。更新を検知するために、リモートマシンのレプリカがローカルマシンに転送される必要があるからです)。

rootの名前は実行時にUnisonによって内部的に変換されます。 各rootに対応するアーカイブファイル名を特定するためです。 つまり //saul//home/bcpierce/common//saul.cis.upenn.edu/common は名前の違う同一のレプリカであると認識されます。

path

pathとは同期を取るファイル群の中の一つを指します。 レプリカのrootからの相対パスで表わされます。

pathは単なる / で区切られた名前の羅列です。 Unisonが動作する環境に関係無く、pathの区切りは常に /(スラッシュ)であることに注意してください。 ローカルのファイルシステムにおいて必要がある場合は、/\(バックスラッシュ)に自動的に変換されます(例えばWindowsマシンの c:\pierce とUnixサーバの ssh://saul.cis.upenn.edu/home/bcpierce の同期を取る場合、current/todo.txt というpathはクライアントでは c:\pierce\current\todo.txt となり、サーバでは /home/bcpierce/current/todo.txt となります)。

pathが空の場合、レプリカ全体を表わします。 Unisonは空のpathを [root] と表示します。

変更

あるレプリカのpath、p の指し示す内容は、ファイルかディレクトリ、シンボリックリンク、もしくは(p がレプリカの中の何も指し示していない時は)空っぽであるかもしれません。 より詳しく見てみましょう。

Unisonは同期が成功した後、それぞれのpathの内容を記憶します(つまり2つのレプリカの内容が同じであったときの最後の状態を記憶しているわけです)。

あるレプリカにおいて、pathの中身が最後に同期させた時から見て変更されている場合、そのpathは変更されたと判断します。

衝突

以下のような場合、そのpathは衝突しているとされます。

  1. どちらかのレプリカで変更された。
  2. そのpathかその子がもう一方のレプリカで変更された。そして
  3. 2つのレプリカの同一のpathの内容が異なる。

衝突の解決

Unisonはいくつかの異なった段階を踏みます。

  1. それぞれのホストにおいて、どのpathが変更されたか判断するために、現在のレプリカの内容とアーカイブファイルの内容を比較します。
  2. 両方のレプリカで変更されていて、なおかつ内容が異なるpath(false conflicts)を調べます。 これらのpathは両方のレプリカにおいて、同期されたと内部的にマークされます。
  3. 更新されたpathをユーザに提示します。 衝突しない更新に関しては、更新されたレプリカ同様にもう一方を更新するという、デフォルトの動作を提案します。 衝突する更新は単に表示されます。 ユーザはレプリカ全体の更新状況を見極め、衝突しない更新の動作を変え、衝突する更新に対する動作を決めることができます。
  4. 選択された動作を一つずつ実行します。 転送されたファイルはまず受け取り側のホストに一時ファイルとして作成され、次にそのファイルをあるべき場所に移動します。
  5. アーカイブファイルに現在のレプリカの内容を反映します。

原則

その実行内容の重要性と繊細さから、シンクロナイザが通常の状態でどのような動作をしているのかだけでなく、システムのクラッシュや通信が切断した場合等の異常事態にどのように動作するのかを知ることもまた重要です。

Unisonは実行中、常に内部の状態やレプリカの状態を保護するよう設計されています。 特に、以下のような特徴を備えています。

つまり結論として、人為的にであろうと事故であろうと、いつUnisonの実行を停止しても安全だということが言えます。

更新を実行している最中に停止された場合、あるpathの更新は完了しているのにアーカイブファイルにその更新が反映されていないということが起こり得ます。 しかし問題はありません。 次にUnisonが実行された際に、Unisonはこれらのpathが変更されていながらも内容は同じであると判断し、同期は成功したと記憶してそのpathに関する処理を終了するからです。

Unisonが停止された場合、レプリカの中に(.tmp という拡張子の付いた)一時ファイルが残っていることがあります。 それらのファイルは消してしまって構いません。 同様に(deprecatedな)backupフラグが設定されている場合、Unisonは file.0.unison.bak というような古いバージョンのファイルを残します。 これらのファイルも、Unisonの動作には影響ありませんから、消してしまって結構です。

Unisonは、動作しているマシンの間のクロック・スキュー(クロックのばらつき)には影響されません。 Unisonは単に一つのホスト上で手に入れたタイムスタンプの比較を行ない、それを行なう上で必要な前提は、それぞれのシステムのクロックが常に前に進むということだけだからです。

アーカイブファイルが削除されている(もしくはファイルのフォーマットが変更されていて読み込めない、もしくはあるrootに対して初めて実行したためまだファイルが作られていない)場合、Unisonは非常に保守的な動作をします。 つまり双方のレプリカが最後の更新時に完全に空であったかのように動作します。 その結果、初めての実行時には一方のレプリカに存在するファイルは他方に転送され、両方のレプリカに存在しながら内容が異なるファイルは衝突しているとマークされます。

あるファイルに対して変更を加えずに更新時刻だけを変更する(touchする)操作は、Unisonの動作に影響を与えません。 Unixでは、Unisonはどのファイルが絶対に更新されていないかを知るために、まずファイルの更新時刻を調べます。 そして更新された可能性のあるファイルに対してフィンガープリントを計算し、最後の更新時の状態と比較します。

アーカイブファイルを両方のレプリカから削除して、Unisonを洗脳しても構いません。 次に実行した時、Unisonはレプリカの全てのファイルが新しく作られたものだと仮定します。

Unisonの実行の最中にファイルに変更を加えても安全です。 古い状態で更新してしまった時、もしくは更新している最中にターゲットのレプリカのファイルが変更された時は、Unisonはそのファイルの更新に失敗した旨を表示します。 最新の更新を行なうにはもう一度Unisonを実行してください。

UIからの(例えば i キー等による)無視(ignore)パターンの変更は、すぐに現在のプロファイルに反映されます。

警告と短所

Unisonを利用する際に注意すべきことがあります。 バグの完全なリストは、ソースアーカイブの中の BUGS.txt にあります。

アドバイス

FAQ

Unisonとrsyncの違いは何ですか?

端的に言ってしまえば、rsyncはミラーリングツールで、Unisonはシンクロナイザです。 つまりrsyncには「このレプリカが最新バージョンですから、もう一方をこれで上書きしてください」と指示する必要があるのですが、Unisonはレプリカをそれぞれ見比べて、どちらでもう一方を上書きすべきか勝手に判断してくれます。

Unisonもrsyncも、更新にはAndrew TridgellとPaul Mackerrasによるrsyncアルゴリズムを用いています。 これは巨大なファイルの一部分のみが変更された場合に、転送効率を最適化するアルゴリズムです。

UnisonとCVSの違いは何ですか?

(訳注: まずはファイルシンクロナイザであるUnisonとリビジョン管理システムであるCVSの本質的な違いを押さえておくべきでしょう。)

両方とも、中心となるリポジトリの内容に応じて、ディレクトリ構造からなるリモートのレプリカを最新に保つことができます。 また双方向にファイルの更新を行なったり、衝突する更新を検知したりもできます。 同時に、UnisonもCVSもファイルの転送にはrsyncのものと同じプロトコルを用います。

CVSに勝るUnisonの利点は、特に大量のファイルに対して、より自動的に、簡単に更新が行なえることでしょう。 CVSを使う場合は、ファイルを追加したり削除したりした場合に、手動でその手続きを行なう必要があります。 ファイルを移動する場合は少しトリッキーです。 ディレクトリを移動したい場合なんか‥‥まあ、これは実際にやってみてください。

しかしながら成熟したリビジョンコントロールシステムであるCVSは、例えば履歴や複数のブランチを保持できる等、単なるファイルシンクロナイザであるUnisonにはない多くの機能を備えています。

NFSでリモートのファイルシステムをマウントしてローカルでUnisonを実行しても構いませんか?それともリモートでサーバを起動しておく必要がありますか?

ローカルネットワークが十分に速いのであれば、レプリカをNFSでマウントしても構いません。 Unisonは(特に同期の度に全てのファイルの更新時刻をチェックする必要があるために)たくさんのファイルを読む必要があります。 よって帯域が細いのであれば、リモートでサーバを起動しておいた方が良いでしょう。

WindowsでGUIを起動すると、メインのウィンドウと空のコンソールウィンドウが開きます。コンソールウィンドウを開かなくすることはできますか?

コンソールウィンドウはsshのパスワードを入力する時に使います。 残念ながら現在のバージョンのUnisonでは、sshを利用するか否かに関わらず、コンソールウィンドウが表示されてしまいます。

Karl Moerderがコンソールウィンドウの見た目をもう少し良くするためのスクリプトを公開しています。 彼の方法では、.cmdファイルへのショートカットからUnisonを起動します。 するとコンソールウィンドウのサイズを小さくし、背景を灰色にし、パスフレーズの入力欄をセンタリングさせる等、ウィンドウの属性をコントロールすることができるようになります。 彼の書いたスクリプトはhttp://www.cis.upenn.edu/~bcpierce/unison/download/resources/karls-winhax.zipからダウンロードできます。

また(ソケットモードでサーバに接続しているユーザは)アイコンに細工することでウィンドウを消してしまうこともできます。 実行可能ファイルに対してショートカットを設定しているなら、プロパティを設定してそのウィンドウが最小化された状態で表示することができます(最小化ですから、タスクバーからも消してしまうことはできませんが)。

推移的に用いた場合でもUnisonはうまく動きますか?つまり host1/dirhost2/dirhost2/dirhost3/dir をそれぞれ違うタイミングで同期させても大丈夫ですか?接続のグラフがループになっていると何か問題になりますか?

大丈夫でしょう。 それぞれのホストのペアが接続されている限り、Unisonが他のホストとの間で行なった更新がファイルシステムに及ぼす影響は、ユーザが手動で行なった場合と変わりませんから。 もし一つのホスト上のみで変更されたファイルがあり、Unisonがそのファイルが変更されたことを発見した場合には、もう一方のホストで変更されていなければそのファイルがもう一方のホストに転送されます。 もし両方のホストで変更されていると確認した場合は、そのファイルには手をつけません。 よって接続のグラフがループになっているように見えても、(接続が分かれていない限りは)全てのホストでファイルが最新のものに更新されます。

この場合気をつけるべきことがあるとすれば、最初のマシン(むしろ実際は他の全てのマシンについてなのですが)に対して、全てのマシンがファイルの変更を知る前にもう一度更新をかけてしまわないことです。 この場合Unisonはファイルが衝突したと判断するため、手作業で衝突を解決しなければなりません。

/dev/proc のファイルのように特別なファイルを同期させようとするとどうなりますか?

Unisonは単純に同期を拒否します。 Unisonは一般ファイル、ディレクトリ、シンボリックリンクのみを扱えます。

Unisonを同時に複数実行することはできますか?

Unisonはこのような状況に対応しています。 が、あまりテストされてはいませんので、実行する際には注意してください。

ローカル(もしくはNFS等)でUnisonを実行した際、もしあるファイルが両方のレプリカに含まれていた場合はどうなりますか?

同期させようとしていたファイルが他の誰かによって変更されたと判断し、それらのファイルについて(安全に)同期を失敗します。

Unisonが実行中にkillされたらどうなりますか?普通にkillすべきか、もしくはkill -9すべきでしょうか。同期の最中にネットワークが切れたらどうなりますか?一方のマシンがクラッシュしてもう一方が動きつづけた場合は?

心配には及びません。

Unisonと他のプログラム、もしくはユーザが同じファイルにちょうど同時に書き込もうとするような状況ではどうですか?

そういった windows of danger はできるだけ短時間に済ますように努力しますが、その危険性は完全には消し去れません。

UnixのファイルロックはNFS上ではうまく機能しませんが、Unisonにとって問題となりますか?

いいえ。

Windowsシステムで、root オプションはバックスラッシュで区切られているように見えますが、path オプションや ignore オプションはスラッシュで区切られています。どういうことですか?

Unisonは2種類のpathを使います。 ローカルファイルシステムのシンタックスを用いたネイティブのファイルシステムのpathと、常にスラッシュを区切り文字に用いるポータブルな pathです。 root オプションはネイティブのpath、その他はrootから相対的に表現されます。

一般的な問題

Unisonを使っていて問題が発生した時には、以下の情報が解決の助けになるかもしれません。

まず一般的な推奨事項として、理解し難い状況に陥った時はアーカイブファイル(.unison ディレクトリに arNNNNNNNNNNNNNNN のような名前で保存されています)を削除することで、最初の状態に戻すことができます。 2つのレプリカが同一である場合には、アーカイブファイルを削除しても問題ありません。 もし変更点がある場合には、変更されたファイルがもう一方のレプリカにコピーされ、両方のレプリカに同名の、しかし内容の異なるファイルがある場合には衝突として報告されます。

もしUnisonが明らかにバグであるというような動作をした場合には、アーカイブを一旦別の場所に移動してしまうのも手です。 そうすることでその動作を再現することができ、より詳細にバグの報告ができます。

CUIでssh2越しに使った場合にUncaught exception Sys_blocked_ioというエラーが出ます。

これはssh2がその標準出力を non-blocked で開くことが原因です。 しかしUnisonとsshは標準エラー出力とnon-blockedな設定を共有しています(ですからサーバから送られてきたエラーが表示されるのです)。 これはUnisonの実行時に

unison -ui text < other args > 2>/dev/tty

として標準エラー出力をリダイレクトすることで解決できます。

但しこのリダイレクトの書式はシェルによって少し異なります。 例えばcshやtcshを使っている場合には

unison -ui text < other args > >&/dev/tty

とする必要があります。

以下のようなエラーはどんな意味ですか?
Propagating updates [accounting/fedscwh3qt2000.wb3]
failed: error in renaming locally:
/DANGER.README: permission denied

これはUnisonが、中止されるとファイルシステムを良くない状態にするような動作を行なう時にコミットログとして用いる(accounting/fedscwh3qt2000.wb3 という実際の場所に対して accounting/fedscwh3qt2000.wb3.unison.tmp という名前で残っている一時ファイルと同様のものです)DANGER.README というファイルを作成する際にエラーが発生したことを示します。 リネームの操作は短時間に行なわれますが、しかしながら可能性はあります。 もしこの状況が発生した場合コミットログはそのまま残され、次回実行された際にファイルの一貫性がチェックされるべきであることをUnisonに教えます(同時にユーザにも報告されます)。

ここではホームディレクトリ(/ に設定されているのでしょう)に DANGER.README というファイルを作成しようとしたが、書き込み権限がなかったことを意味しています。

コマンドラインで unison work ssh://remote.dcs.ed.ac.uk/work と実行しましたが、fatal error: could not connect to server. というエラーが出て失敗します。しかし ssh remote.dcs.ed.ac.uk/work で直接接続してみると、$PATH は設定されていて、Unisonの実行可能ファイルもちゃんとあります。

最初のケースは Unisonが実行時にsshを呼び出し、2番目のケースではsshがあなたにリモートシェルを提供しています。 sshの設定次第では、この2つのシーケンスは異なるものです。

ssh remote.dcs.ed.ac.uk 'echo $PATH'

と打った時の表示と、一旦ログインしてシェルから echo $PATH と打った時と同じ表示が同じか試してみましょう。 これはsshの設定によるものだと思われますが、詳しいことはわかりません。 詳しい人がいたら是非教えてください(訳注: 例えばユーザのシェルの設定とシステム全体の設定で $PATH が異なる場合に、このようなトラブルが起こるものと思われます。2つ下の項目参照)。

Windows上のOpenSSH越しにUnisonが実行できません。原因はわかりませんか?

Antony Courtneyが以下のコメントを寄せてくれました。

私もこのsshクライアントでUnisonを実行させるのに苦労しました。 そして少なくとも一つの問題に行き当たりました。 この経験を共有して、Windows/Unison/ssh/Cygwinの組み合わせで使おうとするユーザに known good な解決法を提供したいと思います。 bashから実行すると(少なくとも私の場合は)失敗します。 unison\_win32-gtkui.exe を実行すると、Fatal error: Error in checkServer: Broken pipe[read()]というダイアログが出ます。 標準エラー出力にはssh: unison_win32-gtkui.exe: no address associated with hostname. という出力がされます。 これはOcaml Win32ライブラリとCygwinの間で、子プロセスに対する argv[] の扱いが異なるためではないかと思います。 解決法として、UnisonをDOSプロンプトから起動する方法があります。

sshでサーバにログインすると、ちゃんと動いているように見えます(Unisonのバイナリにもちゃんとパスが通っています)が、ssh <server> unison は失敗します。何故でしょうか。

Nick Phillipsが以下の説明を寄せてくれました。

簡単なことです。 sshを起動し、パスワードを入れるなどして、最後にログインシェルに行き着きます。 しかし ssh myhost.com unison を実行すると、Unisonはログインシェルから実行されるわけではありません。 これは異なるシェルの設定スクリプトが使われていることを意味します。 同時に、多くの人が間違った設定スクリプトを設定しています。 例えばbashの場合、.bash_profile はログインシェルとして実行した際にだけ使われます。 これはシステムのコンソールか、ターミナルか、もしくはリモートからログインした場合です。 コマンドラインからxtermを実行した場合にはログインシェルは実行されません。 sshやrshでログインした場合、ログインシェルは実行されないでしょう(これはもちろん良いことです。例えばどんなターミナルが使われているかを尋ねるように、そこからインタラクティブにコマンドを実行したいでしょう。) .bash_profile$PATH の設定をしたいと言い張る人たちは、以下のどれか一つ以上を実行する必要があるでしょう。 これは他の多くのシェルに関しても言えることです。

  1. それをやめる
  2. bashのマニュアルのINVOCATIONのセクションを読む
  3. $PATH.bashrc で設定する
  4. 管理者にシステムの大本で $PATH の設定をするように頼む
  5. .bashrc から .bash_profilesource する...
非常に巨大なディレクトリに対してUnisonを実行するとout of memoryというエラーが出ます。

スタックの最大サイズを増やす必要があります。 例えばLinuxやSolarisのシステムでは、ulimit コマンドを実行します(詳しくはbashのドキュメントを読んでください。)

非常に巨大なファイルをコピーできません。以下のようなエラーが出ます。
Error in querying file information:
Value too large for defined data type [lstat(...)]

これはUnixシステムコールに対するOCamlインタフェースの制限です。 OCamlライブラリがファイルの位置を表現するのに32bitを使っているのが原因です。 OCamlでの正のintの最大値はおよそ2.1E9です。 OCamlの開発チームがいつの日か64bitの整数を用いるインタフェースを提供してくれるのを待ちます。

最初に実行する時、何故Unisonはこんなに遅いのですか?

最初の同期の際、Unisonはレプリカの状態に関する記憶を全く持っていません。 よってUnisonは全てのファイルをチェックし、フィンガープリントを計算し、ネットワーク越しにフィンガープリントを転送し、他方と比較せねばなりません。 一度これが完了するとその情報を蓄えておけるので、次回以降の同期の際にはほとんどの作業をそれぞれローカルに行なうことができるようになります。

プロファイルで指定した path を、コマンドラインの -path オプションでオーバーライドできないのですが。

その通りです。 path は設定を行なう度に、Unisonが同期を行なうリストの中に次々と追加されていきます。 そして一度リストに追加されたpathを削除する方法はありません。 解決法としてはプロファイルを、異なる path を記述した複数のトップレベルのファイルに分け、path 以外の設定に関しては共通のファイルを include する方法があります。

プロファイルに設定した root をコマンドラインからオーバーライドしようとしてもWrong number of roots (2 expected; 4 provided) というエラーが出て失敗します。

root はプロファイルかコマンドラインのいずれかでのみ設定する必要があります。

OCaml 3.04でUnison 2.7.7をコンパイルしようとしていますが、Values do not matchというエラーが出ます。

Unisonの2.7.7はOcaml3.02でコンパイルできます。 それ以降の(3.04を含む)バージョンのデフォルトでは、インタフェースの中で宣言された場合、関数呼び出しへの引数の全てのラベルが必要となります。 解決するにはMakefile.OCamlというファイルに CAMLFLAGS+=-nolabels と追加して -nolabels オプションを有効にします。 2.7.7をGUIをコンパイルする際は、LablGtk 1.1.3の代わりに1.1.2を使ってください。

トリックとTips

Unisonをinetdから実行することはできますか?

私たちは試してはいませんが、Toby Johnsonが詳しいchroot mini-HOWTOを寄せてくれました。(TobyのHOWTOの元になったHOWTOはYan Seinerによるものです。)

Unisonに実行の度にパスワードを尋ねなくさせることはできますか?(そうすれば、例えば30分に一回、シェルスクリプトから自動的に実行させることができます。)

(訳注: この回答は公開鍵認証でssh接続ができるという前提で書かれています。)

実際にパスワードを尋ねているのは、Unisonから内部的に呼び出されたsshです。 UnixでUnisonを実行しているのであれば、ssh-agent を試してみるべきでしょう。

ssh-agent bash

と実行すると、サブプロセスとしてbashが実行されます。 このシェルから ssh-add コマンドで秘密鍵を登録します。 これは実行した際に一度だけパスワードを尋ね、そのセッションが終了するまでそのパスワードを保存します。 これでパスワードを入力せずにUnisonを実行でき、更にはシェルスクリプトから自動的に繰り返しUnisonを実行することもできます。

sshでパスワードを要求しない設定にすることも考えられます。 認証用の公開鍵を作る際に空のパスフレーズを与えれば良いのです。 クライアントにパスフレーズが空の秘密鍵を置いておいても問題ないと思うのであれば、この方法はWindowsマシンでも使うことができます。

WindowsでUnisonをクリックスタートして、特定のプロファイルを使って同期させることはできますか?

Greg Sullivanが以下の有用なトリックを教えてくれました。

Windows 98のマシンでクリックして特定のプロファイルで同期させるには、プロファイルでsshを使っているのであれば、unison profile-name という内容だけ(Unisonの実行可能ファイルがパス上にあるのであれば)を含んだ .bat ファイルを作る必要があります。 最初はデスクトップにショートカットを作り、unison profile-name というコマンドを実行するよう設定したのですが、実行するとハングしてしまいます。 しかし .bat を使うトリックはうまくいきます。 というのも、まず command.com を立ち上げてから .bat ファイルを実行するからです。

sshのポートフォワーディングでUnisonを実行することはできますか?

Mark Thomasは以下の方法でうまくいくと言います。

Windowsでコマンドラインからssh越しにUnisonを使おうとすると問題があったのですが、Unisonは通信にソケットを使えることに気付きました(何て素晴らしいソフトウェアでしょう!)。 そこでTTSSH(http://www.zip.com.au/~roca/ttssh.html)のポートフォワーディング機能を使ってみました。 Unisonを使うには、ポートフォワーディングを有効にしたTTSSHに、Unisonサーバプロセスが走っているLinuxサーバに接続します。 Windowsでは単にUnisonを実行してlocalhostに接続する(unison socket://localhost:XXXX/ ...)だけです。

接続するネットワークによってホスト名が変わるラップトップ上でUnisonを使うことはできますか?

rootalias 機能で使えるようになります。

#####(Unixで)ダイアログボックスではなく、コンソールでパスフレーズを打たねばならないのが面倒です。より良い方法はありますか?

ダイアログボックスにPTYを割り当ててsshとやり取りする等、いくつかのアイディアがあります。 が、まだそれらを実装はしていません。 あなたがハックしてみたいのなら、私たちは喜んでアイディアについての議論やパッチのマージに応じますよ。

一方、tmbがexpectkを使ってその機能を実現するスクリプトを公開しています。 http://www.cis.upenn.edu/~bcpierce/unison/download/resources/expectk-startupから手に入ります。