這個Python程式可以線上將TWNIC的台灣IP清單,轉成iptables的指令,貼到/etc/iptables.rules上,就可以限制只能台灣的IP能存取。
限制port時,用如下寫法,port 80使用"TaiwanIP"規則(平常我們是寫ACCEPT):
-A INPUT -p tcp -m tcp --dport 80 -j TaiwanIP
所以你的iptables.rules裡會先有這些描述:
:INPUT DROP [27:1852]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [164:21816]
:TaiwanIP - [0:0]
如果是更改作用中的防火牆,用以下指令加入:
iptables -N TaiwanIP
設定好iptables.rules後,用如下指令讓新規則產生做用:
sudo iptables-restore < /etc/iptables.rulesP.S. 有些單位的IP範圍不在清單上,好像是比較敏感的單位。
程式碼
# -*- coding: utf-8 -*- ''' 產生台灣IP清單及iptables指令 ''' import urllib.request import pandas as pd import ipaddress from bs4 import BeautifulSoup response = urllib.request.urlopen('https://rms.twnic.net.tw/twnic/User/Member/Search/main7.jsp?Order=ORG.ID') html = response.read().decode(response.headers.get_content_charset()) soup = BeautifulSoup(html, 'html.parser') listTagTable = soup.find_all('table') df = pd.read_html( str(listTagTable[5]),header=0 )[0] def getIP(x): ipStart, ipEnd = x.split(' - ') ipStartInt = int(ipaddress.IPv4Address(ipStart)) ipEndInt = int(ipaddress.IPv4Address(ipEnd)) return pd.Series([ipStart, ipEnd, ipStartInt, ipEndInt], index=['ipStart', 'ipEnd', 'ipStartInt', 'ipEndInt']) df2 = df.iloc[:,3].apply( getIP ) #只一行Series,可以不指定axis df['ipStart'] = 0 df['ipEnd'] = 0 df['ipStartInt'] = 0 df['ipEndInt'] = 0 df[ ['ipStart', 'ipEnd', 'ipStartInt', 'ipEndInt'] ] = df2 df = df.sort_values(by=['ipStartInt']) dicMerge = {'name':[df.iloc[0, 0]] , 'ID':[df.iloc[0, 1]] , 'ipStart':[df.iloc[0, 5]] , 'ipEnd':[df.iloc[0, 6]] , 'ipStartInt':[df.iloc[0, 7]] , 'ipEndInt':[df.iloc[0, 8]] } rowN, colN = df.shape dicMergeIndex = 0 #下列For是將IP範圍相鄰的合併,如此只需一組 for i in range(1,rowN): if (df.iloc[i, 7] - dicMerge['ipEndInt'][dicMergeIndex]) == 1: dicMerge['ipEndInt'][dicMergeIndex] = df.iloc[i, :]['ipEndInt'] dicMerge['ipEnd'][dicMergeIndex] = df.iloc[i, :]['ipEnd'] else: dicMerge['name'].append(df.iloc[i, 0]) dicMerge['ID'].append(df.iloc[i, 1]) dicMerge['ipStart'].append(df.iloc[i, 5]) dicMerge['ipEnd'].append(df.iloc[i, 6]) dicMerge['ipStartInt'].append(df.iloc[i, 7]) dicMerge['ipEndInt'].append(df.iloc[i, 8]) dicMergeIndex += 1 dfTaiwanIP = pd.DataFrame(dicMerge) rowN2, colN2 = dfTaiwanIP.shape with open('TaiwanIP.txt', 'w', encoding='utf8') as f: for i in range(0, rowN2): f.write("-A TaiwanIP -m iprange --src-range %s-%s -j ACCEPT\n" % (dfTaiwanIP.iloc[i]["ipStart"], dfTaiwanIP.iloc[i]["ipEnd"]) ) #上述會產生一連串的iptables指令到TaiwanIP.txt這個檔案,直接貼到/etc/iptables.rules。但我是寫給"TaiwanIP" chain,故前面要有":TaiwanIP - [0:0]"
沒有留言:
張貼留言