FICUSONLINE F9E
Flexisip SIPサーバ on Ubuntu 20.04 (Docker-Compose)
前回のブログ記事で紹介したFlexisip on Ubuntu 20.04 DEBパッケージを利用して、FlexisipのDockerイメージ(Ubuntu 20.04)を作成します。このFlexisipイメージとSIPサーバの稼働に必要な他のイメージ (Redis, Nginx, MariaDB, PHP-FPM) をDocker-Composeファイルにより一元管理しSIPサーバを運用します。
Takanobu FuseAdministrator

12 min read

3 years ago

Linux

今回は、Docker-Composeファイル作成までの手順について紹介し、次回のブログでユーザ登録・管理するためのウェブフロントエンドであるFlexisip Account Manager、Linphoneアプリによる設定の読込み:プロビジョニングについて紹介します。

Docker Flexisip System

以下Docker-Composeファイルに必要なFlexisipイメージ他の関連イメージ作成の為のDockerfileを事前に用意します。

1. Flexisip Dockerイメージ

2. Redis(alpine) Dockerfile

3. Nginx(alpine) Dockerfile

4. PHP-FPM-Laravel(alpine) Dockerfile

5. phpMyAdmin(alpine) Dockerfile

6 Docker-Composeファイルの作成


1. Flexisip Dockerイメージ

ダウンロードしたFlexisipディレクトリ内での作業です。

既にビルドしたflexisipDEBパッケージflexisip/dockerディレクトリ内に新たに作成したDEBSディレクトリにコピーして下さい。下図の + マークは、追加するファイルまたはディレクトリです。

Flexisip Docker Directory

次に、Flexisip Dockerイメージを作成するためのDockerfile:flex-ubuntu-from-debflexisip/dockerディレクトリに用意します。

Dockerfile:flex-ubuntu-from-deb

FROM ubuntu:20.04
MAINTAINER  Takanobu Fuse < [email protected]>

ENV DEBIAN_FRONTEND=noninteractive

# Prepare dependencies + SNMP:https://wiki.linphone.org/xwiki/wiki/public/view/Flexisip/Configuration/SNMP/
RUN apt-get update && apt-get install -y nano xsdcxx gdb libmariadb3 net-tools iptables snmp snmpd snmp-mibs-downloader
RUN update-alternatives --set iptables /usr/sbin/iptables-nft \
    && update-alternatives --set ip6tables /usr/sbin/ip6tables-nft

# Get flexisip package
COPY DEBS/*.deb DEBS/*.ddeb deb-packages/
RUN apt-get install -y /deb-packages/bc-*.deb /deb-packages/bc-*.ddeb
RUN rm -rf /deb-packages

# Add it to the default path
ENV PATH=$PATH:/opt/belledonne-communications/bin
ENV LD_LIBRARY_PATH=/opt/belledonne-communications/lib

WORKDIR /opt/belledonne-communications

# Generate a default configuration
RUN flexisip --dump-default all > /etc/flexisip/flexisip.conf

VOLUME /etc/opt/belledonne-communications/flexisip
VOLUME /var/opt/belledonne-communications/log/flexisip
COPY flexisip-entrypoint.sh /
# COPY flexisip-snmpd.sh /
COPY backtrace.gdb /
# COPY snmp.conf /etc/snmp/snmp.conf
COPY snmpd.conf /etc/snmp/snmpd.conf
RUN chmod a+x /flexisip-entrypoint.sh # /flexisip-snmpd.sh

# Script to wait db before launch flexisip [Licence Apache2]
ADD https://github.com/ufoscout/docker-compose-wait/releases/download/2.2.1/wait /wait
RUN chmod +x /wait

ENTRYPOINT ["/flexisip-entrypoint.sh"]
# CMD ["/flexisip-snmpd.sh"]
CMD flexisip

また、このDockerfileからイメージをビルドするためのコマンドをMakefileに追加します。

Makefile

BASE_NAME=gitlab.linphone.org:4567/bc/public/flexisip
$(eval GIT_DESCRIBE = $(shell sh -c "git describe"))
DOCKER_TAG=$(BASE_NAME):$(GIT_DESCRIBE)
DOCKER_FILE=flex-from-src

# We cannot use dockerfile's COPY outside build context
# we use then flexisip directory as context for flex-from-src instead of docker directory

ifeq ($(DOCKER_FILE), flex-from-src)
  CONTEXT=..
else
  CONTEXT=.
endif

flexisip-build:
	docker build -f $(DOCKER_FILE) --pull --no-cache -t $(DOCKER_TAG) --rm $(CONTEXT)

flexisip-push:
	docker push $(DOCKER_TAG)

flexisip-clean:
	docker image rm $(DOCKER_TAG)

flexisip-deb-before:
	$(eval DOCKER_FILE = flex-from-deb)
	# forcing context to .
	# at the moment of the condition above being executed, $DOCKER_FILE doesn't have the right value
	$(eval CONTEXT = .)
	$(eval DOCKER_TAG = $(DOCKER_TAG)-deb)

# For Ubuntu 20.04
flexisip-ubuntu-deb-before:
	$(eval DOCKER_FILE = flex-ubuntu-from-deb)
	# forcing context to .
	# at the moment of the condition above being executed, $DOCKER_FILE doesn't have the right value
	$(eval CONTEXT = .)
	$(eval DOCKER_TAG = $(DOCKER_TAG)-deb)

flexisip-deb-build: flexisip-deb-before flexisip-build

flexisip-deb-push: flexisip-deb-before flexisip-push

flexisip-deb-clean: flexisip-deb-before flexisip-clean

# For Ubuntu 20.04
flexisip-ubuntu-deb-build: flexisip-ubuntu-deb-before flexisip-build

flexisip-ubuntu-deb-push: flexisip-ubuntu-deb-before flexisip-push

flexisip-ubuntu-deb-clean: flexisip-ubuntu-deb-before flexisip-clean

.PHONY: flexisip-build


ホストマシンで以下コマンドを実行するとFlexisip Dockerイメージが作成されます。

$ make flexisip-ubuntu-deb-build

作成されたイメージの確認

$ docker images
REPOSITORY                                                      TAG                           IMAGE ID       CREATED        SIZE
gitlab.linphone.org:4567/bc/public/flexisip                     2.1.0-beta-14-g0ba5e300-deb   715a157478c9   2 weeks ago    842MB
gitlab.linphone.org:4567/bc/public/linphone-sdk/bc-dev-ubuntu   20.04                         9b42d1ba1b96   2 weeks ago    2.59GB

SNMPはオプションなので、導入する場合とその機能についてはフォーラム記事を参照願います。


2. Redis(alpine) Dockerfile

FlexisipのユーザIPを一時的に保管するキャッシュメモリRedisDockerfileを作成します。Alpineイメージをベースに作成しますが、デフォルトでは設定ファイルが提供されていないため、本家サイトからダウンロードして下さい。

ダウンロードした設定ファイルredis.conf内で以下の (1) bind, (2) requirepass を設定します。

(1) bindの設定

Dockerネットワーク内の他のコンテナからもアクセス出来るように、bindの項目にdocker-composeファイルで指定するredisコンテナのIP 172.xx.x.xを追加。

bind 127.0.0.1 172.xx.x.x

(2) パスワードrequirepassの設定

下記opensslコマンドから60文字から成るランダムパスワードを作成します。

$ openssl rand 60 | openssl base64 -A
ZeXT9aNJc3FjrVZ3i7XYAiqaUXq6OU40C9hbrF3d9oG+Ox+BB51/6O4aZaalXQzQ8UxTqRQx86CnEEiR

作成されたパスワードをredis.conf requirepass にコピーして下さい。

requirepass ZeXT9aNJc3FjrVZ3i7XYAiqaUXq6OU40C9hbrF3d9oG+Ox+BB51/6O4aZaalXQzQ8UxTqRQx86CnEEiR

上記redis.confを取り込んだredisイメージファイルを作成するため、以下のdockerfile:redis-alpineを用意します。

dockerfile:redis-alpine

FROM redis:alpine

RUN apk add --no-cache bash nano
COPY redis/redis.conf /etc/redis/redis.conf

3. Nginx(alpine) Dockerfile

certbotによる認証更新をスケジュール管理するため、デフォルトのジョブNginxにクローンデーモンcrondによるジョブを追加したイメージを作成するためのdockerfile:nginx-alpineを用意します。

dockerfile:nginx-alpine

FROM nginx:alpine

# Set working directory
WORKDIR /var/www/html

RUN apk add --no-cache bash nano tzdata certbot-nginx \
    && cp /usr/share/zoneinfo/Asia/Tokyo /etc/localtime \
    && echo "Asia/Tokyo" > /etc/timezone \
    && apk del tzdata
COPY nginx/nginx_default.conf /etc/nginx/conf.d/default.conf
COPY nginx/nginx_crond /etc/periodic/monthly
COPY nginx-crond.sh /
RUN chmod a+x /nginx-crond.sh
CMD ["/nginx-crond.sh"]

以下シェルスクリプトをクロンジョブのマンスリーディレクトリにコピー。

nginx-crond

#!/bin/sh
certbot renew
nginx -s reload

コンテナのマルチサービスを実行するスクリプト作成。

Run multiple services in a container

nginx-crond.sh

#!/bin/bash

# turn on bash's job control
set -m

# Start the primary process and put it in the background
nginx -g 'daemon off;' &

# Start the helper process
crond

# the my_helper_process might need to know how to wait on the
# primary process to start before it does its work and returns

# now we bring the primary process back into the foreground
# and leave it there
fg %1

4. PHP-FPM-Laravel(alpine) Dockerfile

ユーザ管理ウェブフロントエンド、プロビジョニングのために提供されているFlexisip Account Managerのイメージを作成するdockerfile:php-fpm-alpine-laravelを用意します。composerとPHPフレームワークであるLaravel、sqlドライバなどをインストールしたイメージが作成されます。

dockerfile:php-fpm-alpine-laravel

FROM php:7.4-fpm-alpine

# Set working directory
WORKDIR /var/www/html  

RUN apk add --no-cache bash nano libpng-dev freetype-dev libjpeg-turbo-dev libxml2-dev \
    && docker-php-ext-install mysqli xmlrpc \
    && docker-php-ext-enable mysqli xmlrpc \
    && docker-php-ext-configure gd --with-freetype=/usr/include/ --with-jpeg=/usr/include/ \
    && docker-php-ext-install -j$(nproc) gd pdo pdo_mysql \
    && docker-php-ext-enable gd pdo pdo_mysql

# Installing composer
COPY composer_installer.sh /var/www/html
RUN echo 'precedence ::ffff:0:0/96 100' >> /etc/gai.conf \
    && ./composer_installer.sh && mv composer.phar /usr/local/bin/composer

# Installing Laravel
RUN chown -R www-data:www-data /var/www/html
RUN composer global require laravel/installer \
    && ln -s /root/.config/composer/vendor/laravel/installer/bin/laravel /usr/local/bin/laravel

# Make the log directory and the log file for flexisip-account-manager    
RUN mkdir -p /var/opt/belledonne-communications/log \
    && cd /var/opt/belledonne-communications/log \
    && touch account-manager.log \
    && chown www-data:www-data account-manager.log

5. phpMyAdmin(alpine) Dockerfile

ブラウザによりデータベースを管理するため、phpMyAdminのイメージ作成のためのdockerfile:phpmyadmin-alpineも用意します。

dockerfile:phpmyadmin-alpine

FROM phpmyadmin/phpmyadmin:fpm-alpine

RUN apk add --no-cache bash nano \
    && docker-php-ext-install mysqli \
    && docker-php-ext-enable mysqli

6 Docker-Composeファイル

上記作成されたイメージにMariaDBイメージを加えて、FlexisipによるSIPサーバを運用するためのDocker-Composeファイルを作成します。注)各サービスのコメント欄も一読願います。

docker-compose.yml

version: '3'

services:
##### redis-server
  redis:
    container_name: redis
    build: 
      context: ./docker_files
      dockerfile: redis-alpine
    # need to download default config file:redis.conf from https://redis.io/topics/config
    # then modify it to enable the auth access(password), and input it into /redis/etc directory.
    # NOTE: maybe no need to run with redis.conf, because of it is running only inside the docker network.
    # WARNING overcommit_memory is set to 0! Background save may fail under low memory condition. 
    # To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or 
    # run the command 'sysctl vm.overcommit_memory=1' for this to take effect.
    command: ["redis-server", "/etc/redis/redis.conf"]
    privileged: true
    restart: always
    networks: 
      proxy-tier:
        ipv4_address: 172.xx.x.2

##### nginx
  # after "docker-compose up -d", enter the container and execute the following commands. 
  # "certbot certonly --standalone --agree-tos -n -m [email protected] -d sip.example.org"
  # or
  # "certbot --nginx --agree-tos -n -m [email protected] -d sip.example.org"
  # then
  # "cd /etc/letsencrypt/live/sip.example.org"
  # "cp fullchain.pem cafile.pem"
  # "awk 1 privkey.pem cert.pem > agent.pem"
  nginx:
    container_name: nginx
    build: 
      context: ./docker_files
      dockerfile: nginx-alpine
    tty: true
    ports:
      - "80:80"
      - "443:443"
    volumes:
      # nginx config
      - ./nginx:/etc/nginx/conf.d
      # certbot letsencrypt certification
      - letsencrypt:/etc/letsencrypt
      # shared the directory /var/www/html in php-fpm container
      - ./html:/var/www/html
      # shared the directory /var/www/html in phpmysql-fpm container
      - phpmyadmin:/var/www/html/phpmyadmin
      # for flexisip-account-manager
      #- ./flexisip-account-manager:/var/www/html/flexisip-account-manager
    depends_on:
      - phpmyadmin-fpm
      - php-fpm-laravel
    restart: always
    networks: 
      proxy-tier:
        ipv4_address: 172.xx.x.3        

##### mariadb
  flexisip-mariadb:
    container_name: flexisip-mariadb
    image: mariadb
    restart: always
    volumes:
      - ./db:/var/lib/mysql
      - ./mariadb:/etc/mysql/conf.d
    # refer to .env
    environment:
      - MYSQL_ROOT_PASSWORD=${MYSQL_ROOT_PASSWORD}
      - MYSQL_DATABASE=${MYSQL_DATABASE}
      - MYSQL_USER=${MYSQL_USER}
      - MYSQL_PASSWORD=${MYSQL_PASSWORD}
    networks: 
      proxy-tier:
        ipv4_address: 172.xx.x.5

### flexisip
  ubuntu-flexisip:
    container_name: ubuntu-flexisip
    image: gitlab.linphone.org:4567/bc/public/flexisip:2.1.0-beta-14-g0ba5e300-deb
    ports:
      - 5060-5061:5060-5061
      #### Presence-Server
      - 5065:5065
      #### Conference and RegEvent Server
      - 6064-6065:6064-6065
      - 10000-10050:10000-10050/udp
      #### STUN Server
      - 3478:3478/udp   
    volumes:
      - letsencrypt:/etc/flexisip/tls
      # previously need to add "flexisip" directory and input "flexisip.conf" into it.
      - ./flexisip:/etc/flexisip
    depends_on:
      - nginx
      - flexisip-mariadb
    restart: always
    networks: 
      proxy-tier:
        ipv4_address: 172.xx.x.6
    ## allow the privilege of network to the container
    #ulimits:
    #  nofile:
    #    soft: 200
    #    hard: 400
    cap_add:
      - NET_ADMIN
    #  - SYS_RESOURCE
    privileged: true
    
##### phpmyadmin-fpm
  phpmyadmin-fpm:
    container_name: phpmyadmin-fpm
    build: 
      context: ./docker_files
      dockerfile: phpmyadmin-alpine
    tty: true
    expose: 
      - "9000"
    environment:
      - PMA_HOST=flexisip-mariadb
      - PMA_PORT=3306
      - PMA_ABSOLUTE_URI=http://localhost/phpmyadmin
    volumes:
      - phpmyadmin:/var/www/html
      - /sessions
    depends_on:
      - flexisip-mariadb
    restart: always
    networks: 
      proxy-tier:
        ipv4_address: 172.xx.x.7
        
##### php-fpm-laravel
  php-fpm-laravel:
    container_name: php-fpm-laravel
    build: 
      context: ./docker_files
      dockerfile: php-fpm-alpine-laravel      
    tty: true
    expose: 
      - "9000"
    # "php artisan serve" commmand default port
    ports:
      - 8000:8000
    volumes:
      # for laravel php framework
      - ./html:/var/www/html
      - ./etc/conf:/etc/flexisip-account-manager
    depends_on:
      - flexisip-mariadb
    restart: always
    networks: 
      proxy-tier:
        ipv4_address: 172.xx.x.8

### $ docker network create --gateway 172.xx.x.1 --subnet 172.xx.x.0/24 nginx-proxy
networks:
  proxy-tier:
    external:
      name: nginx-proxy

### $ docker volume create phpmyadmin letsencrypt     
volumes:
  phpmyadmin:
    external: true
  letsencrypt:
    external: true

Flexisip SIPサーバシステムの起動

Flexisipの設定ファイルflexisip.confを、各々の環境に合うよう以下のリファレンスガイドを参照して編集して下さい。

Configuration Reference Guide

https://wiki.linphone.org/xwiki/wiki/public/view/Flexisip/A.%20Configuration%20Reference%20Guide/master/

docker-compose.ymlファイルを格納しているディレクトリからdocker-composeコマンドによりFlexisip SIPサーバシステムを起動します。

$ docker-compose up -d

注)デフォルトの設定ファイルflexisip.confflexisipコンテナの/etc/flexisipディレクトリ内に作成されますが、docker-composeファイル内で指定した./flexisip内のflexisip.confに置き換わりますデフォルトのflexisip.confファイルを入手する場合、この " - ./flexisip:/etc/flexisip " のラインをコメントアウトして起動して下さい。

Flexisipコンテナから設定ファイルのコピー

$ mkdir flexisip
$ docker cp ubuntu-flexisip:/etc/flexisip/flexisip.conf ./flexisip

flexisip.confのサンプルは、以下からも入手出来ます。

https://github.com/BelledonneCommunications/liblinphone/tree/master/tester/flexisip


GitHub : Flexisip + Account Manager on Ubuntu 20.04

以下GitHubに関連ファイルをアップロード。一部設定ファイルなどはセキュリティ上割愛。docker-composeファイルのコメント欄を一読願います。

docker-flexisip/ubuntu20-04 at master · capitalfuse/docker-flexisip