.htaccess で出来る事

最近.htaccessを利用する機会が多くなったのでまとめて見ました。

# .htaccessとは
・Apacheなどのソフトウェアが使用されている環境で、
使用可能なディレクトリ単位のWebサーバー設定ファイル
・記述されている内容が、設置されたディレクトリ内とその下層のディレクトリ内に対して適用される
・Nginx などでは使用できない

# .htaccess 利用目的
・基本的に.htaccess ファイルの使用は極力避けるべき
・ディレクトリ毎の設定を行ないたいけれど、サーバシステムの root アクセス権限を持っていない場合
・サーバ管理者が頻繁に httpd.conf の設定変更を行ないたくはないので、個々のユーザが .htaccess ファイルを使って設定変更を行なう場合

# .htaccess で出来る事
・ベーシック認証
・ファイルへのアクセス制御
・リダイレクト
・ URLの正規化
・ファイル一覧表示の中止
・特定のIPアドレスやドメインからのアクセス制限
・ URL拡張子なしでのアクセス
・キャッシュの制御
・gzip 圧縮での高速化

## 　ベーシック認証
### ベーシック認証とは？
・ディレクトリなどに認証を付けてID/パスワードの入力を強制する仕組み

### 用途
・公開前のサイトをユーザーとGooglebot共に弾きたい場合
・アイパスを知っている人だけに公開したい場合

### 設定
.htpasswdファイル作成
passwordの箇所は暗号化する必要がある

``` 
id:password
``` 
.htaccessに下記を追加

``` 
AuthUserfile /FullPath/.htpasswd (FullPath)
AuthName "Please enter your ID and password"
AuthType Basic
require valid-user
``` 
## ファイルへのアクセス制御
・Filesや FilesMatch　ディレクティブを使って、特定のファイルをブラウザーからアクセスできないよう制限
   
### Files ディレクティブ

``` 
特定の IP(192.168.1.1) 以外からの phpinfo.php へのアクセスを拒否

<Files phpinfo.php>
  Order Deny,Allow
  Deny from all
  Allow from 192.168.1.1
</Files>
``` 
### FilesMatch ディレクティブ
``` 
 .htaccess と .htpasswd を見れないようにする

<FilesMatch "^\.(htaccess|htpasswd)$">
  deny from all
</FilesMatch> 
``` 
    
## 　301リダイレクト
・SEOで最も利用される転送方法
・旧ページから新ページへ評価を継承できる

### 用途
・恒久的な移転で、URLの変更やドメインの移転の際に利用

### 設定
http://site.jp/old.html ページから http://site.jp/new.html へ301リダイレクトを行う場合

``` 
RewriteEngine on
RewriteBase /
RewriteRule ^old.html$ http://site.jp/new.html [R=301,L]
``` 
・RewriteRule 転送元ファイル正規表現 転送先URL [フラグ])
    
### RewriteRule で利用可能なフラグ
・R[=code]はredirect：
指定した URL にリダイレクト、指定しない場合は 302(Moved Temporarily) でリダイレクト

・「L」はlast： 
URL の書き換え処理を終了（last）を意味

・「P」は proxy： 
 ルールにマッチしている場合は、書き換えたURLをプロキシ要求とみなし、リバースプロキシとして動作
 
 *フラグを使用する場合は、mod_proxy が組み込まれている必要

### 文字列に利用できる環境変数
・HTTP_HOST
リクエスト先のホスト名 (DNS 名) 情報
www.site.jp/～ でアクセスがあった場合、%{HTTP_HOST} は www.site.jp
    
・THE_REQUEST
リクエスト文字列　例 GET /index.html HTTP/1.1
    
・REQUEST_URI
リクエストされた URI 情報
www.site.jp/blog/detail にアクセスされた場合は /blog/detail
    
・DOCUMENT_ROOT
ドキュメントルートのパス
    
・REQUEST_FILENAME
リクエストされたファイル名(ファイルシステム内の絶対パス)

``` 
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
``` 

## URLの正規化
・URLを1つに統一

### 設定
http://site.jp/
http://www.site.jp/

www無しに統一する場合

``` 
RewriteEngine on
RewriteCond %{HTTP_HOST} ^www\.site\.jp$
RewriteRule ^(.*)$ http://site.jp/$1 [R=301,L]
``` 

## ファイル一覧表示の中止
### 用途
・ディレクトリ構造が外部に公開されるセキュリティ的な懸念を無くす
・ディレクトリ内のファイル一覧表示を中止する

### 設定
```
#ファイル一覧機能を無効にする命令
Options All -Indexes
```

## 特定のIPアドレスやドメインからのアクセス制限
・特定のIPアドレスやドメインからのアクセスを制限・拒否

### 設定
・アクセスを制限したい場合

```
order allow,deny
allow from all
deny from site.jp
deny from 192.168.1.1
```
・アクセスを許可したい場合

``` 
order deny,allow
deny from all
deny from site.jp
deny from 192.168.1.1
``` 
    
## 拡張子なしでのアクセス
### 用途
拡張子表示させったくない
    
### 設定
 ```   
RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.html -f
RewriteRule ^(.*)$ $1.html 
``` 
    
## キャッシュの制御
・ mod_expires は、Expires ヘッダと Cache-Control ヘッダの max-age の設定を制御
    
``` 
<ifModule mod_expires.c>
  ExpiresActive On
  ExpiresDefault "access plus 10 minutes"
  ExpiresByType text/html "access plus 10 seconds"
  ExpiresByType image/jpg "access plus 7 days"
</ifModule> 
``` 
ExpiresDefault ディレクティブ：全てのドキュメントに対してデフォルトの期限切れ期日を設定

ExpiresByType ディレクティブ：タイプ毎に上書きする
    
## gzip 圧縮での高速化
### 用途
 サイズを小さくすることでブラウザと Web サーバ間での通信データ量を減らし、ページの表示がより高速に
    
### 設定
```     
    RewriteCond %{HTTP:Accept-Encoding} gzip
    RewriteCond %{REQUEST_FILENAME} "\.(js)$"
    RewriteCond %{REQUEST_FILENAME} !"\.gz$"
    RewriteCond %{REQUEST_FILENAME}.gz -s
    RewriteRule .+ %{REQUEST_URI}.gz [L]
    
    <FilesMatch "\.js\.gz$">
      ForceType application/x-javascript
      AddEncoding x-gzip .gz
    </FilesMatch>
    Header append Vary Accept-Encoding env=!dont-vary
``` 

## .htaccessで利用するテキスト正規表現について

###  ^(.*)$ の例
.htaccessに下記を書いた場合

``` 
RewriteRule ^(.*)$ blog/$1
``` 
https:/site.jp/detail　にアクセスすると　https:/site.jp/blog/detail　へリダイレクトされる

・　 .*  はあらゆる文字列が対象となる
・　^(.*)$」は「detail」を受け入れる事になり、detailが「$1」の部分へと後方参照
・　「blog/$1」とは「blog/detail」を示す

###  ^.*/(.*)$ の例
.htaccessに下記を書いた場合

``` 
RewriteRule ^.*/(.*)$ news/$1
``` 
https:/site.jp/blog/detail にアクセスすると　https:/site.jp/news/detail　へリダイレクトされる

・ .*  には「blog」の部分、  (.*)  には「detail」が入る
・ 「news/$1」の部分が「news/detail」となる
・ 「blog」は　「()」で囲まれていないので「$1」部分に後方参照されない
・ 「detail」は　「()」で囲まれているので「$1」部分に後方参照される