自建服务替代gitbook插件pageview-count中的hitcounter.pythonanywhere.com页面计数

教育   2024-09-11 20:37   陕西  

简介

配置gitbook项目,显示浏览记数,结果报错:

Access to XMLHttpRequest at 'https://hitcounter.pythonanywhere.com/count?url=http%253A%252F%252F192.16.7.162%253A51122%252Fscript_docs%252FDB2_dbhealthcheck.html%253Fq%253D' from origin 'http://192.16.7.162:51122' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.

原因是 网站跨域请求禁止了,所以,我们可以使用Flask框架来实现一个简单的页面访问计数器功能,步骤如下:

步骤:

  1. 创建一个Flask应用: 使用Flask框架编写一个Python脚本,用于处理请求并返回页面访问次数。

  2. 存储页面访问次数: 可以使用内存中的字典或者数据库来根据请求的URL存储和增加访问次数。

  3. 部署Flask应用: 完成后,你可以将这个Flask应用部署到本地服务器或云服务器上。

数据存储在内存

安装python依赖包:

1 pip3 install flask  flask-cors

新增app.py程序:

 1from flask import Flask, request, jsonify
2from flask_cors import CORS
3
4app = Flask(__name__)
5CORS(app)  # 允许所有跨域请求
6
7# 存储页面访问次数的字典
8page_views = {}
9
10@app.route('/count', methods=['GET'])
11def count():
12    # 获取请求的URL
13    target_url = request.args.get('url')
14
15    if not target_url:
16        return jsonify("缺少URL参数"), 400
17
18    # 增加页面访问次数
19    if target_url in page_views:
20        page_views[target_url] += 1
21    else:
22        page_views[target_url] = 1
23
24    # 返回当前访问次数
25    return jsonify(page_views[target_url])
26
27if __name__ == '__main__':
28    app.run(host='0.0.0.0', port=5000)

如何使用

  1. 将该脚本保存为 app.py

  2. 运行该脚本来启动Flask服务:python3 app.py

  3. 在你的GitBook脚本中,将请求的URL更改为你服务器的IP或域名。

这样,每次用户访问GitBook页面时,都会向Flask服务器发送请求,并返回相应的页面访问次数。

测试代码:

1curl  http://192.16.7.162:5000/count?url=htttps://www.dbaup.com

可以返回阅读记数。

 1[root@alldb ~]# curl  http://192.16.7.162:5000/count?url=htttps://www.baidu.com
21
3[root@alldb ~]# curl  http://192.16.7.162:5000/count?url=htttps://www.baidu.com
42
5[root@alldb ~]# curl  http://192.16.7.162:5000/count?url=htttps://www.dbaup.com
61
7[root@alldb ~]# curl  http://192.16.7.162:5000/count?url=htttps://www.dbaup.com
82
9[root@alldb ~]# curl  http://192.16.7.162:5000/count?url=htttps://www.dbaup.com
103
11[root@alldb ~]

数据存储在磁盘文件中

为了使页面访问次数能够持久化,当Flask程序重启时不会丢失计数数据,可以将数据存储到磁盘文件中,例如使用JSON文件来存储页面访问次数。这样,程序每次启动时都会从文件加载数据,并在每次请求后更新文件。

 1import json
2from flask import Flask, request, jsonify
3from flask_cors import CORS
4import os
5
6app = Flask(__name__)
7CORS(app)
8
9# 持久化文件路径
10DATA_FILE = 'page_views.json'
11
12# 加载页面访问次数
13def load_data():
14    if os.path.exists(DATA_FILE):
15        with open(DATA_FILE, 'r') as f:
16            return json.load(f)
17    return {}
18
19# 保存页面访问次数
20def save_data(data):
21    with open(DATA_FILE, 'w') as f:
22        json.dump(data, f)
23
24# 加载现有的访问次数
25page_views = load_data()
26
27@app.route('/count', methods=['GET'])
28def count():
29    # 获取请求的URL
30    target_url = request.args.get('url')
31
32    if not target_url:
33        return jsonify("缺少URL参数"), 400
34
35    # 增加页面访问次数
36    if target_url in page_views:
37        page_views[target_url] += 1
38    else:
39        page_views[target_url] = 1
40
41    # 将数据保存到文件
42    save_data(page_views)
43
44    # 返回当前访问次数
45    return jsonify(page_views[target_url])
46
47if __name__ == '__main__':
48    app.run(host='0.0.0.0', port=5000)

解释:

  1. `load_data()`:程序启动时,从指定的JSON文件中加载页面访问次数。如果文件不存在,则返回一个空字典。

  2. `save_data()`:每次请求后,将更新的页面访问次数写入到JSON文件中,确保数据持久化到磁盘。

  3. `page_views`:程序启动时,从JSON文件中读取已有的数据。

使用说明:

  1. 当你启动Flask应用时,它会从page_views.json文件中加载数据。

  2. 每次有新访问时,数据都会自动写回该文件。

  3. 即使重启Flask应用,页面访问次数也不会丢失。

只允许特定域名

 1import json
2from urllib.parse import urlparse, unquote
3from flask import Flask, request, jsonify
4from flask_cors import CORS
5import os
6
7app = Flask(__name__)
8CORS(app)
9
10# 持久化文件路径
11DATA_FILE = 'page_views.json'
12
13# 加载页面访问次数
14def load_data():
15    if os.path.exists(DATA_FILE):
16        with open(DATA_FILE, 'r') as f:
17            return json.load(f)
18    return {}
19
20# 保存页面访问次数
21def save_data(data):
22    with open(DATA_FILE, 'w') as f:
23        json.dump(data, f)
24
25# 加载现有的访问次数
26page_views = load_data()
27
28# 检查URL是否包含 'dbaup.com' 作为主域名或子域名
29def is_dbaup_domain(url):
30    decoded_url = unquote(url)  # 首先对URL进行解码
31    parsed_url = urlparse(decoded_url)  # 解析URL
32    domain = parsed_url.netloc  # 获取主域名
33    # 检查主域名是否包含 'dbaup.com'
34    return domain.endswith('dbaup.com')
35
36@app.route('/count', methods=['GET'])
37def count():
38    # 获取请求的URL
39    target_url = request.args.get('url')
40
41    if not target_url:
42        return jsonify("缺少URL参数"), 400
43
44    # 检查URL是否以 'dbaup.com' 作为主域名或子域名
45    if not is_dbaup_domain(target_url):
46        return jsonify("Disallowed Domains"), 403
47
48    # 增加页面访问次数
49    if target_url in page_views:
50        page_views[target_url] += 1
51    else:
52        page_views[target_url] = 1
53
54    # 将数据保存到文件
55    save_data(page_views)
56
57    # 返回当前访问次数
58    return jsonify(page_views[target_url])
59
60if __name__ == '__main__':
61    app.run(host='0.0.0.0', port=5000)

关键修改点:

  1. `unquote(url)`:使用 urllib.parse.unquote() 对传入的URL进行解码,将类似 https%253A%252F%252Fdbhealthcheck.dbaup.com%252Fscript_docs%252FDB2_dbhealthcheck.html 这样的编码URL转换为标准的 https://dbhealthcheck.dbaup.com/script_docs/DB2_dbhealthcheck.html

  2. `parsed_url.netloc`:解析解码后的URL,并从中提取出主域名。

运行后的效果:

  • 程序会先对URL进行解码,然后再检查是否符合 dbaup.com 主域名的要求。

  • 这样即使URL被编码,也能够正确地识别出 dbaup.com 域名并进行访问次数的计数。

脚本

修改文件_book/gitbook/gitbook-plugin-pageview-count/plugin.js中的https://hitcounter.pythonanywhere.com/count为你自己的服务器地址:

1function requestCount(targetUrl) {
2  return $.ajax('https://hitcounter.pythonanywhere.com/count',{
3    data:{url:encodeURIComponent(targetUrl)},
4  })
5}

为:

1function requestCount(targetUrl) {
2  return $.ajax('http://192.16.7.162:5000/count',{
3    data:{url:encodeURIComponent(targetUrl)},
4  })
5}

报错

Access to XMLHttpRequest at 'http://192.16.7.162:5000/count?url=http%253A%252F%252F192.16.7.162%253A51122%252Fscript_docs%252FDB2_dbhealthcheck.html' from origin 'http://192.16.7.162:51122' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.

这个错误是因为浏览器的同源策略阻止了来自不同源的请求(CORS跨域请求)。为了解决这个问题,你需要在Flask服务器上允许跨域请求。

可以通过使用Flask的flask-cors扩展来解决CORS问题。


效果


总结

1、可以使用宝塔面板将该程序部署为python程序,直接对外访问:https://hitcounter.dbaup.com/count

参考

https://blog.csdn.net/qq_21336651/article/details/100150264

https://developer.aliyun.com/article/1116353


AiDBA
【PostgreSQL培训认证】【Oracle OCP、OCM、高可用(RAC+DG+OGG)培训认证】【MySQL OCP培训认证】【GreenPlum培训】【SQL Server培训】官网:www.dbaup.com,学习不止数据库
 最新文章