Avahi 筆記
Avahi 是一個在內網內, 用來廣播自己是什麼服務以及用來尋找那些服務的一個工具, 有點像是在一個社區內有個廣播系統, 大家利用他就可以找到郵局在那裡, 醫院在那裡, 而不必事先知道郵局或醫院的名字. 據了解 avahi 是利用 multicast 來做到這件事,安裝上要細分的話可以分成 server 以及 client.
client 的部份主要是用來聽廣播, 得到網路上所有可使用的服務.
server 的部份主要是要告訴大家你自己是誰, 提供什麼服務
裝好 package 之後, 就可以開始編寫你自己的服務, 預設是放在 /etc/avahi/services 下, 而在 /usr/share/doc/avahi-daemon/examples 裡有一些現成的範例
主要需要設定的
1. service protocol, ipv4/ipv6/all
2. service 名稱,
3. port number
其它細節可以參考這裡
http://manpages.ubuntu.com/manpages/precise/man5/avahi.service.5.html
在顯示上不想要顯示 _xxxx._tcp 可以透過設定 /usr/share/avahi/service-types
那就可以讓別人看到 Human readable 的文字
實際應用上, 我曾因為 ipv6 打開的關係造成了一些困擾, 所以如果想要把 ipv6 關掉, 可以在 /etc/avahi/avahi-daemon.conf 內關掉 ipv6. 也可以設定只對那些 interface 發送廣播.
因為 avahi 是一個 daemon, 如果想要和這個 daemon 溝通, 可以通過 dbus. 下面是 Python 的範例. 有一次我無法將 avahi-daemon 叫起來, 後來才發現是 dbus 這個 service 死掉了, 一但把 dbus 叫起來之後, avahi 就可以啟動了
http://stackoverflow.com/questions/3430245/how-to-develop-an-avahi-client-server
如果覺得透過 dbus 溝通有點麻煩的話, 也可以直接透過 bash command, 下面是我寫的一個小程式
最後分享的一個經驗是, 在使用 avahi 要注意的一點就是他為了要降低 loading, 所以更新的速度並不是很快, 一般他都是直接從 cache 裡面抓資料給你, 所以有時你會發現有的服務不存在了, 但從 avahi-browse 還是會看到它, 所以拿到資料後, 你還是要處理有可能服務已經不存在的情況. 不過如果有新的服務加進來, 因為是主動 broadcast, 所以你一定會接到更新. 如果你一定要拿到最新的情況, 目前我已知的方法就只有重啟 avahi-daemon, 比較耗時間.
Reference link:
http://manpages.ubuntu.com/manpages/precise/man5/avahi.service.5.html
http://manpages.ubuntu.com/manpages/precise/man8/avahi-daemon.8.html
http://manpages.ubuntu.com/manpages/precise/man1/avahi-browse.1.html
http://en.gentoo-wiki.com/wiki/Avahi
client 的部份主要是用來聽廣播, 得到網路上所有可使用的服務.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
| pjack@ubuntu:~$ sudo apt-get install avahi-utils pjack@ubuntu:~$ avahi-browse --help avahi-browse [options] avahi-browse [options] -a avahi-browse [options] -D avahi-browse [options] -b -h --help Show this help -V --version Show version -D --browse-domains Browse for browsing domains instead of services -a --all Show all services, regardless of the type -d --domain=DOMAIN The domain to browse in - v --verbose Enable verbose mode -t --terminate Terminate after dumping a more or less complete list -c --cache Terminate after dumping all entries from the cache -l --ignore- local Ignore local services -r --resolve Resolve services found -f --no-fail Don't fail if the daemon is not available -p --parsable Output in parsable format -k --no-db-lookup Don't lookup service types -b --dump-db Dump service type database # 不間斷的聽取廣播內容, 一但有更新就會顯示出來 pjack@ubuntu:~$ avahi-browse -a + eth0 IPv6 Virtualization Host centos Virtual Machine Manager local + eth0 IPv4 Virtualization Host centos Virtual Machine Manager local # 你也可以只聽特定的服務, 並且加上 -t 參數, 表示不需要持續的聽廣播 pjack@ubuntu:~$ avahi-browse -t _nodeinfo._tcp + eth0 IPv6 bmc-00:26:2d:0a:35:a4 _nodeinfo._tcp local + eth0 IPv4 bmc-00:26:2d:0a:35:a4 _nodeinfo._tcp local # 可以再加上 -r, 除了可以獲得該服務的 ip address/hostname 之外, # 其實有時候該服務也會加上更多有關自己的訊息在 "txt" 欄位 pjack@ubuntu:~$ avahi-browse -r -t _mongodb._tcp + eth0 IPv4 db on mongodb-001 _mongodb._tcp local = eth0 IPv4 db on mongodb-001 _mongodb._tcp local hostname = [mongodb-001. local ] address = [172.17.255.33] port = [0] txt = [] # -p 這個參數是把 output 格式變成方便處理一點, 但在舊一點的版本還沒有這個功能 pjack@ubuntu:~$ avahi-browse -r -p -t _mongodb-db._tcp +;eth0;IPv4;db\032on\032mongodb-001;_mongodb._tcp; local =;eth0;IPv4;db\032on\032mongodb-001;_mongodb._tcp; local ;mongodb-001. local ;172.17.255.33;0; |
server 的部份主要是要告訴大家你自己是誰, 提供什麼服務
1
| pjack@ubuntu:~$ sudo apt-get install avahi-daemon |
裝好 package 之後, 就可以開始編寫你自己的服務, 預設是放在 /etc/avahi/services 下, 而在 /usr/share/doc/avahi-daemon/examples 裡有一些現成的範例
主要需要設定的
1. service protocol, ipv4/ipv6/all
2. service 名稱,
3. port number
其它細節可以參考這裡
http://manpages.ubuntu.com/manpages/precise/man5/avahi.service.5.html
1
2
3
4
5
6
7
8
9
10
|
< type >_ssh._tcp< /type >
/port > < /service > < /service-group > |
在顯示上不想要顯示 _xxxx._tcp 可以透過設定 /usr/share/avahi/service-types
那就可以讓別人看到 Human readable 的文字
1
2
| pjack@ubuntu:~$ avahi-browse -t _libvirt._tcp + eth0 IPv6 Virtualization Host localhost Virtual Machine Manager local |
實際應用上, 我曾因為 ipv6 打開的關係造成了一些困擾, 所以如果想要把 ipv6 關掉, 可以在 /etc/avahi/avahi-daemon.conf 內關掉 ipv6. 也可以設定只對那些 interface 發送廣播.
1
2
3
4
5
6
7
| [server] #host-name=foo #domain-name=local #browse-domains=0pointer.de, zeroconf.org use-ipv4= yes use-ipv6=no allow-interfaces=eth0 |
因為 avahi 是一個 daemon, 如果想要和這個 daemon 溝通, 可以通過 dbus. 下面是 Python 的範例. 有一次我無法將 avahi-daemon 叫起來, 後來才發現是 dbus 這個 service 死掉了, 一但把 dbus 叫起來之後, avahi 就可以啟動了
http://stackoverflow.com/questions/3430245/how-to-develop-an-avahi-client-server
1
2
3
4
| pjack@ubuntu: /etc/avahi $ ps aux | grep daemon 102 506 0.0 0.0 23908 1000 ? Ss 08:48 0:00 dbus-daemon --system --fork --activation=upstart avahi 523 0.0 0.0 32560 1952 ? S 08:48 0:00 avahi-daemon: running [wistor. local ] avahi 524 0.0 0.0 32172 472 ? S 08:48 0:00 avahi-daemon: chroot helper |
如果覺得透過 dbus 溝通有點麻煩的話, 也可以直接透過 bash command, 下面是我寫的一個小程式
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
| def _avahi_browse(service): output = subprocess.check_output( 'avahi-browse -r -t %s' % service, shell = True ) node = {} nodes = [] for line in output.splitlines(): if line.startswith( ' ' ): key,value = line.split( '=' ) key = key.strip( ' ' ) value = value.strip( ' []' ) node.update({key:value}) else : if node: node[ 'hostname' ] = node[ 'hostname' ].strip( '.local' ) nodes.append(node) node = {} if node: node[ 'hostname' ] = node[ 'hostname' ].strip( '.local' ) nodes.append(node) return nodes |
最後分享的一個經驗是, 在使用 avahi 要注意的一點就是他為了要降低 loading, 所以更新的速度並不是很快, 一般他都是直接從 cache 裡面抓資料給你, 所以有時你會發現有的服務不存在了, 但從 avahi-browse 還是會看到它, 所以拿到資料後, 你還是要處理有可能服務已經不存在的情況. 不過如果有新的服務加進來, 因為是主動 broadcast, 所以你一定會接到更新. 如果你一定要拿到最新的情況, 目前我已知的方法就只有重啟 avahi-daemon, 比較耗時間.
Reference link:
http://manpages.ubuntu.com/manpages/precise/man5/avahi.service.5.html
http://manpages.ubuntu.com/manpages/precise/man8/avahi-daemon.8.html
http://manpages.ubuntu.com/manpages/precise/man1/avahi-browse.1.html
http://en.gentoo-wiki.com/wiki/Avahi
沒有留言:
張貼留言