geoip-lite2 2.2.7 → 2.2.8-beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +7 -16
- package/data/city.checksum +1 -1
- package/data/country.checksum +1 -1
- package/data/geoip-city-names.dat +0 -0
- package/data/geoip-city.dat +0 -0
- package/data/geoip-city6.dat +0 -0
- package/data/geoip-country.dat +0 -0
- package/data/geoip-country6.dat +0 -0
- package/dist/main.js +1 -1
- package/dist/utils.js +1 -1
- package/package.json +5 -5
package/README.md
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
<br>
|
|
6
6
|
<p>
|
|
7
7
|
A native <a href="https://nodejs.org" target="_blank" title="Open nodejs.org">Node.js</a> API for the GeoLite data from MaxMind.<br>
|
|
8
|
-
This
|
|
8
|
+
This library includes GeoLite data created by MaxMind, available from <a href="https://www.maxmind.com" target="_blank" title="Open www.maxmind.com">maxmind.com</a>.
|
|
9
9
|
</p>
|
|
10
10
|
<a href="https://www.npmjs.com/package/geoip-lite2" target="_blank" title="geoip-lite2 - npm" style="text-decoration:none">
|
|
11
11
|
<img src="https://img.shields.io/npm/dt/geoip-lite2?maxAge=3600" alt="The number of downloads">
|
|
@@ -18,26 +18,18 @@
|
|
|
18
18
|
|
|
19
19
|
|
|
20
20
|
# 🚀 Improved GeoIP Module by [Sefinek](https://sefinek.net)
|
|
21
|
-
This module is an
|
|
21
|
+
This module is an optimized version of [geoip-lite](https://github.com/geoip-lite/node-geoip) and runs slightly faster.
|
|
22
|
+
The project has been migrated to the [Jest](https://www.npmjs.com/package/jest) testing library.
|
|
22
23
|
|
|
23
|
-
|
|
24
|
-
The module now runs even faster, thanks to file minification!
|
|
25
|
-
|
|
26
|
-
Furthermore, the testing process has been improved with the adoption of the [Jest](https://www.npmjs.com/package/jest) testing library.
|
|
27
|
-
|
|
28
|
-
> I am not the primary creator of this! All copyright rights belong to the original [authors](AUTHORS).
|
|
24
|
+
> I am not the primary creator of this project! All copyright rights belong to the original [authors](AUTHORS).
|
|
29
25
|
|
|
30
26
|
|
|
31
27
|
## ⚠️ Important
|
|
32
|
-
Remember to regularly update the
|
|
33
|
-
|
|
28
|
+
Remember to regularly update the MaxMind database. You'll need the token for this.
|
|
34
29
|
|
|
35
|
-
## 🌠 Version without a Local Database
|
|
36
|
-
This module requires a significant amount of RAM because geolocation data is stored in memory.
|
|
37
|
-
However, you can always opt for the official alternative, the [geoip2-api](https://www.npmjs.com/package/geoip2-api) module, which sends requests to an API server and retrieves information about specific IP addresses directly from there.
|
|
38
30
|
|
|
39
|
-
|
|
40
|
-
You can see this module in action using my [official API](https://api.sefinek.net). The
|
|
31
|
+
## ✨ API
|
|
32
|
+
You can see this module in action using my [official API](https://api.sefinek.net). The `/api/v2/geoip` endpoint should not be used in production environments.
|
|
41
33
|
|
|
42
34
|
- Specific IP: https://api.sefinek.net/api/v2/geoip/109.207.159.255
|
|
43
35
|
- Client's IP: https://api.sefinek.net/api/v2/geoip/me
|
|
@@ -259,7 +251,6 @@ console.log(process.memoryUsage());
|
|
|
259
251
|
|
|
260
252
|
## 👥 Copyright
|
|
261
253
|
`GeoIP-Lite` is Copyright 2011-2018 **Philip Tellis** <philip@bluesmoon.info>
|
|
262
|
-
`GeoIP-Lite2` is Copyright 2023-2024 **Sefinek** <contact@sefinek.net> (https://sefinek.net)
|
|
263
254
|
|
|
264
255
|
|
|
265
256
|
## 🔐 License
|
package/data/city.checksum
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
43cd254f51bc2e181c37b82bc3e575d702fb80e47403415369588585ee012abf GeoLite2-City-CSV_20251104.zip
|
package/data/country.checksum
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
55f23aac3290cee0cc46ea41d02c8f063357aad8446163065ea6743517b42513 GeoLite2-Country-CSV_20251104.zip
|
|
Binary file
|
package/data/geoip-city.dat
CHANGED
|
Binary file
|
package/data/geoip-city6.dat
CHANGED
|
Binary file
|
package/data/geoip-country.dat
CHANGED
|
Binary file
|
package/data/geoip-country6.dat
CHANGED
|
Binary file
|
package/dist/main.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
const{open:e,fstat:
|
|
1
|
+
const{open:e,fstat:t,read:r,close:n,openSync:i,fstatSync:o,readSync:a,closeSync:l}=require('node:fs'),{join:f,resolve:u}=require('node:path'),{isIP:c}=require('node:net'),s=require('async'),{aton4:d,aton6:B,cmp6:y,ntoa4:I,ntoa6:E,cmp:g}=require('./utils.js'),m=require('./fsWatcher.js'),{version:S}=require('../package.json'),z='dataWatcher',p=u(__dirname,global.geoDataDir||process.env.GEODATADIR||'../data/'),P={city:f(p,'geoip-city.dat'),city6:f(p,'geoip-city6.dat'),cityNames:f(p,'geoip-city-names.dat'),country:f(p,'geoip-country.dat'),country6:f(p,'geoip-country6.dat')},h=[[d('10.0.0.0'),d('10.255.255.255')],[d('172.16.0.0'),d('172.31.255.255')],[d('192.168.0.0'),d('192.168.255.255')]],F={firstIP:null,lastIP:null,lastLine:0,locationBuffer:null,locationRecordSize:88,mainBuffer:null,recordSize:24},L={firstIP:null,lastIP:null,lastLine:0,mainBuffer:null,recordSize:48};let U={...F},D={...L};const N=e=>{const t=e.indexOf('\0');return-1===t?e:e.substring(0,t)},T=(e,t,r,n)=>{const i=[];for(let o=0;o<2;o++)i.push(e.readUInt32BE(t*r+16*n+4*o));return i},w=e=>{let t,r,n=0,i=U.lastLine,o=U.lastIP,a=U.firstIP;const l=U.mainBuffer,f=U.locationBuffer,u=h,c=U.recordSize,s=U.locationRecordSize,d={range:[null,null],country:'',region:'',eu:'',timezone:'',city:'',ll:[null,null],metro:null,area:null};if(e>U.lastIP||e<U.firstIP)return null;for(let t=0;t<u.length;t++)if(e>=u[t][0]&&e<=u[t][1])return null;for(;;){t=Math.round((i-n)/2)+n;const u=t*c;if(o=l.readUInt32BE(u),a=l.readUInt32BE(u+4),o<=e&&a>=e){if(d.range=[o,a],10===c)d.country=l.toString('utf8',u+8,u+10);else if(r=l.readUInt32BE(u+8),-1>>>0>r){const e=r*s;d.country=N(f.toString('utf8',e,e+2)),d.region=N(f.toString('utf8',e+2,e+5)),d.metro=f.readInt32BE(e+5),d.ll[0]=l.readInt32BE(u+12)/1e4,d.ll[1]=l.readInt32BE(u+16)/1e4,d.area=l.readUInt32BE(u+20),d.eu=N(f.toString('utf8',e+9,e+10)),d.timezone=N(f.toString('utf8',e+10,e+42)),d.city=N(f.toString('utf8',e+42,e+s))}return d}if(n===i)return null;n===i-1?t===n?n=i:i=n:o>e?i=t:a<e&&(n=t)}},A=['0:0:0:0:0:FFFF:','::FFFF:'];function q(f){let u,c;const d={...F};if('function'==typeof arguments[0])s.series([i=>{s.series([t=>{e(P.cityNames,'r',(e,r)=>{u=r,t(e)})},e=>{t(u,(t,r)=>{c=r.size,d.locationBuffer=Buffer.alloc(c),e(t)})},e=>{r(u,d.locationBuffer,0,c,0,e)},e=>{n(u,e)},t=>{e(P.city,'r',(e,r)=>{u=r,t(e)})},e=>{t(u,(t,r)=>{c=r.size,e(t)})}],r=>{if(r){if('ENOENT'!==r.code&&'EBADF'!==r.code)throw r;e(P.country,'r',(e,r)=>{e?i(e):(u=r,t(u,(e,t)=>{c=t.size,d.recordSize=10,i()}))})}else i()})},()=>{d.mainBuffer=Buffer.alloc(c),s.series([e=>{r(u,d.mainBuffer,0,c,0,e)},e=>{n(u,e)}],e=>{e||(d.lastLine=c/d.recordSize-1,d.lastIP=d.mainBuffer.readUInt32BE(d.lastLine*d.recordSize+4),d.firstIP=d.mainBuffer.readUInt32BE(0),U=d),f(e)})}]);else{try{if(u=i(P.cityNames,'r'),c=o(u).size,0===c)throw{code:'EMPTY_FILE'};U.locationBuffer=Buffer.alloc(c),a(u,U.locationBuffer,0,c,0),l(u),u=i(P.city,'r'),c=o(u).size}catch(e){if('ENOENT'!==e.code&&'EBADF'!==e.code&&'EMPTY_FILE'!==e.code)throw e;u=i(P.country,'r'),c=o(u).size,U.recordSize=10}U.mainBuffer=Buffer.alloc(c),a(u,U.mainBuffer,0,c,0),l(u),U.lastLine=c/U.recordSize-1,U.lastIP=U.mainBuffer.readUInt32BE(U.lastLine*U.recordSize+4),U.firstIP=U.mainBuffer.readUInt32BE(0)}}function O(f){let u,c;const d={...L};if('function'==typeof arguments[0])s.series([r=>{s.series([t=>{e(P.city6,'r',(e,r)=>{u=r,t(e)})},e=>{t(u,(t,r)=>{c=r.size,e(t)})}],n=>{if(n){if('ENOENT'!==n.code&&'EBADF'!==n.code)throw n;e(P.country6,'r',(e,n)=>{e?r(e):(u=n,t(u,(e,t)=>{c=t.size,d.recordSize=34,r()}))})}else r()})},()=>{d.mainBuffer=Buffer.alloc(c),s.series([e=>{r(u,d.mainBuffer,0,c,0,e)},e=>{n(u,e)}],e=>{e||(d.lastLine=c/d.recordSize-1,D=d),f(e)})}]);else{try{if(u=i(P.city6,'r'),c=o(u).size,0===c)throw{code:'EMPTY_FILE'}}catch(e){if('ENOENT'!==e.code&&'EBADF'!==e.code&&'EMPTY_FILE'!==e.code)throw e;u=i(P.country6,'r'),c=o(u).size,D.recordSize=34}D.mainBuffer=Buffer.alloc(c),a(u,D.mainBuffer,0,c,0),l(u),D.lastLine=c/D.recordSize-1}}module.exports={cmp:g,lookup:e=>{if(!e)return null;if('number'==typeof e)return w(e);if(4===c(e))return w(d(e));if(6===c(e)){const t=(e=>{const t=e.toUpperCase();for(let e=0;e<A.length;e++){const r=A[e];if(0===t.indexOf(r))return t.substring(r.length)}return null})(e);return t?w(d(t)):(e=>{const t=D.mainBuffer,r=D.recordSize,n=U.locationBuffer,i=U.locationRecordSize,o={range:[null,null],country:'',region:'',city:'',ll:[0,0],metro:null,area:null,eu:'',timezone:''};D.lastIP=T(t,D.lastLine,r,1),D.firstIP=T(t,0,r,0);let a,l,f=0,u=D.lastLine,c=D.lastIP,s=D.firstIP;if(y(e,D.lastIP)>0||y(e,D.firstIP)<0)return null;for(;;){if(a=Math.round((u-f)/2)+f,c=T(t,a,r,0),s=T(t,a,r,1),y(c,e)<=0&&y(s,e)>=0){const e=a*r;if(34===r)o.country=N(t.toString('utf8',e+32,e+34));else if(l=t.readUInt32BE(e+32),-1>>>0>l){const r=l*i;o.country=N(n.toString('utf8',r,r+2)),o.region=N(n.toString('utf8',r+2,r+5)),o.metro=n.readInt32BE(r+5),o.ll[0]=t.readInt32BE(e+36)/1e4,o.ll[1]=t.readInt32BE(e+40)/1e4,o.area=t.readUInt32BE(e+44),o.eu=N(n.toString('utf8',r+9,r+10)),o.timezone=N(n.toString('utf8',r+10,r+42)),o.city=N(n.toString('utf8',r+42,r+i))}return o}if(f===u)return null;f===u-1?a===f?f=u:u=f:y(c,e)>0?u=a:y(s,e)<0&&(f=a)}})(B(e))}return null},pretty:e=>'string'==typeof e?e:'number'==typeof e?I(e):Array.isArray(e)?E(e):e,startWatchingDataUpdate:e=>{m.makeFsWatchFilter(z,p,6e4,async()=>{await s.series([e=>{q(e)},e=>{O(e)}],e)})},stopWatchingDataUpdate:()=>m.stopWatching(z),clear:()=>{U={...F},D={...L}},reloadDataSync:()=>{q(),O()},reloadData:async e=>{await s.series([e=>{q(e)},e=>{O(e)}],e)},version:S},q(),O();
|
package/dist/utils.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
const t=module.exports={};t.aton4=t=>
|
|
1
|
+
const t=module.exports={};t.aton4=t=>{const r=t.split('.');return(parseInt(r[0],10)<<24>>>0)+(parseInt(r[1],10)<<16>>>0)+(parseInt(r[2],10)<<8>>>0)+(parseInt(r[3],10)>>>0)},t.aton6=t=>{const r=(t=t.replace(/"/g,'').split(':')).length-1;let e;if(''===t[r]&&(t[r]=0),r<7)for(t.length=8,e=r;e>=0&&''!==t[e];e--)t[7-r+e]=t[e];for(e=0;e<8;e++)t[e]?t[e]=parseInt(t[e],16):t[e]=0;const n=[];for(e=0;e<4;e++)n.push((t[2*e]<<16)+t[2*e+1]>>>0);return n},t.cmp=(t,r)=>'number'==typeof t&&'number'==typeof r?t<r?-1:t>r?1:0:t instanceof Array&&r instanceof Array?this.cmp6(t,r):null,t.cmp6=(t,r)=>{for(let e=0;e<2;e++){if(t[e]<r[e])return-1;if(t[e]>r[e])return 1}return 0},t.isPrivateIP=t=>{const r=t.toString();return r.startsWith('10.')||r.startsWith('192.168.')||r.startsWith('172.16.')||r.startsWith('127.')||r.startsWith('169.254.')||r.startsWith('fc00:')||r.startsWith('fe80:')},t.ntoa4=t=>((t=t.toString())>>>24&255)+'.'+(t>>>16&255)+'.'+(t>>>8&255)+'.'+(255&t),t.ntoa6=t=>{let r='[';for(let e=0;e<t.length;e++)r+=(t[e]>>>16).toString(16)+':',r+=(65535&t[e]).toString(16)+':';return r=r.replace(/:$/,']').replace(/:0+/g,':').replace(/::+/,'::'),r};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "geoip-lite2",
|
|
3
|
-
"version": "2.2.
|
|
3
|
+
"version": "2.2.8-beta.1",
|
|
4
4
|
"description": "A light weight native JavaScript implementation of GeoIP API from MaxMind. Improved and faster version by Sefinek.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"city",
|
|
@@ -80,12 +80,12 @@
|
|
|
80
80
|
"async": "^3.2.6",
|
|
81
81
|
"iconv-lite": "0.7.0",
|
|
82
82
|
"ip-address": "^10.0.1",
|
|
83
|
-
"rimraf": "^6.0
|
|
83
|
+
"rimraf": "^6.1.0"
|
|
84
84
|
},
|
|
85
85
|
"devDependencies": {
|
|
86
|
-
"@eslint/js": "^9.
|
|
87
|
-
"globals": "^16.
|
|
88
|
-
"jest": "^30.
|
|
86
|
+
"@eslint/js": "^9.39.1",
|
|
87
|
+
"globals": "^16.5.0",
|
|
88
|
+
"jest": "^30.2.0",
|
|
89
89
|
"terser": "^5.44.0"
|
|
90
90
|
},
|
|
91
91
|
"engines": {
|