Monthly ArchiveOctober 2007
軟體 dada on October 11, 2007
Access Subversion with Apache Proxy Module
由於網路架構的問題,我們有時會設計讓不同網段必須透過 Proxy 才能存取 Subversion Repository,但是為此架設一個獨立的 Proxy Server (如 squid)實在太麻煩,利用 Apache 內建的 mod_proxy / mod_proxy_http 功能有時候會讓工作簡化很多
ProxyRequests Off <Proxy *> Order deny,allow Deny from all </Proxy> ProxyVia On
為了安全性考量,如同上面的設定,我們先把所有 Proxy 的存取關掉,然後依據需要開放特定目錄來允許 Proxy
例如我們想把對 /svn 的存取導向到 http://svn.domain/svn,那麼設定內容就會變成:
<VirtualHost *:80> ProxyPass /svn http://svn.domain/svn ProxyPassReverse /svn http://svn.domain/svn <Location /svn> <Limit OPTIONS PROPFIND GET REPORT MKACTIVITY PROPPATCH PUT CHECKOUT MKCOL MOVE COPY DELETE LOCK UNLOCK MERGE> Order Deny,Allow Allow from all Satisfy Any </Limit> </Location> </VirtualHost>
裡面最重要的就是 <Limit OPTIONS PROPFIND... > 這一行(這一整行不能分成兩行,Copy-Paste時請注意),因為 Subversion 會用到除了 HTTP GET / POST 以外的一些特殊 Method,因此必須設定讓 HTTP 的 Proxy Module 允許這些 Methods 通過,才能讓 Subversion 正常運作
另外建議修改 Allow from all 這一行,改成僅允許特定 IP 來連結,也可強化系統的安全性
參考資料: Subversion behind an Apache Reverse Proxy (不過裡面的設定方式跟我上面提供的有一點點小小差異)
如果你還是想用 squid 來解決問題,那您可以參考 Subversion 網站上面的 FAQ
程式語言 dada on October 04, 2007
File handle is always global in Perl
Perl 的 file handle 及 directory handle 一定是 global 的,無法宣告成 local
一般使用上沒有大問題,但是當用在遞迴式呼叫時,就會產生錯誤了,下面是一個把目錄下包含子目錄中所有檔案列出來的 perl 程式,採用遞迴式呼叫。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | #!/usr/bin/perl die "Usage: $0 [directory]\n" unless @ARGV == 1; die "ERROR: $ARGV[0] is not a directory\n" unless -d $ARGV[0]; &show_dir($ARGV[0]); exit; sub show_dir { my( $dir ) = @_; my( $fname ); opendir( DIR, $dir ); while( $fname = readdir(DIR) ) { next if $fname eq '.' || $fname eq '..'; if( -d "$dir/$fname" ) { &show_dir("$dir/$fname"); } else { print "$dir/$fname\n"; } } closedir(DIR); } |
由於 DIR 這個 directory-handle 會被當成 global 變數,因此這段程式會出錯,無法列出所有檔案。
解決方法是把 DIR 這一個 directory-handle 直接用 $dir 來代替,這樣在遞迴的時候就不會因為重複使用而造成錯誤了,下面是改過的程式:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | #!/usr/bin/perl die "Usage: $0 [directory]\n" unless @ARGV == 1; die "ERROR: $ARGV[0] is not a directory\n" unless -d $ARGV[0]; &show_dir($ARGV[0]); exit; sub show_dir { my( $dir ) = @_; my( $fname ); opendir( $dir, $dir ); while( $fname = readdir($dir) ) { next if $fname eq '.' || $fname eq '..'; if( -d "$dir/$fname" ) { &show_dir("$dir/$fname"); } else { print "$dir/$fname\n"; } } closedir($dir); } |