25.09.05
parent
407c803550
commit
d6696ff765
|
@ -11,7 +11,7 @@ bind = "0.0.0.0:8000"
|
|||
workers = 2
|
||||
|
||||
# 工作模式(sync、gevent、uvicorn.workers.UvicornWorker)
|
||||
worker_class = "uvicorn.workers.UvicornWorker"
|
||||
worker_class = "uvicorn_worker.UvicornWorker"
|
||||
|
||||
# 日志目录
|
||||
log_dir = Path("logs")
|
||||
|
@ -34,7 +34,7 @@ accesslog = "logs/access.log"
|
|||
errorlog = "-"
|
||||
|
||||
# access_log_format 仅在 同步 worker 下有效,UvicornWorker下不可用;以 YAML 配置优先
|
||||
# access_log_format = '%(h)s %(l)s %(u)s %(t)s "%(r)s" %(s)s %(b)s "%(f)s" "%(a)s" %(D)s'
|
||||
access_log_format = '%(h)s %(l)s %(u)s %(t)s "%(r)s" %(s)s %(b)s "%(f)s" "%(a)s" %(D)s'
|
||||
raw_env = [
|
||||
"UVICORN_ACCESS_LOGFORMAT=%(h)s %(l)s %(u)s %(t)s \"%(r)s\" %(s)s %(b)s \"%(f)s\" \"%(a)s\" %(D)s"
|
||||
]
|
||||
|
@ -44,9 +44,3 @@ timeout = 120
|
|||
|
||||
# Keep-Alive超时
|
||||
keepalive = 5
|
||||
|
||||
# 进程名(ps aux 中显示)
|
||||
# proc_name = "gunicorn"
|
||||
|
||||
# 守护进程运行(后台运行,默认 False)
|
||||
# daemon = True
|
||||
|
|
|
@ -11,7 +11,7 @@ bind = "0.0.0.0:8000"
|
|||
workers = 2
|
||||
|
||||
# 工作模式(sync、gevent、uvicorn.workers.UvicornWorker)
|
||||
worker_class = "uvicorn.workers.UvicornWorker"
|
||||
worker_class = "uvicorn_worker.UvicornWorker"
|
||||
|
||||
# 日志目录
|
||||
log_dir = Path("logs")
|
||||
|
@ -34,7 +34,7 @@ accesslog = "logs/access.log"
|
|||
errorlog = "-"
|
||||
|
||||
# access_log_format 仅在 同步 worker 下有效,UvicornWorker下不可用;以 YAML 配置优先
|
||||
# access_log_format = '%(h)s %(l)s %(u)s %(t)s "%(r)s" %(s)s %(b)s "%(f)s" "%(a)s" %(D)s'
|
||||
access_log_format = '%(h)s %(l)s %(u)s %(t)s "%(r)s" %(s)s %(b)s "%(f)s" "%(a)s" %(D)s'
|
||||
raw_env = [
|
||||
"UVICORN_ACCESS_LOGFORMAT=%(h)s %(l)s %(u)s %(t)s \"%(r)s\" %(s)s %(b)s \"%(f)s\" \"%(a)s\" %(D)s"
|
||||
]
|
||||
|
@ -44,9 +44,3 @@ timeout = 120
|
|||
|
||||
# Keep-Alive超时
|
||||
keepalive = 5
|
||||
|
||||
# 进程名(ps aux 中显示)
|
||||
# proc_name = "gunicorn"
|
||||
|
||||
# 守护进程运行(后台运行,默认 False)
|
||||
# daemon = True
|
||||
|
|
|
@ -311,10 +311,10 @@ class Favicon:
|
|||
Returns:
|
||||
域名是否合法且非内网地址
|
||||
"""
|
||||
return _check_internal(domain) and _pattern_domain.match(domain)
|
||||
return Favicon.check_internal(domain) and _pattern_domain.match(domain)
|
||||
|
||||
@staticmethod
|
||||
def _check_internal(domain: str) -> bool:
|
||||
def check_internal(domain: str) -> bool:
|
||||
"""检查网址是否非内网地址
|
||||
|
||||
Args:
|
||||
|
@ -348,27 +348,4 @@ _pattern_domain = re.compile(
|
|||
|
||||
|
||||
def _check_url(domain: str) -> Optional[Any]:
|
||||
return _check_internal(domain) and _pattern_domain.match(domain)
|
||||
|
||||
|
||||
def _check_internal(domain: str) -> bool:
|
||||
"""
|
||||
检查网址是否非内网地址
|
||||
Args:
|
||||
domain:
|
||||
|
||||
Returns: True 非内网;False 是内网/无法解析
|
||||
"""
|
||||
try:
|
||||
if domain.replace('.', '').isdigit():
|
||||
return not ipaddress.ip_address(domain).is_private
|
||||
else:
|
||||
ips = socket.getaddrinfo(domain, None)
|
||||
for ip_info in ips:
|
||||
ip = ip_info[4][0]
|
||||
if '.' in ip:
|
||||
return not ipaddress.ip_address(ip).is_private
|
||||
return True
|
||||
except Exception as e:
|
||||
print(f"解析网址出错: {e}")
|
||||
return False
|
||||
return Favicon.check_internal(domain) and _pattern_domain.match(domain)
|
||||
|
|
|
@ -344,7 +344,7 @@ class FaviconService:
|
|||
with self._lock:
|
||||
if entity.domain in self.domain_list:
|
||||
self.domain_list.remove(entity.domain)
|
||||
# 同时从两个队列中移除元素(处理完成)
|
||||
# 任务完成,从两个队列中移出元素
|
||||
self._queue_pull(True, self.icon_queue)
|
||||
self._queue_pull(True, self.total_queue)
|
||||
|
||||
|
@ -401,7 +401,8 @@ class FaviconService:
|
|||
if _cached and not cached_icon:
|
||||
# 缓存已过期,后台刷新缓存
|
||||
logger.info(f"缓存已过期,加入后台队列刷新: {entity.domain}")
|
||||
# 只增加总队列计数,不增加实时队列计数(后台任务)
|
||||
# 开始图标处理,加入两个队列
|
||||
self.icon_queue.put(entity.domain)
|
||||
self.total_queue.put(entity.domain)
|
||||
bg_tasks.add_task(self.get_icon_sync, entity, _cached)
|
||||
|
||||
|
@ -415,31 +416,33 @@ class FaviconService:
|
|||
if not is_sync:
|
||||
# 返回默认图片并加入后台队列
|
||||
logger.info(f"返回默认图片并加入后台队列: {entity.domain}")
|
||||
# 只增加总队列计数,不增加实时队列计数(后台任务)
|
||||
# 开始图标处理,加入两个队列
|
||||
self.icon_queue.put(entity.domain)
|
||||
self.total_queue.put(entity.domain)
|
||||
bg_tasks.add_task(self.get_icon_sync, entity, _cached)
|
||||
return self.get_default(0)
|
||||
return self.get_default()
|
||||
else:
|
||||
# 没有缓存,实时处理,检查队列大小
|
||||
queue_size = self.icon_queue.qsize()
|
||||
if queue_size >= self.MAX_QUEUE_SIZE:
|
||||
# 加入后台队列并返回默认图片
|
||||
logger.info(f"队列大小({queue_size})>={self.MAX_QUEUE_SIZE},返回默认图片并加入后台队列: {entity.domain}")
|
||||
# 只增加总队列计数,不增加实时队列计数(后台任务)
|
||||
# 开始图标处理,加入两个队列
|
||||
self.icon_queue.put(entity.domain)
|
||||
self.total_queue.put(entity.domain)
|
||||
bg_tasks.add_task(self.get_icon_sync, entity, _cached)
|
||||
return self.get_default(0)
|
||||
return self.get_default()
|
||||
else:
|
||||
# 队列<MAX_QUEUE_SIZE,实时处理
|
||||
logger.info(f"队列大小({queue_size})<{self.MAX_QUEUE_SIZE},实时处理: {entity.domain}")
|
||||
# 同时增加两个队列计数(实时处理任务)
|
||||
# 开始图标处理,加入两个队列
|
||||
self.icon_queue.put(entity.domain)
|
||||
self.total_queue.put(entity.domain)
|
||||
icon_content = self.get_icon_sync(entity, _cached)
|
||||
|
||||
if not icon_content:
|
||||
# 获取失败,返回默认图标,不缓存
|
||||
return self.get_default(0)
|
||||
return self.get_default()
|
||||
|
||||
# 确定内容类型和缓存时间
|
||||
content_type = filetype.guess_mime(icon_content) if icon_content else ""
|
||||
|
@ -451,7 +454,7 @@ class FaviconService:
|
|||
except Exception as e:
|
||||
logger.error(f"处理图标请求时发生错误 {url}: {e}")
|
||||
# 返回默认图标
|
||||
return self.get_default(0)
|
||||
return self.get_default()
|
||||
|
||||
def get_header(self, content_type: str, cache_time: int = None) -> dict:
|
||||
return self._get_header(content_type, cache_time)
|
||||
|
|
9
main.py
9
main.py
|
@ -30,13 +30,10 @@ app.include_router(favicon_router)
|
|||
|
||||
@app.middleware("http")
|
||||
async def log_referer(request: Request, call_next):
|
||||
_flag = True if ('/icon' in request.url.path and 'url=' in request.url.query) else False
|
||||
logger.info('#' * 60) if _flag else None
|
||||
referer = request.headers.get('referrer') or request.headers.get('referer')
|
||||
if referer:
|
||||
FileUtil.write_file(referer_log_file, referer, mode='a', atomic=True)
|
||||
_referrer = request.headers.get('referrer') or request.headers.get('referer')
|
||||
if _referrer:
|
||||
FileUtil.write_file(referer_log_file, '%s\n' % _referrer, mode='a')
|
||||
response = await call_next(request)
|
||||
logger.info('#' * 60) if _flag else None
|
||||
return response
|
||||
|
||||
|
||||
|
|
|
@ -8,4 +8,5 @@ beautifulsoup4~=4.13.5
|
|||
lxml~=6.0.1
|
||||
PyYAML~=6.0.2
|
||||
uvicorn~=0.35.0
|
||||
uvicorn-worker~=0.3.0
|
||||
gunicorn~=23.0.0
|
||||
|
|
Loading…
Reference in New Issue