Freeradius 整合 Gmail POP3s 協定認證

Freeradius整合POP3這個應用已經蠻長一段時間了,這個方式其實在整合及擴充上相對比較簡單及便利,使用既有的Mail Server(支援POP3 over SSL協定)來達到認證的需求,就可以省下架設Microsoft Active Directory or LDAP或是複雜的介接設定。

以下就來說明一下Freeradius是如何透過POP3協定來作認證。

Change Log

  • 20170101 更新針對Freeradius 3.0.x版本對於authorize的設定方式,加入Policy的應用。

基本環境

  • CentOS 6.x
  • Freeradius 2.1.12 / 3.0.x
  • Google Mail (Gmail) / POP3 over SSL

Packages Install

此次的功能我們會需要freeradius2-perl來擴充應用,撰寫Freeradius的perl module作為pop3的溝通媒介。

1
yum install freeradius2 freeradius2-utils freeradius2-perl perl

由於安全性的考量,很多Mail Server都會採用加密的方式來作界接,所以我們也需要針對perl來安裝ssl的外掛套件。

1
2
3
4
[root@radius ~]# cpan

cpan[1]>install Mail::POP3Client
cpan[2]>install IO::Socket::SSL

proxy.conf

在最下面加入你所要認證的domain,這裡你可以加好幾個gmail所屬的domain(Google Apps)。

1
2
3
4
5
realm gmail.com {
type = radius
authhost = LOCAL
accthost = LOCAL
}

users (Freeradius 2.x)

在這個檔案的最下面加入

1
2
3
4
5
6
7
8
9
# #
# # Last default: shell on the local terminal server.
# #
# DEFAULT
# Service-Type = Administrative-User

# On no match, the user is denied access.

DEFAULT Auth-Type = Perl, Realm != DEFAULT

這個用意是指,如果帳號的字串裡面沒有match到proxy.conf所設定的Realm DEFAULT,就將此request加入Auth-Type = Perl,並繼續執行驗證。

modules/perl

尋找module這個參數,將example.pl改為你想要自訂的perl script檔名。

此例為pop3s.pl

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
# -*- text -*-
#
# $Id$

# Persistent, embedded Perl interpreter.
#
perl {
#
# The Perl script to execute on authorize, authenticate,
# accounting, xlat, etc. This is very similar to using
# 'rlm_exec' module, but it is persistent, and therefore
# faster.
#
#module = ${confdir}/example.pl
module = ${confdir}/pop3s.pl
...
}

pop3s.pl

上述我們提到的example.pl範例檔案位於/etc/raddb/,我們可以將他複製一份,並改名為pop3s.pl

1
cp -p /etc/raddb/example.pl /etc/raddb/pop3s.pl

然後進行編輯,找到use Data::Dumper;,在下面加上

1
2
3
4
5
6
7
8
9
use Mail::POP3Client;
use IO::Socket::SSL;
use strict;
# use ...
# This is very important ! Without this script will not get the filled hashesh from main.
use vars qw(%RAD_REQUEST %RAD_REPLY %RAD_CHECK);
use Data::Dumper;
use Mail::POP3Client;
use IO::Socket::SSL;

接下來找到sub authenticate {...},在這個section裡面改成。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
sub authenticate {
my $pop = Mail::POP3Client->new(
USER => $RAD_REQUEST{'User-Name'},
PASSWORD => $RAD_REQUEST{'User-Password'},
HOST => "pop.gmail.com",
USESSL => 1,
);

if($pop->Connect()){
# login success
return RLM_MODULE_OK;
}else{
# login fail
return RLM_MODULE_REJECT;
}

$pop->Close;
}
...

policy.d/ (Freeradius 3.x)

新增一個檔案 pop3s (注意檔案權限)。加入以下內容

1
2
3
4
5
6
7
pop3s.authorize {
if (!control:Auth-Type && Realm =~ /gmail\.com$/) {
update control {
Auth-Type := Perl
}
}
}

sites-available/default (Freeradius 2.x/3.x)

authorize {...}裡面找到files,在下面加入

1
2
3
4
5
6
7
authorize {
...
files
perl #2.x
pop3s #3.x
...
}

authenticate {...}裡面找到Auth-Type MS-CHAP {...},在下面加入

1
2
3
4
5
6
7
8
9
10
11
12
13
authenticate {
...
#
# MSCHAP authentication.
Auth-Type MS-CHAP {
mschap
}

Auth-Type Perl {
perl
}
...
}

這裡的Auth-Type Perl就是我們上面users裡的定義,意思就是說當request裡面有Auth-Type = Perl,他就會來找authenticate裡面的Auth-Type Perl,然後找到perl這個module來作驗證。

以上的設定基本上啟動Freeradius後就可以透過POP3對Gmail進行認證了。