Last-modified: 2014-08-25 (月) 01:51:56
Nginx/Gitlab,Redmine,Jenkinsサブディレクトリ構成の設定

概要

GitLab, Redmine, JenkinsをHTTPS、サブディレクトリ、MariaDB構成で構築したときのNginxの設定例です。
ここでは、以下のサンプルURLを使用します。
https://hoge.paburica.com/gitlab
https://hoge.paburica.com/redmine
https://hoge.paburica.com/jenkins
各サービス自体のインストールについては、以下のリンクをご覧ください。
MariaDB/Debianへのインストール
GitLab/Debianへのインストール
Redmine/Debianへのインストール
Jenkins/Debianへのインストール

/etc/nginx/nginx.conf(一応)

Everything is expanded.Everything is shortened.
  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
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 
 
 
 
 
 
 
 
 
 
 
 
 
 
-
|
|
!
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
-
|
|
!
 
 
-
|
|
!
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
-
|
|
!
 
 
user                            www-data;
worker_processes                1;
pid                             /var/run/nginx.pid;
worker_rlimit_nofile            8192;
 
events
{
    worker_connections          1024;
    multi_accept                on;
    use                         epoll;
}
 
http
{
    ##
    # 基本設定
    ##
    sendfile                    on;
    tcp_nopush                  on;
    tcp_nodelay                 on;
    keepalive_timeout           10;
    types_hash_max_size         2048;
    server_tokens               off;
    include                     /etc/nginx/mime.types;
    default_type                application/octet-stream;
    client_max_body_size        20M;
    client_body_buffer_size     64k;
    open_file_cache             max=1000 inactive=20s;
    open_file_cache_valid       30s;
    open_file_cache_min_uses    2;
    open_file_cache_errors      on;
    add_header                  X-Frame-Options DENY;
    add_header                  X-Content-Type-Options nosniff;
 
 
    ##
    # ログ設定
    ##
    log_format  main            '[$time_local],$status,$upstream_cache_status,$request_time,'
                                '$body_bytes_sent,$remote_addr,"$request","$http_user_agent"';
 
    ##
    # Gzip設定
    ##
    gzip                        on;
    gzip_disable                "msie6";
    gzip_vary                   on;
    gzip_proxied                any;
    gzip_comp_level             6;
    gzip_min_length             1024;
    gzip_types                  text/plain
                                text/xml
                                text/css
                                application/xml
                                application/xhtml+xml
                                application/rss+xml
                                application/atom_xml
                                application/json
                                application/javascript
                                application/x-javascript;
 
    ##
    # Virtual Host設定
    ##
    include                     /etc/nginx/conf.d/*.conf;
    include                     /etc/nginx/sites-enabled/*;
}

/etc/nginx/sites-available/hoge(本筋)

Everything is expanded.Everything is shortened.
  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
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
-
!
 
 
 
-
!
 
 
 
-
!
 
 
 
 
-
!
 
 
 
 
 
 
 
-
!
 
-
!
 
 
 
 
 
-
!
 
 
 
 
 
 
 
 
-
!
 
 
-
!
 
 
 
 
 
 
 
 
 
 
-
!
 
 
 
 
 
 
-
!
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
-
|
|
|
|
|
|
|
|
|
|
!
 
 
 
-
!
 
 
-
!
 
 
 
 
-
!
 
 
 
 
 
 
 
-
!
-
!
 
# Gitlabサーバー
upstream gitlab
{
    server unix:/home/git/gitlab/tmp/sockets/gitlab.socket;
}
# Redmineサーバー
upstream redmine
{
    server unix:/home/redmine/redmine/tmp/sockets/redmine.socket;
}
# Jenkinsサーバー
upstream jenkins
{
    server 127.0.0.1:8080 fail_timeout=0;
}
 
# httpアクセスをhttpsへrewrite
server
{
    listen                          80;
    server_name                     hoge.paburica.com;
    rewrite                         ^ https://$server_name$request_uri? permanent;
}
 
 
# httpsでの設定
server
{
    # 基本設定
    listen                          443 ssl spdy;
    server_name                     hoge.paburica.com;
    root                            /opt/www/hoge;
    access_log                      off;
    error_log                       off;
 
    # SSL
    ssl                             on;
    ssl_certificate                 <公開鍵パス>;
    ssl_certificate_key             <秘密鍵パス>;
    ssl_session_cache               shared:SSL:10m;
    ssl_session_timeout             10m;
    ssl_prefer_server_ciphers       on;
    gzip                            off;        # BREACH ATTACK対策
    add_header                      Strict-Transport-Security max-age=63072000;
 
    # basic認証
    auth_basic                      <basic認証領域名(適当で良い)>;
    auth_basic_user_file            <basic認証ファイルパス>;
 
    # プロキシ
    proxy_read_timeout              300;
    proxy_connect_timeout           300;
    proxy_set_header                Host                $host;
    proxy_set_header                X-Real-IP           $remote_addr;
    proxy_set_header                X-Forwarded-Proto   https;
    proxy_set_header                X-Forwarded-Host    $host;
    proxy_set_header                X-Forwarded-For     $proxy_add_x_forwarded_for;
    proxy_set_header                X-Frame-Options     SAMEORIGIN;
    proxy_buffer_size               64k;
    proxy_buffers                   50 32k;
 
    # ルート
    location /
    {
        index                       index.php   index.html;
        access_log                  /opt/nginx/log/hoge/access.log main;
        error_log                   /opt/nginx/log/hoge/error.log warn;
    }
 
    # Gitlab
    location /gitlab
    {
        proxy_pass                  http://gitlab;
        access_log                  /opt/nginx/log/gitlab/access.log main;
        error_log                   /opt/nginx/log/gitlab/error.log warn;
    }
    location /gitlab/assets/
    {
        alias                       /home/git/gitlab/public/assets/;
        gzip_static                 on;
        expires                     max;
        add_header                  Cache-Control public;
        log_not_found               off;
        access_log                  off;
    }
    location /gitlab/uploads/
    {
        alias                       /home/git/gitlab/public/uploads/;
        gzip_static                 on;
        log_not_found               off;
        access_log                  off;
    }
    location ~ /gitlab/.*\.git
    {
        proxy_pass                  http://gitlab;
        access_log                  /opt/nginx/log/gitlab/access.log main;
        error_log                   /opt/nginx/log/gitlab/error.log warn;
        # nginxのbasic認証と、プライベートリポジトリへアクセスする際の
        # gitlabアカウント認証という2段構成になる為、https経由のgit操作が行えない
        # なので、.gitに限りnginxのbasic認証をしない
        # ただし、これだけだとgitlabアカウント認証後にプライベートリポジトリのcloneはできるが、pushはできない
        # pushまで行うには、gitlab-shellのconfig.ymlにnginxのbasic認証情報を足せば良い
        #
        # .gitの場合にnginxのbasic認証をスキップするので
        # gitlabのリポジトリはprivateもしくはinternalのみの運用にする
        # publicにしていると、仮に.gitパスが漏れた場合、そのリポジトリは認証なしでgit操作が可能になってしまう
        #
        # 通常はSSH経由でアクセスするので、いっその事https経由のgit操作を禁止にするのも手
        satisfy                     any;
        allow                       all;
    }
 
    # Jenkins
    location /jenkins
    {
        proxy_pass                  http://jenkins;
        # Nginxのbasic認証情報がjenkinsに伝わり401になるため、空にする
        proxy_set_header            Authorization "";
        access_log                  /opt/nginx/log/jenkins/access.log main;
        error_log                   /opt/nginx/log/jenkins/error.log warn;
    }
 
    # Redmine
    location /redmine
    {
        proxy_pass                  http://redmine;
        access_log                  /opt/nginx/log/redmine/access.log main;
        error_log                   /opt/nginx/log/redmine/error.log warn;
    }
 
 
    # .から始まるファイルへのアクセスを禁止
    location ~ /\. { deny all; log_not_found off; access_log off; }
    # robots.txtのアクセスログをとらない
    location = /robots.txt { log_not_found off; access_log off; }
}    

/etc/nginx/sites-available/local(Jenkins・GitLab連携用)

/etc/nginx/sites-available/hogeからもわかるように、JenkinsもフロントにNginxのbasic認証があります。
さらにJenkins自体の認証も有効にしています。

さてここで、GitLabからのWebhook URLにbasic認証情報は載せたくないので、notifyCommitのみbasic認証対象外にすると仮定します。
するとnotifyCommitはJenkins認証不要かつ、パスが自明なので外部から幾らでもGET/POST出来てしまいます(正常にビルドさせるには追加の正しいパラメータが必要ではありますが)

今回はGitLabとJenkinsが同じサーバー上にあるため、GitLabで叩くURLを127.0.0.1/~にすることでセキュリティを保ちつつ正常に動作させるようにしました。
notifyCommitを外から叩いても、Nginxのbasic認証に阻まれます。
別サーバーにある場合は、Jenkinsの別プラグインを使い、tokenありのWebhook URLでないと動かない仕組みにした上で、そのURLのbasic認証を無効にすればいけるでしょう。

Everything is expanded.Everything is shortened.
  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
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
-
!
 
 
 
 
-
!
 
 
 
 
 
 
 
-
!
 
-
!
 
 
 
 
 
 
 
-
!
 
 
 
 
 
 
 
 
-
!
 
 
 
 
 
 
 
 
 
 
-
!
 
 
 
 
 
 
-
!
-
!
 
 
# Jenkinsサーバー
upstream jenkins_webhook
{
    server 127.0.0.1:8080 fail_timeout=0;
}
 
# httpアクセスをhttpsへrewrite
server
{
    listen                          80;
    server_name                     127.0.0.1;
    rewrite                         ^ https://$server_name$request_uri? permanent;
}
 
 
# httpsでの設定
server
{
    # 基本設定
    listen                          443 ssl spdy;
    server_name                     127.0.0.1;
    root                            /opt/www/hoge;
    access_log                      off;
    error_log                       off;
    allow                           127.0.0.1;
    deny                            all;
 
    # SSL
    ssl                             on;
    ssl_certificate                 <公開鍵パス>;
    ssl_certificate_key             <秘密鍵パス>;
    ssl_session_cache               shared:SSL:10m;
    ssl_session_timeout             10m;
    ssl_prefer_server_ciphers       on;
    gzip                            off;        # BREACH ATTACK対策
    add_header                      Strict-Transport-Security max-age=63072000;
 
    # プロキシ
    proxy_read_timeout              300;
    proxy_connect_timeout           300;
    proxy_set_header                Host                $host;
    proxy_set_header                X-Real-IP           $remote_addr;
    proxy_set_header                X-Forwarded-Proto   https;
    proxy_set_header                X-Forwarded-Host    $host;
    proxy_set_header                X-Forwarded-For     $proxy_add_x_forwarded_for;
    proxy_set_header                X-Frame-Options     SAMEORIGIN;
    proxy_buffer_size               64k;
    proxy_buffers                   50 32k;
 
    # Jenkins webhook
    location /jenkins/git/notifyCommit
    {
        proxy_pass                  http://jenkins_webhook;
        access_log                  /opt/nginx/log/jenkins/access.log main;
        error_log                   /opt/nginx/log/jenkins/error.log warn;
    }
 
    # .から始まるファイルへのアクセスを禁止
    location ~ /\. { deny all; log_not_found off; access_log off; }
    # robots.txtのアクセスログをとらない
    location = /robots.txt { log_not_found off; access_log off; }
}

再起動

Everything is expanded.Everything is shortened.
  1
  2
  3
  4
  5
-
|
|
!
 
# sites-enabledにシンボリックリンクがなければ作る
# ln -s /etc/nginx/sites-available/hoge /etc/nginx/sites-enabled/
# ln -s /etc/nginx/sites-available/local /etc/nginx/sites-enabled/
 
service nginx restart

補足

SSLサーバー証明書の秘密鍵はchmod 600でアクセス権を締めないといけません。

検証時の環境