PowerShellで、Apacheのhttpd.confのコメントと空行を削除する

前回の記事Apache Lounge版のバイナリを使って、WindowsApacheを入れました。

デフォルトのhttpd.confの内容を確認しようとしたところ、コメントアウトされている行が多く、生きている設定を探すのが手間でした。

そこでコメントアウト行を削除しようと思い探したところ、以下の記事がありました。
設定ファイルのコメントと空行以外を出力する - 元RX-7乗りの適当な日々

 
ただ、手元の端末はWindowsなのでgrepがないことから、Windowsでもできる方法を探してみたところ、

  • find
  • findstr
  • PowerShellのSelect-Stringコマンドレット

があるとのことでした。
外部アプリケーションなしのWindowsでgrepみたいなことをする - Sanwa Systems Tech Blog

そこで、最近使っているPowerShellで試してみたため、その時のメモを残します。

 

環境

 

流れ

デフォルトのhttpd.confの内容を抜粋してみます。

#
# This is the main Apache HTTP server configuration file.  It contains the
# configuration directives that give the server its instructions.
# See <URL:http://httpd.apache.org/docs/2.4/> for detailed information.
# In particular, see 
# <URL:http://httpd.apache.org/docs/2.4/mod/directives.html>
# for a discussion of each configuration directive.
#
# Do NOT simply read the instructions in here without understanding
# what they do.  They're here only as hints or reminders.  If you are unsure
# consult the online docs. You have been warned.  
#
# Configuration and logfile names: If the filenames you specify for many
# of the server's control files begin with "/" (or "drive:/" for Win32), the
# server will use that explicit path.  If the filenames do *not* begin
# with "/", the value of ServerRoot is prepended -- so "logs/access_log"
# with ServerRoot set to "/usr/local/apache2" will be interpreted by the
# server as "/usr/local/apache2/logs/access_log", whereas "/logs/access_log" 
# will be interpreted as '/logs/access_log'.
#
# NOTE: Where filenames are specified, you must use forward slashes
# instead of backslashes (e.g., "c:/apache" instead of "c:\apache").
# If a drive letter is omitted, the drive on which httpd.exe is located
# will be used by default.  It is recommended that you always supply
# an explicit drive letter in absolute paths to avoid confusion.

#
# ServerRoot: The top of the directory tree under which the server's
# configuration, error, and log files are kept.
#
# Do not add a slash at the end of the directory path.  If you point
# ServerRoot at a non-local disk, be sure to specify a local disk on the
# Mutex directive, if file-based mutexes are used.  If you wish to share the
# same ServerRoot for multiple httpd daemons, you will need to change at
# least PidFile.
#
ServerRoot "c:/Apache24"
...

このファイルに対してSelect-Stringコマンドレットで不要な行を削除していきます。

Select-Stringコマンドレット仕様は以下となります。
Select-String - TechNet Library

今回はコメントアウト行(#で始まる行)以外を抜き出したいため、-NotMatchパラメータを使うのが良さそうでした。

# 実行
PS C:\Apache24\conf> Select-String -NotMatch "#" -Path ".\httpd.conf" -Encoding default > result1.txt

# 結果(result1.txt)
httpd.conf:26:
httpd.conf:37:ServerRoot "c:/Apache24"
httpd.conf:38:
httpd.conf:48:
httpd.conf:58:Listen 80
httpd.conf:59:
httpd.conf:72:LoadModule access_compat_module modules/mod_access_compat.so
httpd.conf:73:LoadModule actions_module modules/mod_actions.so
...

コメントアウト行は削除されたようですが、 httpd.conf:26:のようなファイル名と元ファイルの行数が残っています。

 
これについて調べてみたところ、以下に分かりやすく記載されていました。
おえかきWindows: Select-String その他。

今回の場合も、

PS C:\Apache24\conf> Select-String -NotMatch "#" -Path ".\httpd.conf" -Encoding default | gm


   TypeName: Microsoft.PowerShell.Commands.MatchInfo

Name         MemberType Definition
----         ---------- ----------
Equals       Method     bool Equals(System.Object obj)
GetHashCode  Method     int GetHashCode()
GetType      Method     type GetType()
RelativePath Method     string RelativePath(string directory)
ToString     Method     string ToString(), string ToString(string directory)
Context      Property   Microsoft.PowerShell.Commands.MatchInfoContext Conte...
Filename     Property   string Filename {get;}
IgnoreCase   Property   bool IgnoreCase {get;set;}
Line         Property   string Line {get;set;}
LineNumber   Property   int LineNumber {get;set;}
Matches      Property   System.Text.RegularExpressions.Match[] Matches {get;...
Path         Property   string Path {get;set;}
Pattern      Property   string Pattern {get;set;}

Microsoft.PowerShell.Commands.MatchInfoオブジェクトの配列を持っているようです。
MatchInfo Class (Microsoft.PowerShell.Commands) - MSDN

 
そのため、Lineプロパティを使ってみます。

# 実行
PS C:\Apache24\conf> Select-String -NotMatch "#" -Path ".\httpd.conf" -Encoding default | %{ $_.line} > result2.txt

# 結果 (result2.txt)

ServerRoot "c:/Apache24"


Listen 80

LoadModule access_compat_module modules/mod_access_compat.so
LoadModule actions_module modules/mod_actions.so
...

コメントアウト行以外の情報だけになりました。

 
ただ、空行があって見づらい場合があるかもしれないので、空行も消してみます。

# 実行
PS C:\Apache24\conf> Select-String -NotMatch "#|^$" -Path ".\httpd.conf" -Encoding default | %{ $_.line} > result3.txt

# 結果 (result3.txt)
ServerRoot "c:/Apache24"
Listen 80
LoadModule access_compat_module modules/mod_access_compat.so
LoadModule actions_module modules/mod_actions.so
...

空行も消えました。

 
他のパターンとして、複数行の空行を1つの空行にまとめることもやってみたかったのですが、今回はここまでにしておきます。