首页
关于
壁纸
直播
留言
友链
统计
Search
1
《三国志英杰传》攻略
6,329 阅读
2
Emby客户端IOS破解
6,196 阅读
3
白嫖Emby
6,187 阅读
4
《吞食天地1》金手指代码
6,066 阅读
5
破解emby-server
4,364 阅读
moonjerx
game
age-of-empires
zx3
san-guo-zhi
尼尔:机械纪元
net
emby
learn-video
docker
torrent
photoshop
route
minio
git
ffmpeg
im
vue
gitlab
typecho
svn
alipay
nasm
srs
mail-server
tailscale
kkfileview
aria2
webdav
synology
redis
oray
chemical
mxsite
math
π
x-ui
digital-currency
server
nginx
baota
k8s
http
cloud
linux
shell
database
vpn
esxi
rancher
domain
k3s
ewomail
os
android
windows
ios
app-store
macos
develop
java
javascript
uniapp
nodejs
hbuildx
maven
android-studio
jetbrain
jenkins
css
mybatis
php
python
hardware
hard-disk
pc
RAM
software
pt
calibre
notion
office
language
literature
philosophy
travel
登录
Search
标签搜索
ubuntu
mysql
openwrt
zerotier
springboot
centos
openvpn
jdk
吞食天地2
synology
spring
idea
windows11
吞食天地1
transmission
google-play
Japanese
xcode
群晖
kiftd
MoonjerX
累计撰写
380
篇文章
累计收到
465
条评论
首页
栏目
moonjerx
game
age-of-empires
zx3
san-guo-zhi
尼尔:机械纪元
net
emby
learn-video
docker
torrent
photoshop
route
minio
git
ffmpeg
im
vue
gitlab
typecho
svn
alipay
nasm
srs
mail-server
tailscale
kkfileview
aria2
webdav
synology
redis
oray
chemical
mxsite
math
π
x-ui
digital-currency
server
nginx
baota
k8s
http
cloud
linux
shell
database
vpn
esxi
rancher
domain
k3s
ewomail
os
android
windows
ios
app-store
macos
develop
java
javascript
uniapp
nodejs
hbuildx
maven
android-studio
jetbrain
jenkins
css
mybatis
php
python
hardware
hard-disk
pc
RAM
software
pt
calibre
notion
office
language
literature
philosophy
travel
页面
关于
壁纸
直播
留言
友链
统计
搜索到
70
篇与
develop
的结果
2025-08-27
解决Docker容器中MySQL连接因LANG环境变量缺失导致的问题
解决Docker容器中MySQL连接因LANG环境变量缺失导致的问题问题描述在使用Docker容器部署Spring Boot应用时,遇到以下错误:java.lang.IllegalStateException: DBAppender cannot function if the JDBC driver does not support getGeneratedKeys method *and* without a specific SQL dialect环境信息:Docker容器:基于Ubuntu 22.04,运行宝塔面板数据库:MySQL 8.0.26(独立容器)应用:Spring Boot + Logback + MySQL Connector 8.0.16关键发现:同样的JAR包在虚拟机上运行正常,在容器中无法启动快速解决方案根本解决方案(推荐):apt-get update && apt-get install -y locales && locale-gen en_US.UTF-8 && update-locale LANG=en_US.UTF-8 && export LANG=en_US.UTF-8 && export LC_ALL=en_US.UTF-8 && echo 'export LANG=en_US.UTF-8' >> ~/.bashrc && echo 'export LC_ALL=en_US.UTF-8' >> ~/.bashrc && source ~/.bashrc临时解决方案(连接参数):在数据库连接URL中添加:allowPublicKeyRetrieval=true&useUnicode=true&characterEncoding=UTF-8spring: datasource: url: jdbc:mysql://127.0.0.1:3306/your_database?useSSL=false&allowPublicKeyRetrieval=true&useUnicode=true&characterEncoding=UTF-8或者在启动容器时添加环境变量:docker run -d \ --name your-container \ --net=host \ --restart always \ --privileged \ -e LANG=C.UTF-8 \ -e LC_ALL=C.UTF-8 \ your-image:tag详细排查过程初期错误理解最初看到错误信息,以为是Logback配置问题,尝试了多种方案:取消注释SQL方言配置 ❌<sqlDialect class="ch.qos.logback.core.db.dialect.MySQLDialect"/>使用DriverManagerConnectionSource ❌升级/降级Logback版本 ❌使用HikariCP替代Commons DBCP ❌暂时禁用DBAppender ✅(临时方案,不是根本解决)转换思路:环境差异分析经过两天的配置调试无果后,开始从环境角度分析问题。1. Java版本对比# 容器和虚拟机都是相同版本 java version "1.8.0_381" Java(TM) SE Runtime Environment (build 1.8.0_381-b09)2. 环境变量对比容器环境:JAVA_HOME=/home/root/soft/jdk1.8.0_381 PATH=/home/root/soft/jdk1.8.0_381/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin # 缺失 LANG 和 LC_* 变量虚拟机环境:JAVA_HOME=/home/root/soft/jdk1.8.0_381 LANG=en_US.UTF-8 # 关键差异! PATH=/home/root/soft/jdk1.8.0_381/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin3. MySQL驱动行为测试创建测试程序验证MySQL驱动的getGeneratedKeys支持:import java.sql.*; public class TestMySQLDriver { public static void main(String[] args) { try { Class.forName("com.mysql.cj.jdbc.Driver"); Connection conn = DriverManager.getConnection( "jdbc:mysql://127.0.0.1:3306/your_database?useSSL=false", "username", "password"); DatabaseMetaData meta = conn.getMetaData(); System.out.println("supportsGetGeneratedKeys: " + meta.supportsGetGeneratedKeys()); System.out.println("Driver version: " + meta.getDriverVersion()); System.out.println("Database version: " + meta.getDatabaseProductVersion()); conn.close(); } catch (Exception e) { e.printStackTrace(); } } }测试结果对比:容器中:java.sql.SQLNonTransientConnectionException: Public Key Retrieval is not allowed at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:110) at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:97) at com.mysql.cj.jdbc.exceptions.SQLExceptionsMapping.translateException(SQLExceptionsMapping.java:122) at com.mysql.cj.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:835) ... at TestMySQLDriver.main(TestMySQLDriver.java:7)虚拟机中:supportsGetGeneratedKeys: true Driver version: mysql-connector-java-8.0.16 Database version: 8.0.26关键发现: 容器环境尝试设置LANG环境变量时出现警告:export LANG=en_US.UTF-8 export LC_ALL=en_US.UTF-8 -bash: warning: setlocale: LC_ALL: cannot change locale (en_US.UTF-8)根因分析核心问题: 容器环境缺少LANG和LC_ALL环境变量,导致:Public Key Retrieval错误 - 这是MySQL 8.0的安全特性,在字符编码异常时更容易触发字符编码处理异常 - MySQL连接器在处理字符编码时出现问题SSL/TLS握手失败 - 编码问题影响了安全连接的建立getGeneratedKeys方法识别失败 - 驱动无法正确识别数据库功能支持本质问题: Public Key Retrieval is not allowed 错误在MySQL 8.0中很常见,但通常在环境正常的情况下可以通过连接参数解决。然而在缺少locale的容器环境中,这个错误变得更加顽固。解决方案详解方案1:修复LANG环境变量(根本解决方案,推荐)# 1. 安装locale支持 apt-get update apt-get install -y locales # 2. 生成UTF-8 locale locale-gen en_US.UTF-8 update-locale LANG=en_US.UTF-8 # 3. 设置环境变量 export LANG=en_US.UTF-8 export LC_ALL=en_US.UTF-8 # 4. 永久化配置 echo 'export LANG=en_US.UTF-8' >> ~/.bashrc echo 'export LC_ALL=en_US.UTF-8' >> ~/.bashrc source ~/.bashrc # 5. 验证配置 locale方案2:连接字符串参数解决(临时方案)如果无法修改容器环境,可以通过调整MySQL连接参数来绕过这个问题:// 添加 allowPublicKeyRetrieval=true 参数 String url = "jdbc:mysql://127.0.0.1:3306/your_database?useSSL=false&allowPublicKeyRetrieval=true&useUnicode=true&characterEncoding=UTF-8";完整连接参数建议:String url = "jdbc:mysql://127.0.0.1:3306/your_database?" + "useSSL=false&" + "allowPublicKeyRetrieval=true&" + "useUnicode=true&" + "characterEncoding=UTF-8&" + "serverTimezone=Asia/Shanghai";Spring Boot配置文件:spring: datasource: url: jdbc:mysql://127.0.0.1:3306/your_database?useSSL=false&allowPublicKeyRetrieval=true&useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai username: username password: password driver-class-name: com.mysql.cj.jdbc.Driver注意: 方案2虽然能解决连接问题,但不能根本解决locale缺失问题,可能在其他功能上仍有隐患。推荐优先使用方案1。方案3:Docker启动时配置docker run -d \ --name baota \ --net=host \ --restart always \ --privileged \ -e LANG=C.UTF-8 \ -e LC_ALL=C.UTF-8 \ -v /path/to/data:/data \ your-image:tag方案4:Dockerfile中预设FROM ubuntu:22.04 # 安装locale并设置环境变量 RUN apt-get update && \ apt-get install -y locales && \ locale-gen en_US.UTF-8 && \ update-locale LANG=en_US.UTF-8 ENV LANG=C.UTF-8 ENV LC_ALL=C.UTF-8 # 其他配置...验证解决效果修复后重新测试MySQL连接:java -cp .:mysql-connector-java-8.0.16.jar TestMySQLDriver期望输出:supportsGetGeneratedKeys: true Driver version: mysql-connector-java-8.0.16 Database version: 8.0.26经验总结环境一致性的重要性 - 看似相同的环境可能存在关键差异字符编码的影响范围 - LANG环境变量不仅影响显示,还会影响网络通信和数据库连接问题定位思路 - 当配置层面无法解决时,要从环境层面分析Docker容器的注意事项 - 容器环境通常是精简的,可能缺少一些基础的系统配置相关问题和预防类似问题可能出现在:其他需要字符编码的Java应用Python应用的数据库连接文件上传/下载功能国际化(i18n)应用预防措施:构建Docker镜像时主动设置LANG环境变量在CI/CD流程中添加环境一致性检查制作标准化的基础镜像,包含必要的locale配置关键要点:根本问题是locale缺失:Public Key Retrieval is not allowed 在MySQL 8.0中很常见,但在locale正常的环境中通常可以通过连接参数解决。在Docker容器的精简环境中,locale缺失使这个问题变得更加复杂。两种解决思路:治本:修复容器的locale环境,这样应用的各个方面都能正常工作治标:通过连接参数绕过验证,但可能在其他功能上仍有隐患环境一致性:Docker容器环境的精简性可能导致一些看似无关的系统配置缺失,而这些配置对应用的正常运行至关重要。在排查此类问题时,环境差异分析往往比配置调优更有效。
2025年08月27日
12 阅读
0 评论
0 点赞
2025-01-26
查询IP地址信息的免费开放接口
在开发网络应用时,了解用户地理位置是提升用户体验的关键之一。本文将介绍多个免费的开放API来查询IP地址的具体信息,并展示其请求方式和返回结果。我们将以阿里巴巴接口文档规范为标准,详细说明每个接口的使用方法。1. 阿里巴巴IP查询接口请求地址https://ip.taobao.com/outGetIpInfo?ip=121.8.215.106&accessKey=alibaba-inc请求方法GET参数说明参数名必选类型说明ip是string待查询的IP地址accessKey是string访问密钥返回数据格式{ "data": { "area": "", "country": "中国", "isp_id": "100017", "queryIp": "121.8.215.106", "city": "广州", "ip": "121.8.215.106", "isp": "电信", "county": "", "region_id": "440000", "area_id": "", "county_id": null, "region": "广东", "country_id": "CN", "city_id": "440100" }, "msg": "query success", "code": 0 }2. 百度IP查询接口请求地址https://sp0.baidu.com/8aQDcjqpAAV3otqbppnN2DJv/api.php?query=119.135.194.24&co=&resource_id=6006&ie=utf8&oe=gbk&format=json请求方法GET参数说明参数名必选类型说明query是string待查询的IP地址resource_id是int资源IDie是string输入编码oe是string输出编码format是string数据格式返回数据格式{ "status": "0", "t": "", "set_cache_time": "", "data": [ { "location": "广东省清远市 电信", "origip": "119.135.194.24" } ] }3. VORE-API IP查询接口请求地址https://api.vore.top/api/IPdata?ip=121.8.215.106请求方法GET参数说明参数名必选类型说明ip是string待查询的IP地址返回数据格式{ "code": 200, "msg": "SUCCESS", "ipinfo": { "type": "ipv4", "text": "121.8.215.106", "cnip": true }, "ipdata": { "info1": "广东省", "info2": "广州市", "info3": "增城", "isp": "电信" }, "adcode": { "o": "广东省广州市增城 - 电信" }, "tips": "接口由VORE-API(https://api.vore.top/)免费提供" }4. 百度地图IP定位接口请求地址https://api.map.baidu.com/location/ip?ak=LA46NZu12hG3MHAfH9jhDRhObBd0uR9t&ip=121.8.215.106请求方法GET参数说明参数名必选类型说明ak是stringAPI密钥ip是string待查询的IP地址返回数据格式{ "address": "CN|广东省|广州市|None|None|100|100", "content": { "address_detail": { "province": "广东省", "city": "广州市", "district": "" }, "address": "广东省广州市", "point": { "x": "12609455.26", "y": "2631453.98" } }, "status": 0 }5. IP.cn API请求地址https://www.ip.cn/api/index?ip=121.8.215.106&type=1请求方法GET参数说明参数名必选类型说明ip是string待查询的IP地址type是int查询类型返回数据格式{ "rs": 1, "code": 0, "address": "中国 广东省 广州市 电信", "ip": "121.8.215.106", "isDomain": 0 }6. db-ip.com API请求地址https://db-ip.com/demo/home.php?s=121.8.215.106请求方法GET返回数据格式{ "demoInfo": { "ipAddress": "121.8.215.106", "continentName": "Asia", "countryName": "中国", "stateProv": "广东", "city": "广州", "timezone": "Asia/Shanghai", "latitude": 23.1317, "longitude": 113.266, "isp": "Chinanet", "organization": "Chinanet GD" } }7. OpenData百度API请求地址https://opendata.baidu.com/api.php?co=&resource_id=6006&oe=utf8&query=121.8.215.106请求方法GET参数说明参数名必选类型说明query是string待查询的IP地址resource_id是int资源IDoe是string输出编码返回数据格式{ "status": "0", "data": [ { "location": "广东省广州市 电信", "origip": "121.8.215.106" } ] }8. Whois.pconline.com.cn API请求地址https://whois.pconline.com.cn/ipJson.jsp?ip=121.8.215.106&json=true请求方法GET参数说明参数名必选类型说明ip是string待查询的IP地址json是bool是否返回JSON返回数据格式{ "ip": "121.8.215.106", "pro": "广东省", "city": "广州市", "addr": "广东省广州市 电信" }9. API.IP.SB GeoIP接口请求地址https://api.ip.sb/geoip/121.8.215.106请求方法GET返回数据格式{ "organization": "China Telecom", "longitude": 113.2539, "city": "Guangzhou", "timezone": "Asia/Shanghai", "isp": "China Telecom", "offset": 28800, "region": "Guangdong", "asn": 4134, "asn_organization": "Chinanet", "country": "China", "ip": "121.8.215.106", "latitude": 23.1181, "continent_code": "AS", "country_code": "CN", "region_code": "GD" }10. IPINFO.IO JSON接口请求地址https://ipinfo.io/121.8.215.106/json请求方法GET返回数据格式{ "ip": "121.8.215.106", "city": "Shenzhen", "region": "Guangdong", "country": "CN", "loc": "22.5455,114.0683", "org": "AS4134 CHINANET-BACKBONE", "postal": "518000", "timezone": "Asia/Shanghai", "readme": "https://ipinfo.io/missingauth" }11. IPINFO.IO Widget接口请求地址https://ipinfo.io/widget/demo/121.8.215.106请求方法GET返回数据格式{ "input": "121.8.215.106", "data": { "ip": "121.8.215.106", "city": "Shenzhen", "region": "Guangdong", "country": "CN", "loc": "22.5455,114.0683", "org": "AS4134 CHINANET-BACKBONE", "postal": "518000", "timezone": "Asia/Shanghai", "is_anycast": false, "is_mobile": false, "is_anonymous": false, "is_satellite": false, "is_hosting": false, "asn": { "asn": "AS4134", "name": "CHINANET-BACKBONE", "domain": "chinatelecom.com.cn", "route": "121.8.0.0/13", "type": "isp" }, "company": { "name": "CHINANET Guangdong province network", "domain": "chinatelecom.cn", "type": "isp" }, "privacy": { "vpn": false, "proxy": false, "tor": false, "relay": false, "hosting": false, "service": "" }, "abuse": { "address": "No.31 ,jingrong street,beijing, 100032", "country": "CN", "email": "anti-spam@chinatelecom.cn", "name": "ABUSE CHINANETCN", "network": "121.8.0.0/13", "phone": "+000000000" } } }12. API.IPBASE.COM IP查询接口请求地址https://api.ipbase.com/v1/json/121.8.215.106请求方法GET返回数据格式{ "ip": "121.8.215.106", "country_code": "CN", "country_name": "China", "region_code": "CN-GD", "region_name": "Guangdong", "city": "Guangzhou", "zip_code": "510140", "time_zone": "Asia/Shanghai", "latitude": 23.1273612976074, "longitude": 113.264572143555, "metro_code": 0 }13. IP-API.IO JSON接口请求地址https://ip-api.io/json?ip=121.8.215.106请求方法GET返回数据格式{ "ip": "27.158.109.238", "countryCode": "CN", "country_code": "CN", "countryName": "China", "country_name": "China", "isInEuropeanUnion": false, "is_in_european_union": false, "regionName": "Guangdong", "region_name": "Guangdong", "regionCode": "GD", "region_code": "GD", "city": "Guangzhou", "zipCode": "", "zip_code": "", "timeZone": "Asia/Shanghai", "time_zone": "Asia/Shanghai", "latitude": 23.1181, "longitude": 113.2539, "metroCode": 0, "metro_code": 0, "organisation": "Chinanet", "flagUrl": "https://www.countryflags.io/CN/flat/64.png", "emojiFlag": "https://www.countryflags.io/CN/emoji.png", "currencySymbol": "", "currency": "", "callingCode": "", "countryCapital": "", "suspiciousFactors": { "isProxy": false, "isTorNode": false, "isSpam": false, "isSuspicious": false } }14. API.IPAPI.IS 查询接口请求地址https://api.ipapi.is/?ip=121.8.215.106请求方法GET返回数据格式{ "ip": "121.8.215.106", "rir": "APNIC", "is_bogon": false, "is_mobile": false, "is_crawler": false, "is_datacenter": false, "is_tor": false, "is_proxy": true, "is_vpn": false, "is_abuser": true, "company": { "name": "CHINANET Guangdong province network", "abuser_score": "0.0003 (Very Low)", "domain": "chinatelecom.cn", "type": "isp", "network": "121.8.0.0 - 121.15.255.255", "whois": "https://api.ipapi.is/?whois=121.8.0.0" }, "abuse": { "name": "IPMASTER CHINANET-GD", "address": "NO.18,RO. ZHONGSHANER,YUEXIU DISTRIC,GUANGZHOU", "email": "anti-spam@chinatelecom.cn", "phone": "+86-20-87189274" }, "asn": { "asn": 4134, "abuser_score": "0.001 (Low)", "route": "121.8.0.0/13", "descr": "CHINANET-BACKBONE No.31,Jin-rong Street, CN", "country": "cn", "active": true, "org": "CHINANET BACKBONE", "domain": "chinatelecom.cn", "abuse": "anti-spam@chinatelecom.cn", "type": "business", "updated": "2021-06-15", "rir": "APNIC", "whois": "https://api.ipapi.is/?whois=AS4134" }, "location": { "is_eu_member": false, "calling_code": "86", "currency_code": "CNY", "continent": "AS", "country": "China", "country_code": "CN", "state": "Guangdong", "city": "Guangzhou", "latitude": 23.11667, "longitude": 113.25, "zip": "510000", "timezone": "Asia/Shanghai", "local_time": "2025-01-26T17:34:38+08:00", "local_time_unix": 1737884078, "is_dst": false }, "elapsed_ms": 0.92 }15. IPAPI.COM 查询接口请求地址https://ipapi.com/ip_api.php?ip=121.8.215.106请求方法GET返回数据格式{ "ip": "121.8.215.106", "hostname": "121.8.215.106", "type": "ipv4", "continent_code": "AS", "continent_name": "Asia", "country_code": "CN", "country_name": "China", "region_code": "GD", "region_name": "Guangdong", "city": "Guangzhou", "zip": "510000", "latitude": 23.124719619751, "longitude": 113.238609313965, "msa": null, "dma": null, "radius": null, "ip_routing_type": "fixed", "connection_type": "tx", "location": { "geoname_id": 1809858, "capital": "Beijing", "languages": [ { "code": "zh", "name": "Chinese", "native": "中文" } ], "country_flag": "https://assets.ipstack.com/flags/cn.svg", "country_flag_emoji": "🇨🇳", "country_flag_emoji_unicode": "U+1F1E8 U+1F1F3", "calling_code": "86", "is_eu": false }, "time_zone": { "id": "Asia/Shanghai", "current_time": "2025-01-26T17:27:58+08:00", "gmt_offset": 28800, "code": "CST", "is_daylight_saving": false }, "currency": { "code": "CNY", "name": "Chinese Yuan", "plural": "Chinese yuan", "symbol": "CN¥", "symbol_native": "CN¥" }, "connection": { "asn": 4134, "isp": "Chinanet", "sld": "kj-textile", "tld": "com", "carrier": "chinanet", "home": true, "organization_type": "Internet Service Provider", "isic_code": "J6110", "naics_code": "517311" }, "security": { "is_proxy": false, "proxy_type": null, "is_crawler": false, "crawler_name": null, "crawler_type": null, "is_tor": false, "threat_level": "low", "threat_types": null, "proxy_last_detected": null, "proxy_level": null, "vpn_service": null, "anonymizer_status": null, "hosting_facility": false } }16. API.IP2LOCATION.IO 查询接口请求地址https://api.ip2location.io/?ip=121.8.215.106请求方法GET返回数据格式{ "ip": "121.8.215.106", "country_code": "CN", "country_name": "China", "region_name": "Guangdong", "city_name": "Guangzhou", "latitude": 23.12736, "longitude": 113.26457, "zip_code": "510140", "time_zone": "+08:00", "asn": "4134", "as": "Asia Pacific Network Information Centre", "is_proxy": true, "message": "Limit to 500 queries per day. Sign up for a Free plan at https://www.ip2location.io to get 30K queries per month." }17. REALIP.CC 查询接口请求地址https://realip.cc/?ip=121.8.215.106请求方法GET返回数据格式{ "ip": "121.8.215.106", "city": "Guangzhou", "province": "Guangdong", "country": "China", "continent": "Asia", "isp": "Chinanet", "time_zone": "Asia/Shanghai", "latitude": 23.1181, "longitude": 113.2539, "postal_code": null, "iso_code": "CN", "network": "121.8.128.0/17", "notice": "api文档在/docs路径下,调用并发数是有限制的 ©2021-09-27->now", "provider": "Powered by Bboysoul", "blog": "https://www.bboy.app", "tg_group": "https://t.me/bboyapp", "data_updatetime": 20250102, "count": 195369546 }18. IPAPI.CO 查询接口请求地址https://ipapi.co/121.8.215.106/json/请求方法GET返回数据格式{ "ip": "121.8.215.106", "network": "121.8.128.0/17", "version": "IPv4", "city": "Guangzhou", "region": "Guangdong", "region_code": "GD", "country": "CN", "country_name": "China", "country_code": "CN", "country_code_iso3": "CHN", "country_capital": "Beijing", "country_tld": ".cn", "continent_code": "AS", "in_eu": false, "postal": null, "latitude": 23.1181, "longitude": 113.2539, "timezone": "Asia/Shanghai", "utc_offset": "+0800", "country_calling_code": "+86", "currency": "CNY", "currency_name": "Yuan Renminbi", "languages": "zh-CN,yue,wuu,dta,ug,za", "country_area": 9596960.0, "country_population": 1411778724, "asn": "AS4134", "org": "Chinanet" }19. GET.GEOJS.IO 查询接口请求地址https://get.geojs.io/v1/ip/geo/121.8.215.106.json请求方法GET返回数据格式{ "country_code3": "CHN", "continent_code": "AS", "region": "Guangdong", "latitude": "23.1181", "longitude": "113.2539", "accuracy": 20, "organization_name": "Chinanet", "timezone": "Asia/Shanghai", "asn": 4134, "organization": "AS4134 Chinanet", "city": "Guangzhou", "ip": "121.8.215.106", "area_code": "0", "country": "China", "country_code": "CN" }结语通过上述多个接口的对比和使用,开发者可以根据自身需求选择最适合的API进行IP地址查询。无论是获取详细的地理位置信息,还是简单的城市级别定位,这些接口都能提供丰富的支持。
2025年01月26日
156 阅读
0 评论
0 点赞
2024-11-11
Java面试一
面试概况本次面试为快手商业化部门日常实习生的一轮面试,面试时长约为40分钟。面试内容主要集中在Java基础知识、数据库、并发编程、算法等方面。以下是详细的面试问题及回答整理。面试问题及回答1. Java 的集合类知道哪些?Java 的集合类主要分为以下几类:List:有序集合,允许重复元素。常见实现类有 ArrayList、LinkedList、Vector。Set:不允许重复元素的集合。常见实现类有 HashSet、LinkedHashSet、TreeSet。Map:键值对集合,键唯一但值可以重复。常见实现类有 HashMap、LinkedHashMap、TreeMap、Hashtable、ConcurrentHashMap。Queue:队列集合,支持 FIFO(先进先出)操作。常见实现类有 LinkedList、PriorityQueue、ArrayDeque。2. 说说 HashMap?HashMap 是 Java 中常用的集合类,基于哈希表实现,允许存储键值对。其主要特点如下:无序存储:HashMap 不保证元素的顺序。允许空键和空值:但最多只能有一个空键。线程不安全:在多线程环境下使用 HashMap 可能会导致数据不一致。时间复杂度:插入、删除、查找操作的时间复杂度均为 O(1)(理想情况下)。3. HashMap 线程安全吗,如何变线程安全?HashMap 本身是线程不安全的。可以通过以下几种方式使其线程安全:使用 Collections.synchronizedMap:将 HashMap 包装成线程安全的 Map。Map<String, String> map = Collections.synchronizedMap(new HashMap<>());使用 ConcurrentHashMap:ConcurrentHashMap 是线程安全的 Map 实现,性能优于 Hashtable。Map<String, String> map = new ConcurrentHashMap<>();手动同步:在访问 HashMap 的地方手动加锁。synchronized (map) { map.put(key, value); }4. ConcurrentHashMap 如何实现的?ConcurrentHashMap 通过分段锁(Segment)机制实现线程安全。具体实现如下:分段锁:将整个哈希表分成多个段(Segment),每个段内部是一个小的哈希表。锁粒度:每次操作只锁定当前段,而不是整个哈希表,提高了并发性能。JDK 1.8 改进:取消了 Segment,改为使用 CAS 操作和锁竞争机制,进一步提高了性能。5. synchronized 原理以及升级过程synchronized 是 Java 中的内置锁,用于实现线程同步。其原理如下:锁的状态:锁有四种状态,依次是无锁状态、偏向锁状态、轻量级锁状态和重量级锁状态。锁升级:锁可以从较低状态升级到较高状态,但不能降级。无锁状态:没有任何线程持有锁。偏向锁:偏向于第一个获取锁的线程,减少锁的竞争。轻量级锁:使用 CAS 操作尝试获取锁,如果失败则升级为重量级锁。重量级锁:使用操作系统互斥量实现,性能较差。6. 线程池的参数?ThreadPoolExecutor 是 Java 中创建线程池的类,其构造方法参数如下:corePoolSize:核心线程数。maximumPoolSize:最大线程数。keepAliveTime:线程空闲时间。unit:keepAliveTime 的时间单位。workQueue:任务队列,用于存储等待执行的任务。threadFactory:线程工厂,用于创建线程。handler:拒绝策略,当任务队列满且线程数达到最大值时的处理策略。7. full gc, minor gc?Minor GC:回收年轻代(Young Generation)的垃圾收集操作。当年轻代空间不足时触发。Full GC:回收整个堆(包括年轻代和老年代)的垃圾收集操作。通常在以下情况下触发:老年代空间不足。系统显式调用 System.gc()。Minor GC 时发现老年代空间不足。8. 垃圾回收算法?常见的垃圾回收算法有:标记-清除:标记所有需要回收的对象,然后清除这些对象。标记-整理:标记所有需要回收的对象,然后将存活对象移动到一端,清除边界外的对象。复制:将内存分为两个区域,每次只使用其中一个区域,将存活对象复制到另一个区域。分代收集:将内存分为年轻代和老年代,分别使用不同的回收算法。9. CPU 密集型和 IO 密集型下如何设置核心线程数?CPU 密集型:任务主要消耗 CPU 资源,核心线程数一般设置为 CPU 核心数 + 1。int corePoolSize = Runtime.getRuntime().availableProcessors() + 1;IO 密集型:任务主要消耗 I/O 资源,核心线程数一般设置为 CPU 核心数 * 2。int corePoolSize = Runtime.getRuntime().availableProcessors() * 2;10. 聚簇索引和非聚簇索引区别聚簇索引:数据行的物理存储顺序与索引顺序一致。一个表只能有一个聚簇索引。查询速度快,但插入、删除、更新操作较慢。非聚簇索引:数据行的物理存储顺序与索引顺序无关。一个表可以有多个非聚簇索引。查询速度相对较慢,但插入、删除、更新操作较快。11. MySQL 的各个隔离级别,以及分别解决了什么问题MySQL 的事务隔离级别有四种:读未提交(Read Uncommitted):最低隔离级别,允许脏读。读已提交(Read Committed):允许不可重复读,但不允许脏读。可重复读(Repeatable Read):默认隔离级别,允许幻读,但不允许脏读和不可重复读。串行化(Serializable):最高隔离级别,不允许脏读、不可重复读和幻读。12. Redis 有什么数据类型Redis 支持多种数据类型:字符串(String):最基本的类型,可以存储字符串、数字等。列表(List):有序集合,支持从两端插入和删除操作。集合(Set):无序集合,不允许重复元素。有序集合(Sorted Set):有序集合,每个元素关联一个分数。哈希表(Hash):键值对集合,键唯一。位图(Bitmap):用于处理位级别的操作。HyperLogLog:用于估算集合的基数。13. Redis 分布式锁实现?Redis 分布式锁可以通过以下几种方式实现:SETNX 命令:使用 SETNX 命令尝试获取锁。SETNX key valueEXPIRE 命令:设置锁的超时时间,防止死锁。EXPIRE key secondsLua 脚本:使用 Lua 脚本保证原子性。local key = KEYS[1] local value = ARGV[1] local expire = tonumber(ARGV[2]) if redis.call("setnx", key, value) == 1 then redis.call("expire", key, expire) return 1 else return 0 end14. 项目中的前缀树,自定义注解限频,网站优化过程前缀树(Trie):用于快速查找字符串,常用于搜索引擎、拼写检查等。自定义注解限频:通过自定义注解和 AOP 切面实现接口限流。@Retention(RetentionPolicy.RUNTIME) @Target(ElementType.METHOD) public @interface RateLimit { int limit() default 100; int time() default 1; } @Aspect @Component public class RateLimitAspect { @Around("@annotation(rateLimit)") public Object around(ProceedingJoinPoint joinPoint, RateLimit rateLimit) throws Throwable { // 限流逻辑 return joinPoint.proceed(); } }网站优化过程:前端优化:使用 CDN、压缩资源、合并文件、懒加载等。后端优化:优化数据库查询、使用缓存、减少网络请求等。服务器优化:调整 JVM 参数、优化网络配置、使用负载均衡等。15. 算法:反转链表反转链表的实现如下:public ListNode reverseList(ListNode head) { ListNode prev = null; ListNode current = head; while (current != null) { ListNode next = current.next; current.next = prev; prev = current; current = next; } return prev; }总结本次面试涉及的知识点较为广泛,涵盖了 Java 基础、并发编程、数据库、算法等多个方面。准备面试时,建议重点复习这些知识点,并结合实际项目经验进行准备。希望这篇博客对大家有所帮助!
2024年11月11日
26 阅读
0 评论
0 点赞
2024-05-10
python发送邮件代码
import ssl import smtplib from email.utils import formataddr from email.header import Header from email.mime.text import MIMEText from email.mime.multipart import MIMEMultipart def send_email(to_user, subject, content): # 创建一个MIMEMultipart对象,用于组合邮件头部和正文 mail_username='notify@example.com' mail_password='xxxxxxxxxx' smtp_server = "smtp.test.com" message = MIMEMultipart() message['From'] = formataddr(pair=('MX-Notify', mail_username)) message['To'] = to_user message['Subject'] = Header(subject, 'utf-8') # 标题 # 创建邮件正文 # text = f""" # {content} # It can be in HTML or plain text. # """ html = f""" <html> <body> <p>{content}</p> </body> </html> """ # 添加正文到邮件对象中 # message.attach(MIMEText(text, "plain")) message.attach(MIMEText(html, "html")) # 添加邮件正文 # 设置SMTP服务器和端口 smtp_server = smtp_server port = 465 # 假设使用的是SSL,如果是TLS,通常使用587 server = None # 先初始化为None try: # 创建SMTP SSL连接 context = ssl.create_default_context() context.check_hostname = False context.verify_mode = ssl.CERT_NONE server = smtplib.SMTP_SSL(smtp_server, port, context=context) # 非SSL,如果为SSL则看下面 # server = smtplib.SMTP(smtp_server) # 如果是ssl,需要加多一个端口号映射 # server = smtplib.SMTP_SSL() # server.connect(smtp_server,port,context) # 登录邮箱 server.login(mail_username, mail_password) # 发送邮件 server.sendmail(mail_username, recipient, message.as_string()) print("邮件发送成功") except Exception as e: print(f"邮件发送失败:{e}") finally: # 关闭SMTP连接 if server is not None: server.quit() # 使用示例 try: has_msg = check_fun(check_url) send_email("touser@qq.com", '检测PT开注', "这是一封测试邮件。") except Exception as e: print(f"发生错误:{e}")
2024年05月10日
65 阅读
0 评论
0 点赞
2023-10-31
【MacOS】安装JDK并配置环境变量
JAVA_HOME=/Library/Java/JavaVirtualMachines/jdk1.8.0_241.jdk/Contents/Home PATH=$JAVA_HOME/bin:$PATH //给环境变量赋值 export JAVA_HOME //导出使其生效 export PATH 参考链接:https://blog.csdn.net/m0_51520179/article/details/131295356
2023年10月31日
53 阅读
0 评论
0 点赞
1
2
...
14
您的IP: