実験自動化(Lab Automation)のススメ

こんにちは。
実験系の研究者をやっています、Kumaです。

今回は、急速に普及している「実験自動化」について紹介します。
実験自動化は、英語では「Lab automation」とか「Lab Hack」と呼ばれます。

実験装置にCLIで制御コマンドを送信し、リモート動作させます。
(例えば　"ON")

全ての実験装置に対してAPIを作り、それをスクリプトとして並べれば、実験の工程は完全に自動化できます。
実験データ取得後の分析操作も自動化してしまえば、究極的には結果の考察以外は人間がやることはなくなります。
私の仕事場では、このような環境を実際に（ほぼ）実現しています。

しかしこのような自動化を行うには、気を付けることなど、多くのノウハウがあります。
ここではその概要をお伝えします。

# 言語の選択
こだわりがない限り、Pythonが良いと思います。
MATLAB, Labviewも使えるのですが、Pythonは無料でインストールも軽いので、
「実験装置が点在していて、制御用PCをさっさっと作って装置の近くに持って行きたい」
「作ったAPIをすぐほかの人に使ってもらいたい」
という環境でも対応できます。
以降でもPythonを前提に書きます。

# 装置側I/F確認
もちろん装置側にCLI制御が可能な機能とI/Fがないと詰みます。
まず、装置背面を確認します。GPIB, USB, Dsub 9pin(RS232), RJ45(Ethernet)のいずれかがついていれば
おそらくCLI制御が可能です。
まれに、GUIしか対応していないが、GUIを外部PCと接続するためだけのポートとしてついている場合がありますので注意しましょう。
(原理的にはGUIから送信しているコマンド列を盗聴することでCLI制御が可能と言えますが、かなり面倒なのでおすすめしません)

装置のマニュアルを見るのが確実です。

# 制御系の構築

## 素朴な接続
素朴な制御系は以下のようなものです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/878664/e1e4e3d1-10aa-7075-8814-6273e9f29e41.png)

各I/Fに対してアダプタをかましてUSB化し、PCへUSBケーブルで接続してTeratermやpyserialから制御します。
制御対象は、COMポートの番号(USBポートの位置に相当)で指定します。


しかしI/F毎に通信プロトコルは異なるので、APIを統一するのが手間です。
また、多数接続に向きません。
USBハブを使ったとしても、デバイスの数が5以上ぐらいになると、接続が不安定になります。
(仕様のUSB接続可能数はかなり大きいのですが、実際やってみると、すぐに不安定になります。特にUSB3.0世代からはひどい傾向があります。)
また、制御元(Client PC)はUSBケーブルが届く範囲に置かねばなりません。
ラボ装置の周辺にPCを置いて作業する”作業スペース”が取れない場合は多いでしょう。

## VISAを使う
まず、「APIを統一できない」という課題を、VISAにより解決します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/878664/13f2b805-5e5a-d6c2-127a-182bf7d7e4e2.png)

VISAはソフトウェアで、Client PCにインストールして使います。
VISAはNI, Keysight, Tektronixなど多くの会社から無料でリリースされています。
私はNI VISA を使っています。競合することが多いので、どれか1つのVISAソフトウェアにしたほうが良いです。

VISAを入れておくと、つながっているデバイスたちは"VISAアドレス(VISAリソースネーム)"で識別されます。
装置のI/Fの差は隠ぺいされ、VISAアドレスを変えるだけで同じ制御スクリプトで制御が可能です。
例えば多くの装置で通常利用可能な、S/Nなどを問い合わせる"*IDN?"というコマンドであれば、送る先のvisaアドレスを変えるだけで、まったく同じコマンド(write)で送信でき、まったく同じ形式でリプライが返ってきます(read)。
また、VISAは後述する VISAサーバー　という機能があり、いわゆる"踏み台”構成を取ることで、NWを大幅にスケールアップすることが可能です。

## VISA サーバーを用いた、USB制御の改善

VISAを用いたとしても残る課題である、
「制御元(Client PC)はUSBケーブルが届く範囲に置かねばなりません。」
を解決します。
以下のような構成にすると、制御元(Client PC)から延びるケーブルをRJ45(Ethetnet)にできます。
もちろん、ルータなどに刺してもよくなります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/878664/769b917a-7556-ccaa-77f6-84a8743f9797.png)

"踏み台”となるPC (server PC)を用意します。
このPCにはNI VISA serverをインストールしておきます。
client PC と　server PCをethernetでつなぎます。
server PCには、USB制御のデバイスをUSBケーブルでつなぎます。
client PCから、VISAアドレスを指定すると、踏み台を経由して、デバイスを制御できます。
VISAアドレスは、踏み台PCのIPアドレス＋USBデバイスのVISAアドレス　という形式になっています。

## VISAサーバーを用いた、GPIB制御

GPIBの場合も、USBとほぼ同じです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/878664/1c3693d0-2264-e393-f718-f2e6e400e66d.png)

GPIBには”GPIBハブ”というのはありませんが、GPIBケーブル自体が数珠繋ぎに対応しています。
そのため、複数のGPIBデバイスをぶら下げることができます。
また、server PCにつなぐためにGPIB/USB変換アダプタが必要です。
NIなどから販売されています。（意外と高いです。。）

## RS232制御

RS232の場合、USBやGPIBとはかなり異なります。
"RS232ハブ"というのが（おそらく）ないためです。
かといってRS232/Ethernet(NIC内蔵)変換アダプタを大量に買うのもコスト的に賢くありません。
そこで、RS232多ポート化をするための"踏み台"を立てます。
(ほかにもやり方があるかもしれません)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/878664/809df2ed-0743-7d20-3ae8-3d25afa5e2f1.png)

このような踏み台は”コンソールサーバー”などと呼ばれています。
コンソールサーバーは、RJ45ポートを複数持ちます。
1個がClient PC用、そのほかがRS232デバイス用（装置側）です。
RS232デバイス用のRJ45ポートと、装置のRS232ポートを、変換アダプタ(pin配置の変換のみで、NIC機能は不要)を介して接続します。
すると、client PC からコンソールサーバーに制御コマンドを送ると、そのままフォワーディングされて装置へ届きます。
具体的な実装としては、client PCからコンソールサーバーにtelnetします。
このとき、telnetのポート番号を何にするかで、コンソールサーバーにおける装置側RJ45ポートのどこへフォワーディングするかが決まります。

この構成の場合、telnetプロトコルを使うという仕様上、visaで直接透過することはできません。client PC からvisaリソースネームをサーチしても、装置は見つかりません。
(TCP raw socketで送り付ければいけるかもしれませんが、やったことはありません)
この点はイマイチかもしれません。

# PC側

client PC側はPythonをインストールします。
ライブラリとして、telnetlib, pyvisa, pyserialがあればよいでしょう。
また、NI VISAを入れておきます。

server PCは、NI VISA serverを入れて、サーバーを起動しておきます。

clientPCで、pyvisaをimportして、resourceリストを取得します。
正しく装置が接続できていれば、VISAアドレスのリストが返ってきます。
これを指定して with構文で装置との通信をopenします。

# VISA制御ができない場合
まず、visaを通さずに、かつ1:1接続で、teratermなどで直接ログイン/コマンドが通るか確かめます。

telnetモードで通れば、pythonのtelnetlibでも通るはずです。telnetポート番号は装置によりまちまちなので注意して下さい。
visaはtelnetプロトコルによる接続には対応していない(はず)ので、この場合はtelnetlibで制御することになりますが、pyvisaと使い勝手はそれほど変わりません。
(queryメソッドがないぐらい)

COMポート接続で通れば、pyserialでも通るはずです。この場合はpyvisaでも通るはずです。通らないとしたら、visaアドレスに問題があるか、visaのインストールに問題があるかです。

次に、visaアドレスを手動で指定してみます。アドレスには決まったルールがありますので、自動サーチで引っ掛からなくても諦める必要はありません。実際、踏み台を何個か通したりすると自動サーチで引っかからないことがあります。

# おわりに
装置制御は、とにかく経験の世界です。
簡単なところから制御をしてみて、徐々にスケールアップするとよいでしょう。
自動化することで、実験時間を1/10とか1/100にできることも珍しくありません。
また必然的に入出力データがデジタルデータとして手元に残りますので、データの解析などにも非常に役立ちます。
実験の再現性も上がります("とりあえず10回測ってみるか")。
グラフの分解能も上がります。人間ではやる気にならない数の測定ができるからです。

現在では、visaやpyvisaの存在など、装置制御は非常にやりやすくなっていると思います。

次は、制御のソフトウェア(pyvisaなど)の使い方などについて書こうと思います。