geoip-lite2 2.1.4 → 2.1.6

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 CHANGED
@@ -68,7 +68,7 @@ a Macbook Pro. IPv4 addresses take about 6 microseconds, while IPv6 addresses ta
68
68
  ```javascript
69
69
  const geoIp2 = require('geoip-lite2');
70
70
 
71
- const ip = '207.97.227.239';
71
+ const ip = '146.19.109.255';
72
72
  const geo = geoIp2.lookup(ip);
73
73
 
74
74
  console.log(geo);
@@ -77,15 +77,15 @@ console.log(geo);
77
77
  ### Output
78
78
  ```json
79
79
  {
80
- "range": [ 3479298048, 3479300095 ],
81
- "country": "US",
82
- "region": "TX",
83
- "eu": "0",
84
- "timezone": "America/Chicago",
85
- "city": "San Antonio",
86
- "ll": [ 29.4969, -98.4032 ],
87
- "metro": 641,
88
- "area": 1000
80
+ "range": [ 2450746624, 2450746879 ],
81
+ "country": "PL",
82
+ "region": "14",
83
+ "eu": "1",
84
+ "timezone": "Europe/Warsaw",
85
+ "city": "Warsaw",
86
+ "ll": [ 52.2296, 21.0067 ],
87
+ "metro": 0,
88
+ "area": 20
89
89
  }
90
90
  ```
91
91
 
@@ -135,7 +135,7 @@ If the IP address was found, the `lookup` method returns an object with the foll
135
135
  // FIPS 10-4 subcountry code
136
136
  eu: '0', // 1 if the country is a member state of the European Union, 0 otherwise.
137
137
  timezone: 'Country/Zone', // Timezone from IANA Time Zone Database
138
- city: "City Name", // This is the full city name
138
+ city: 'City Name', // This is the full city name
139
139
  ll: [<latitude>, <longitude>], // The latitude and longitude of the city
140
140
  metro: <metro code>, // Metro code
141
141
  area: <accuracy_radius> // The approximate accuracy radius (km), around the latitude and longitude
@@ -152,7 +152,7 @@ If you have a 32-bit unsigned integer, or a number returned as part of the `rang
152
152
  the `pretty` method can be used to turn it into a human-readable string.
153
153
 
154
154
  ```javascript
155
- console.log('The IP is %s', geoip.pretty(ip));
155
+ console.log('The IP is %s', geoIp2.pretty(ip));
156
156
  ```
157
157
 
158
158
  This method returns a string if the input was in a format that `geoip-lite2` can recognise, else it returns the
@@ -191,10 +191,10 @@ You can do it programmatically, calling after scheduled data updates
191
191
 
192
192
  ```javascript
193
193
  // Synchronously
194
- geoip.reloadDataSync();
194
+ geoIp2.reloadDataSync();
195
195
 
196
196
  // Asynchronously
197
- geoip.reloadData(() => {
197
+ geoIp2.reloadData(() => {
198
198
  console.log('Done');
199
199
  });
200
200
  ```
@@ -203,7 +203,7 @@ geoip.reloadData(() => {
203
203
  You can enable the data watcher to automatically refresh in-memory geo data when a file changes in the data directory.
204
204
 
205
205
  ```javascript
206
- geoip.startWatchingDataUpdate();
206
+ geoIp2.startWatchingDataUpdate();
207
207
  ```
208
208
 
209
209
  This tool can be used with `npm run updatedb` to periodically update geo data on a running server.
@@ -224,7 +224,7 @@ cost though, and you make it up at run time with very fast lookups.
224
224
  Quick test on memory consumption shows that library uses around 100Mb per process.
225
225
 
226
226
  ```javascript
227
- const geoip2 = require('geoip-lite2');
227
+ const geoIp2 = require('geoip-lite2');
228
228
  console.log(process.memoryUsage());
229
229
 
230
230
  /**
@@ -1 +1 @@
1
- b1aa2b8de1afdead4f9c01f9101569bd4a7ae8a5efc760977b0156e216902639 GeoLite2-City-CSV_20230908.zip
1
+ 5cb8483a585354b99dd0edf0f2fde41de392c4671c98cc51f782263adbc147e1 GeoLite2-City-CSV_20230912.zip
@@ -1 +1 @@
1
- 5c009987b9dcc6f71f46f8d1d825ccd8bed11fffdf05b14bf5509289c189aa53 GeoLite2-Country-CSV_20230908.zip
1
+ 926fd3b7a33234806141df355e34713229de458e56cdfb6f5b2881ddaca4ea32 GeoLite2-Country-CSV_20230912.zip
Binary file
Binary file
Binary file
Binary file
Binary file
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "geoip-lite2",
3
- "version": "2.1.4",
3
+ "version": "2.1.6",
4
4
  "description": "A light weight native JavaScript implementation of GeoIP API from MaxMind.",
5
5
  "keywords": [
6
6
  "city",
@@ -34,9 +34,7 @@
34
34
  "types": "index.d.ts",
35
35
  "directories": {
36
36
  "lib": "lib",
37
- "test": "test",
38
- "data": "data",
39
- "utils": "utils"
37
+ "test": "test"
40
38
  },
41
39
  "files": [
42
40
  "data/",
@@ -50,13 +48,14 @@
50
48
  ],
51
49
  "scripts": {
52
50
  "eslint": "eslint .",
53
- "minify-linux": "echo \"Not finished yet >:\"",
51
+ "minify-linux": "echo \"Please wait...\n\" && bash _Minify/linux.bash",
54
52
  "minify-win": "powershell.exe -ExecutionPolicy Bypass .\\_Minify\\windows.ps1",
55
- "test": "mocha test/main.js",
53
+ "test": "jest test",
56
54
  "up": "ncu -u -x chalk && npm install && npm update && npm audit fix",
57
55
  "updatedb": "node utils/updatedb.js",
58
56
  "updatedb-debug": "node utils/updatedb.js debug",
59
- "updatedb-force": "node utils/updatedb.js force"
57
+ "updatedb-force": "node utils/updatedb.js force",
58
+ "version": "node test/version.js"
60
59
  },
61
60
  "dependencies": {
62
61
  "adm-zip": "^0.5.10",
@@ -69,7 +68,7 @@
69
68
  },
70
69
  "devDependencies": {
71
70
  "eslint": "^8.49.0",
72
- "mocha": "^10.2.0",
71
+ "jest": "^29.7.0",
73
72
  "terser": "^5.19.4"
74
73
  },
75
74
  "engines": {
@@ -0,0 +1 @@
1
+ const e=require('../lib/geoip.js');describe('GeoIP2',(()=>{describe('#testLookup()',(()=>{it('should return data about IPv4',(()=>{const t=e.lookup('1.1.1.1');expect(t).toBeTruthy()})),it('should return data about IPv6',(()=>{const t=e.lookup('2606:4700:4700::64');expect(t).toBeTruthy()}))})),describe('#testDataIP4()',(()=>{it('should match data for IPv4 - US',(()=>{const t=e.lookup('72.229.28.185');expect(void 0!==t.range).toBe(!0),expect(t.country).toBe('US'),expect(t.region).toBe('NY'),expect(t.eu).toBe('0'),expect(t.timezone).toBe('America/New_York'),expect(t.city).toBe('New York'),expect(t.ll).toBeTruthy(),expect(t.metro).toBe(501),expect(t.area).toBe(5)})),it('should match data for IPv4 - JP',(()=>{const t=e.lookup('210.138.184.59');expect(void 0!==t.range).toBe(!0),expect(t.country).toBe('JP'),expect(t.region).toBe(''),expect(t.eu).toBe('0'),expect(t.timezone).toBe('Asia/Tokyo'),expect(t.city).toBe(''),expect(t.ll).toBeTruthy(),expect(t.metro).toBe(0),expect(t.area).toBe(200)})),it('should match data for IPv4 - PL',(()=>{const t=e.lookup('104.113.255.255');expect(void 0!==t.range).toBe(!0),expect(t.country).toBe('PL'),expect(t.region).toBe('14'),expect(t.eu).toBe('1'),expect(t.timezone).toBe('Europe/Warsaw'),expect(t.city).toBe('Warsaw'),expect(t.ll).toBeTruthy(),expect(t.metro).toBe(0),expect(t.area).toBe(20)})),it('should match data for IPv4 - RU',(()=>{const t=e.lookup('109.108.63.255');expect(void 0!==t.range).toBe(!0),expect(t.country).toBe('RU'),expect(t.region).toBe('IVA'),expect(t.eu).toBe('0'),expect(t.timezone).toBe('Europe/Moscow'),expect(t.city).toBe('Kineshma'),expect(t.ll).toBeTruthy(),expect(t.metro).toBe(0),expect(t.area).toBe(200)}))})),describe('#testDataIP6()',(()=>{it('should match data for IPv6',(()=>{const t=e.lookup('2001:1c04:400::1');expect(void 0!==t.range).toBe(!0),expect(t.country).toBe('NL'),expect(t.region).toBe('NH'),expect(t.eu).toBe('1'),expect(t.timezone).toBe('Europe/Amsterdam'),expect(t.city).toBe('Zandvoort'),expect(t.ll).toBeTruthy(),expect(t.metro).toBe(0),expect(t.area).toBe(5)})),it('should match data for IPv4 - JP',(()=>{const t=e.lookup('2400:8500:1302:814:a163:44:173:238f');expect(void 0!==t.range).toBe(!0),expect(t.country).toBe('JP'),expect(t.region).toBe(''),expect(t.eu).toBe('0'),expect(t.timezone).toBe('Asia/Tokyo'),expect(t.city).toBe(''),expect(t.ll).toBeTruthy(),expect(t.metro).toBe(0),expect(t.area).toBe(500)})),it('should match data for IPv4 - JP',(()=>{const t=e.lookup('1.79.255.115');expect(void 0!==t.range).toBe(!0),expect(t.country).toBe('JP'),expect(t.region).toBe(''),expect(t.eu).toBe('0'),expect(t.timezone).toBe('Asia/Tokyo'),expect(t.city).toBe(''),expect(t.ll).toBeTruthy(),expect(t.metro).toBe(0),expect(t.area).toBe(500)}))})),describe('#testUTF8()',(()=>{it('should return UTF8 city name',(()=>{const t=e.lookup('2.139.175.1');expect(t).toBeTruthy(),expect(t.city).toBe('Barbera Del Valles')}))})),describe('#testMetro()',(()=>{it('should match metro data',(()=>{const t=e.lookup('23.240.63.68');expect(t.metro).toBe(803)}))})),describe('#testIPv4MappedIPv6()',(()=>{it('should match IPv4 mapped IPv6 data',(()=>{const t=e.lookup('195.16.170.74');expect(t.metro).toBe(0)}))})),describe('#testSyncReload()',(()=>{it('should reload data synchronously',(()=>{const t=e.lookup('75.82.117.180');expect(t).not.toBeNull();const o=e.lookup('::ffff:173.185.182.82');expect(o).not.toBeNull(),e.clear();const c=e.lookup('75.82.117.180');expect(c).toBeNull();const l=e.lookup('::ffff:173.185.182.82');expect(l).toBeNull(),e.reloadDataSync();const p=e.lookup('75.82.117.180');expect(t).toEqual(p);const r=e.lookup('::ffff:173.185.182.82');expect(o).toEqual(r)}))})),describe('#testAsyncReload()',(()=>{it('should reload data asynchronously',(t=>{const o=e.lookup('75.82.117.180');expect(o).not.toBeNull();const c=e.lookup('::ffff:173.185.182.82');expect(c).not.toBeNull(),e.clear();const l=e.lookup('75.82.117.180');expect(l).toBeNull();const p=e.lookup('::ffff:173.185.182.82');expect(p).toBeNull(),e.reloadData((()=>{const l=e.lookup('75.82.117.180');expect(o).toEqual(l);const p=e.lookup('::ffff:173.185.182.82');expect(c).toEqual(p),t()}))}))})),describe('#testInvalidIP()',(()=>{it('should return null for an invalid IP address',(()=>{const t=e.lookup('invalid_ip_address');expect(t).toBeNull()}))})),describe('#testEmptyIP()',(()=>{it('should return null for an empty IP address',(()=>{const t=e.lookup('');expect(t).toBeNull()}))})),describe('#testNullIP()',(()=>{it('should return null for a null IP address',(()=>{const t=e.lookup(null);expect(t).toBeNull()}))})),describe('#testUnknownIP()',(()=>{it('should return null for an unknown IP address',(()=>{const t=e.lookup('192.168.1.1');expect(t).toBeNull()}))})),describe('#testNoDataForIP()',(()=>{it('should return null for an IP address with no data',(()=>{const t=e.lookup('203.0.113.0');expect(t).toBeNull()}))})),describe('#testSpecialCharactersIP()',(()=>{it('should return null for an IP address with special characters',(()=>{const t=e.lookup('1.2.3.@');expect(t).toBeNull()}))}))}));
package/test/one.js CHANGED
@@ -1 +1 @@
1
- const o=require('../lib/geoip.js').lookup('2003:6:2184:e6d5:5991:6779:38be:654');console.log(o);
1
+ const o=require('../lib/geoip.js').lookup('158.255.88.0');console.log(o);
package/utils/updatedb.js CHANGED
@@ -1 +1 @@
1
- 'use strict';const{name:e,version:t}=require('../package.json'),n=`Mozilla/5.0 (compatible; ${e}/${t}; +https://sefinek.net)`,o=require('node:fs'),r=require('node:http'),i=require('node:https'),s=require('node:path'),c=require('node:url'),l=require('node:zlib');o.existsSync=o.existsSync||s.existsSync;const a=require('async'),u=require('chalk'),d=require('iconv-lite'),p=require('lazy'),f=require('rimraf').sync,g=require('adm-zip'),m=require('../lib/utils.js'),{Address6:h,Address4:w}=require('ip-address'),y=process.argv.slice(2);let S=y.find((function(e){return null!==e.match(/^license_key=[a-zA-Z0-9]+/)}));void 0===S&&void 0!==process.env.LICENSE_KEY&&(S='license_key='+process.env.LICENSE_KEY);let v=y.find((function(e){return null!==e.match(/^geoDataDir=[\w./]+/)}));void 0===v&&void 0!==process.env.GEODATADIR&&(v='geoDataDir='+process.env.GEODATADIR);let x=s.resolve(__dirname,'..','data');void 0!==v&&(x=s.resolve(process.cwd(),v.split('=')[1]),o.existsSync(x)||(console.log(u.red('ERROR')+': Directory doesn\'t exist: '+x),process.exit(1)));const E=s.resolve(__dirname,'..','tmp'),k={},I={},D=[{type:'country',url:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-Country-CSV&suffix=zip&'+S,checksum:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-Country-CSV&suffix=zip.sha256&'+S,fileName:'GeoLite2-Country-CSV.zip',src:['GeoLite2-Country-Locations-en.csv','GeoLite2-Country-Blocks-IPv4.csv','GeoLite2-Country-Blocks-IPv6.csv'],dest:['','geoip-country.dat','geoip-country6.dat']},{type:'city',url:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-City-CSV&suffix=zip&'+S,checksum:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-City-CSV&suffix=zip.sha256&'+S,fileName:'GeoLite2-City-CSV.zip',src:['GeoLite2-City-Locations-en.csv','GeoLite2-City-Blocks-IPv4.csv','GeoLite2-City-Blocks-IPv6.csv'],dest:['geoip-city-names.dat','geoip-city.dat','geoip-city6.dat']}];function C(e){const t=s.dirname(e);o.existsSync(t)||o.mkdirSync(t)}function R(e){const t=/^\s*(?:'[^'\\]*(?:\\[\S\s][^'\\]*)*'|"[^"\\]*(?:\\[\S\s][^"\\]*)*"|[^,'"\s\\]*(?:\s+[^,'"\s\\]+)*)\s*(?:,\s*(?:'[^'\\]*(?:\\[\S\s][^'\\]*)*'|"[^"\\]*(?:\\[\S\s][^"\\]*)*"|[^,'"\s\\]*(?:\s+[^,'"\s\\]+)*)\s*)*$/;if(!t.test(e)&&(e=function(e){let t=0,n=-1;for(e=e.replace(/""/,'\\"').replace(/'/g,'\\\'');t<e.length&&n<e.length;)t=n,n=e.indexOf(',',t+1),n<0&&(n=e.length),e.indexOf('\'',t||0)>-1&&e.indexOf('\'',t)<n&&'"'!=e[t+1]&&'"'!=e[n-1]&&(n=(e=e.substr(0,t+1)+'"'+e.substr(t+1,n-t-1)+'"'+e.substr(n,e.length-n)).indexOf(',',n+1),n<0&&(n=e.length));return e}(e),!t.test(e)))return null;const n=[];return e.replace(/(?!\s*$)\s*(?:'([^'\\]*(?:\\[\S\s][^'\\]*)*)'|"([^"\\]*(?:\\[\S\s][^"\\]*)*)"|([^,'"\s\\]*(?:\s+[^,'"\s\\]+)*))\s*(?:,|$)/g,(function(e,t,o,r){return void 0!==t?n.push(t.replace(/\\'/g,'\'')):void 0!==o?n.push(o.replace(/\\"/g,'"').replace(/\\'/g,'\'')):void 0!==r&&n.push(r),''})),/,\s*$/.test(e)&&n.push(''),n}function B(e){const t=c.parse(e);if(t.headers={'User-Agent':n},process.env.http_proxy||process.env.https_proxy)try{const e=require('node:https-proxy-agent');t.agent=new e(process.env.http_proxy||process.env.https_proxy)}catch(e){console.error('Install https-proxy-agent to use an HTTP/HTTPS proxy'),process.exit(-1)}return t}function _(e,t){if(-1!==y.indexOf('force'))return t(null,e);const n=e.checksum;if(void 0===n)return t(null,e);o.readFile(s.join(x,e.type+'.checksum'),{encoding:'utf8'},(function(o,s){!o&&s&&s.length&&(e.checkValue=s),console.log('Checking ',e.fileName);var c=i.get(B(n),(function(n){const o=n.statusCode;200!==o&&(console.log(u.red('ERROR')+n.data),console.log(u.red('ERROR')+': HTTP Request Failed [%d %s]',o,r.STATUS_CODES[o]),c.abort(),process.exit(1));let i='';n.on('data',(function(e){i+=e})),n.on('end',(function(){i&&i.length?i==e.checkValue?(console.log(u.green('Database "'+e.type+'" is up to date')),e.skip=!0):(console.log(u.green('Database '+e.type+' has new data')),e.checkValue=i):(console.log(u.red('ERROR')+': Could not retrieve checksum for',e.type,u.red('Aborting')),console.log('Run with "force" to update without checksum'),c.abort(),process.exit(1)),t(null,e)}))}))}))}function b(e,t){if(e.skip)return t(null,null,null,e);const n=e.url;let c=e.fileName;const a='.gz'===s.extname(c);a&&(c=c.replace('.gz',''));const d=s.join(E,c);if(o.existsSync(d))return t(null,d,c,e);console.log('Fetching ',c),C(d);var p=i.get(B(n),(function(n){const i=n.statusCode;let s;200!==i&&(console.error(u.red('ERROR')+': HTTP Request Failed [%d %s]',i,r.STATUS_CODES[i]),p.abort(),process.exit(1));const f=o.createWriteStream(d);s=a?n.pipe(l.createGunzip()).pipe(f):n.pipe(f),s.on('close',(function(){console.log(u.green(' DONE')),t(null,d,c,e)}))}));process.stdout.write('Retrieving '+c+'...')}function A(e,t,n,r){if(n.skip)return r(null,n);if('.zip'!==s.extname(t))r(null,n);else{process.stdout.write('Extracting '+t+'...');new g(e).getEntries().forEach((e=>{if(e.isDirectory)return;const t=e.entryName.split('/'),n=t[t.length-1],r=s.join(E,n);o.writeFileSync(r,e.getData())})),console.log(u.green(' DONE')),r(null,n)}}function O(e,t,n){let r=0;const i=s.join(x,t),c=s.join(E,e);f(i),C(i),process.stdout.write('Processing data (may take a moment)...');var l=Date.now(),a=o.openSync(i,'w');p(o.createReadStream(c)).lines.map((function(e){return d.decode(e,'latin1')})).skip(1).map((function(e){const t=R(e);if(!t||t.length<6)return void console.warn('weird line: %s::',e);let n,i,s;r++;const c=k[t[1]];let u,d,p;if(c){if(t[0].match(/:/)){for(d=34,s=new h(t[0]),n=m.aton6(s.startAddress().correctForm()),i=m.aton6(s.endAddress().correctForm()),u=Buffer.alloc(d),p=0;p<n.length;p++)u.writeUInt32BE(n[p],4*p);for(p=0;p<i.length;p++)u.writeUInt32BE(i[p],16+4*p)}else d=10,s=new w(t[0]),n=parseInt(s.startAddress().bigInteger(),10),i=parseInt(s.endAddress().bigInteger(),10),u=Buffer.alloc(d),u.fill(0),u.writeUInt32BE(n,0),u.writeUInt32BE(i,4);u.write(c,d-2),o.writeSync(a,u,0,d,null),Date.now()-l>5e3&&(l=Date.now(),process.stdout.write('\nStill working ('+r+')...'))}})).on('pipe',(function(){console.log(u.green(' DONE')),n()}))}function q(e,t,n){let r=0;const i=s.join(x,t),c=s.join(E,e);f(i),process.stdout.write('Processing Data (may take a moment) ...');var l=Date.now(),a=o.openSync(i,'w');p(o.createReadStream(c)).lines.map((function(e){return d.decode(e,'latin1')})).skip(1).map((function(e){if(e.match(/^Copyright/)||!e.match(/\d/))return;const t=R(e);if(!t)return void console.warn('weird line: %s::',e);let n,i,s,c,u,d,p,f,g,y;if(r++,t[0].match(/:/)){let e=0;for(d=48,s=new h(t[0]),n=m.aton6(s.startAddress().correctForm()),i=m.aton6(s.endAddress().correctForm()),c=parseInt(t[1],10),c=I[c],u=Buffer.alloc(d),u.fill(0),y=0;y<n.length;y++)u.writeUInt32BE(n[y],e),e+=4;for(y=0;y<i.length;y++)u.writeUInt32BE(i[y],e),e+=4;u.writeUInt32BE(c>>>0,32),p=Math.round(1e4*parseFloat(t[7])),f=Math.round(1e4*parseFloat(t[8])),g=parseInt(t[9],10),u.writeInt32BE(p,36),u.writeInt32BE(f,40),u.writeInt32BE(g,44)}else d=24,s=new w(t[0]),n=parseInt(s.startAddress().bigInteger(),10),i=parseInt(s.endAddress().bigInteger(),10),c=parseInt(t[1],10),c=I[c],u=Buffer.alloc(d),u.fill(0),u.writeUInt32BE(n>>>0,0),u.writeUInt32BE(i>>>0,4),u.writeUInt32BE(c>>>0,8),p=Math.round(1e4*parseFloat(t[7])),f=Math.round(1e4*parseFloat(t[8])),g=parseInt(t[9],10),u.writeInt32BE(p,12),u.writeInt32BE(f,16),u.writeInt32BE(g,20);o.writeSync(a,u,0,u.length,null),Date.now()-l>5e3&&(l=Date.now(),process.stdout.write('\nStill working ('+r+')...'))})).on('pipe',n)}function L(e,t){if(e.skip)return t(null,e);const n=e.type,r=e.src,i=e.dest;'country'===n?Array.isArray(r)?function(e,t){const n=s.join(E,e);process.stdout.write('Processing Lookup Data (may take a moment)...'),p(o.createReadStream(n)).lines.map((function(e){return d.decode(e,'latin1')})).skip(1).map((function(e){const t=R(e);!t||t.length<6?console.log('weird line: %s::',e):k[t[0]]=t[4]})).on('pipe',(function(){console.log(u.green(' DONE')),t()}))}(r[0],(function(){O(r[1],i[1],(function(){O(r[2],i[2],(function(){t(null,e)}))}))})):O(r,i,(function(){t(null,e)})):'city'===n&&function(e,t,n){let r=null,i=0;const c=s.join(x,t),l=s.join(E,e);f(c);var a=o.openSync(c,'w');p(o.createReadStream(l)).lines.map((function(e){return d.decode(e,'utf-8')})).skip(1).map((function(e){if(e.match(/^Copyright/)||!e.match(/\d/))return;const t=Buffer.alloc(88),n=R(e);if(!n)return void console.warn('weird line: %s::',e);r=parseInt(n[0]),I[r]=i;const s=n[4],c=n[6],l=n[10],u=parseInt(n[11]),d=n[12],p=n[13];t.fill(0),t.write(s,0),t.write(c,2),u&&t.writeInt32BE(u,5),t.write(p,9),t.write(d,10),t.write(l,42),o.writeSync(a,t,0,t.length,null),i++})).on('pipe',n)}(r[0],i[0],(function(){q(r[1],i[1],(function(){console.log('city data processed'),q(r[2],i[2],(function(){console.log(u.green(' DONE')),t(null,e)}))}))}))}function F(e,t){if(e.skip||!e.checkValue)return t();o.writeFile(s.join(x,e.type+'.checksum'),e.checkValue,'utf8',(function(n){n&&console.log(u.red('Failed to Update checksums.'),'Database:',e.type),t()}))}S||(console.error(u.red('ERROR')+': Missing license_key'),process.exit(1)),f(E),C(E),a.eachSeries(D,(function(e,t){a.seq(_,b,A,L,F)(e,t)}),(function(e){e?(console.error(u.red('Failed to Update Databases from MaxMind.'),e),process.exit(1)):(console.log(u.green('Successfully Updated Databases from MaxMind.')),-1!==y.indexOf('debug')?console.log(u.yellow.bold('Notice: temporary files are not deleted for debug purposes.')):f(E),process.exit(0))}));
1
+ 'use strict';const{name:e,version:t}=require('../package.json'),n=`Mozilla/5.0 (compatible; ${e}/${t}; +https://sefinek.net)`,o=require('node:fs'),r=require('node:http'),s=require('node:https'),i=require('node:path'),c=require('node:url'),l=require('node:zlib');o.existsSync=o.existsSync||i.existsSync;const a=require('async'),u=require('chalk'),d=require('iconv-lite'),p=require('lazy'),f=require('rimraf').sync,g=require('adm-zip'),m=require('../lib/utils.js'),{Address6:h,Address4:w}=require('ip-address'),y=process.argv.slice(2);let S=y.find((function(e){return null!==e.match(/^license_key=[a-zA-Z0-9]+/)}));void 0===S&&void 0!==process.env.LICENSE_KEY&&(S='license_key='+process.env.LICENSE_KEY);let v=y.find((function(e){return null!==e.match(/^geoDataDir=[\w./]+/)}));void 0===v&&void 0!==process.env.GEODATADIR&&(v='geoDataDir='+process.env.GEODATADIR);let x=i.resolve(__dirname,'..','data');void 0!==v&&(x=i.resolve(process.cwd(),v.split('=')[1]),o.existsSync(x)||(console.log(u.red('ERROR')+': Directory doesn\'t exist: '+x),process.exit(1)));const E=i.resolve(__dirname,'..','tmp'),k={},I={},D=[{type:'country',url:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-Country-CSV&suffix=zip&'+S,checksum:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-Country-CSV&suffix=zip.sha256&'+S,fileName:'GeoLite2-Country-CSV.zip',src:['GeoLite2-Country-Locations-en.csv','GeoLite2-Country-Blocks-IPv4.csv','GeoLite2-Country-Blocks-IPv6.csv'],dest:['','geoip-country.dat','geoip-country6.dat']},{type:'city',url:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-City-CSV&suffix=zip&'+S,checksum:'https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-City-CSV&suffix=zip.sha256&'+S,fileName:'GeoLite2-City-CSV.zip',src:['GeoLite2-City-Locations-en.csv','GeoLite2-City-Blocks-IPv4.csv','GeoLite2-City-Blocks-IPv6.csv'],dest:['geoip-city-names.dat','geoip-city.dat','geoip-city6.dat']}];function C(e){const t=i.dirname(e);o.existsSync(t)||o.mkdirSync(t)}function R(e){const t=/^\s*(?:'[^'\\]*(?:\\[\S\s][^'\\]*)*'|"[^"\\]*(?:\\[\S\s][^"\\]*)*"|[^,'"\s\\]*(?:\s+[^,'"\s\\]+)*)\s*(?:,\s*(?:'[^'\\]*(?:\\[\S\s][^'\\]*)*'|"[^"\\]*(?:\\[\S\s][^"\\]*)*"|[^,'"\s\\]*(?:\s+[^,'"\s\\]+)*)\s*)*$/;if(!t.test(e)&&(e=function(e){let t=0,n=-1;for(e=e.replace(/""/,'\\"').replace(/'/g,'\\\'');t<e.length&&n<e.length;)t=n,n=e.indexOf(',',t+1),n<0&&(n=e.length),e.indexOf('\'',t||0)>-1&&e.indexOf('\'',t)<n&&'"'!=e[t+1]&&'"'!=e[n-1]&&(n=(e=e.substr(0,t+1)+'"'+e.substr(t+1,n-t-1)+'"'+e.substr(n,e.length-n)).indexOf(',',n+1),n<0&&(n=e.length));return e}(e),!t.test(e)))return null;const n=[];return e.replace(/(?!\s*$)\s*(?:'([^'\\]*(?:\\[\S\s][^'\\]*)*)'|"([^"\\]*(?:\\[\S\s][^"\\]*)*)"|([^,'"\s\\]*(?:\s+[^,'"\s\\]+)*))\s*(?:,|$)/g,(function(e,t,o,r){return void 0!==t?n.push(t.replace(/\\'/g,'\'')):void 0!==o?n.push(o.replace(/\\"/g,'"').replace(/\\'/g,'\'')):void 0!==r&&n.push(r),''})),/,\s*$/.test(e)&&n.push(''),n}function B(e){const t=c.parse(e);if(t.headers={'User-Agent':n},process.env.http_proxy||process.env.https_proxy)try{const e=require('node:https-proxy-agent');t.agent=new e(process.env.http_proxy||process.env.https_proxy)}catch(e){console.error('Install https-proxy-agent to use an HTTP/HTTPS proxy'),process.exit(-1)}return t}function b(e,t){if(-1!==y.indexOf('force'))return t(null,e);const n=e.checksum;if(void 0===n)return t(null,e);o.readFile(i.join(x,e.type+'.checksum'),{encoding:'utf8'},(function(o,i){!o&&i&&i.length&&(e.checkValue=i),console.log('Checking ',e.fileName);var c=s.get(B(n),(function(n){const o=n.statusCode;200!==o&&(console.log(u.red('ERROR')+n.data),console.log(u.red('ERROR')+': HTTP Request Failed [%d %s]',o,r.STATUS_CODES[o]),c.abort(),process.exit(1));let s='';n.on('data',(function(e){s+=e})),n.on('end',(()=>{s&&s.length?s==e.checkValue?(console.log(u.green('Database "'+e.type+'" is up to date')),e.skip=!0):(console.log(u.green('Database '+e.type+' has new data')),e.checkValue=s):(console.log(u.red('ERROR')+': Could not retrieve checksum for',e.type,u.red('Aborting')),console.log('Run with "force" to update without checksum'),c.abort(),process.exit(1)),t(null,e)}))}))}))}function _(e,t){if(e.skip)return t(null,null,null,e);const n=e.url;let c=e.fileName;const a='.gz'===i.extname(c);a&&(c=c.replace('.gz',''));const d=i.join(E,c);if(o.existsSync(d))return t(null,d,c,e);console.log('Fetching ',c),C(d);var p=s.get(B(n),(function(n){const s=n.statusCode;let i;200!==s&&(console.error(u.red('ERROR')+': HTTP Request Failed [%d %s]',s,r.STATUS_CODES[s]),p.abort(),process.exit(1));const f=o.createWriteStream(d);i=a?n.pipe(l.createGunzip()).pipe(f):n.pipe(f),i.on('close',(()=>{console.log(u.green(' DONE')),t(null,d,c,e)}))}));process.stdout.write('Retrieving '+c+'...')}function A(e,t,n,r){if(n.skip)return r(null,n);if('.zip'!==i.extname(t))r(null,n);else{process.stdout.write('Extracting '+t+'...');new g(e).getEntries().forEach((e=>{if(e.isDirectory)return;const t=e.entryName.split('/'),n=t[t.length-1],r=i.join(E,n);o.writeFileSync(r,e.getData())})),console.log(u.green(' DONE')),r(null,n)}}function O(e,t,n){let r=0;const s=i.join(x,t),c=i.join(E,e);f(s),C(s),process.stdout.write('Processing data (may take a moment)...');var l=Date.now(),a=o.openSync(s,'w');p(o.createReadStream(c)).lines.map((function(e){return d.decode(e,'latin1')})).skip(1).map((function(e){const t=R(e);if(!t||t.length<6)return void console.warn('weird line: %s::',e);let n,s,i;r++;const c=k[t[1]];let u,d,p;if(c){if(t[0].match(/:/)){for(d=34,i=new h(t[0]),n=m.aton6(i.startAddress().correctForm()),s=m.aton6(i.endAddress().correctForm()),u=Buffer.alloc(d),p=0;p<n.length;p++)u.writeUInt32BE(n[p],4*p);for(p=0;p<s.length;p++)u.writeUInt32BE(s[p],16+4*p)}else d=10,i=new w(t[0]),n=parseInt(i.startAddress().bigInteger(),10),s=parseInt(i.endAddress().bigInteger(),10),u=Buffer.alloc(d),u.fill(0),u.writeUInt32BE(n,0),u.writeUInt32BE(s,4);u.write(c,d-2),o.writeSync(a,u,0,d,null),Date.now()-l>5e3&&(l=Date.now(),process.stdout.write('\nStill working ('+r+')...'))}})).on('pipe',(()=>{console.log(u.green(' DONE')),n()}))}function q(e,t,n){let r=0;const s=i.join(x,t),c=i.join(E,e);f(s),process.stdout.write('Processing Data (may take a moment) ...');var l=Date.now(),a=o.openSync(s,'w');p(o.createReadStream(c)).lines.map((function(e){return d.decode(e,'latin1')})).skip(1).map((function(e){if(e.match(/^Copyright/)||!e.match(/\d/))return;const t=R(e);if(!t)return void console.warn('weird line: %s::',e);let n,s,i,c,u,d,p,f,g,y;if(r++,t[0].match(/:/)){let e=0;for(d=48,i=new h(t[0]),n=m.aton6(i.startAddress().correctForm()),s=m.aton6(i.endAddress().correctForm()),c=parseInt(t[1],10),c=I[c],u=Buffer.alloc(d),u.fill(0),y=0;y<n.length;y++)u.writeUInt32BE(n[y],e),e+=4;for(y=0;y<s.length;y++)u.writeUInt32BE(s[y],e),e+=4;u.writeUInt32BE(c>>>0,32),p=Math.round(1e4*parseFloat(t[7])),f=Math.round(1e4*parseFloat(t[8])),g=parseInt(t[9],10),u.writeInt32BE(p,36),u.writeInt32BE(f,40),u.writeInt32BE(g,44)}else d=24,i=new w(t[0]),n=parseInt(i.startAddress().bigInteger(),10),s=parseInt(i.endAddress().bigInteger(),10),c=parseInt(t[1],10),c=I[c],u=Buffer.alloc(d),u.fill(0),u.writeUInt32BE(n>>>0,0),u.writeUInt32BE(s>>>0,4),u.writeUInt32BE(c>>>0,8),p=Math.round(1e4*parseFloat(t[7])),f=Math.round(1e4*parseFloat(t[8])),g=parseInt(t[9],10),u.writeInt32BE(p,12),u.writeInt32BE(f,16),u.writeInt32BE(g,20);o.writeSync(a,u,0,u.length,null),Date.now()-l>5e3&&(l=Date.now(),process.stdout.write('\nStill working ('+r+')...'))})).on('pipe',n)}function L(e,t){if(e.skip)return t(null,e);const n=e.type,r=e.src,s=e.dest;'country'===n?Array.isArray(r)?function(e,t){const n=i.join(E,e);process.stdout.write('Processing Lookup Data (may take a moment)...'),p(o.createReadStream(n)).lines.map((function(e){return d.decode(e,'latin1')})).skip(1).map((function(e){const t=R(e);!t||t.length<6?console.log('weird line: %s::',e):k[t[0]]=t[4]})).on('pipe',(()=>{console.log(u.green(' DONE')),t()}))}(r[0],(()=>{O(r[1],s[1],(()=>{O(r[2],s[2],(()=>{t(null,e)}))}))})):O(r,s,(()=>{t(null,e)})):'city'===n&&function(e,t,n){let r=null,s=0;const c=i.join(x,t),l=i.join(E,e);f(c);var a=o.openSync(c,'w');p(o.createReadStream(l)).lines.map((function(e){return d.decode(e,'utf-8')})).skip(1).map((function(e){if(e.match(/^Copyright/)||!e.match(/\d/))return;const t=Buffer.alloc(88),n=R(e);if(!n)return void console.warn('weird line: %s::',e);r=parseInt(n[0]),I[r]=s;const i=n[4],c=n[6],l=n[10],u=parseInt(n[11]),d=n[12],p=n[13];t.fill(0),t.write(i,0),t.write(c,2),u&&t.writeInt32BE(u,5),t.write(p,9),t.write(d,10),t.write(l,42),o.writeSync(a,t,0,t.length,null),s++})).on('pipe',n)}(r[0],s[0],(()=>{q(r[1],s[1],(()=>{console.log('city data processed'),q(r[2],s[2],(()=>{console.log(u.green(' DONE')),t(null,e)}))}))}))}function F(e,t){if(e.skip||!e.checkValue)return t();o.writeFile(i.join(x,e.type+'.checksum'),e.checkValue,'utf8',(function(n){n&&console.log(u.red('Failed to Update checksums.'),'Database:',e.type),t()}))}S||(console.error(u.red('ERROR')+': Missing license_key'),process.exit(1)),f(E),C(E),a.eachSeries(D,(function(e,t){a.seq(b,_,A,L,F)(e,t)}),(function(e){e?(console.error(u.red('Failed to update databases from MaxMind.'),e),process.exit(1)):(console.log(u.green('Successfully updated databases from MaxMind.')),-1!==y.indexOf('debug')?console.debug(u.yellow.bold('Notice: temporary files are not deleted for debug purposes.')):f(E),process.exit(0))}));
package/test/main.js DELETED
@@ -1 +0,0 @@
1
- const t=require('assert'),o=require('../lib/geoip.js');describe('GeoIP2',(function(){describe('#testLookup()',(function(){it('should return data about IPv4',(function(){const u=o.lookup('1.1.1.1');t.ok(u)})),it('should return data about IPv6',(function(){const u=o.lookup('2606:4700:4700::64');t.ok(u)}))})),describe('#testDataIP4()',(function(){it('should match data for IPv4 - US',(function(){const u=o.lookup('72.229.28.185');t.strictEqual(void 0!==u.range,!0),t.strictEqual(u.country,'US'),t.strictEqual(u.region,'NY'),t.strictEqual(u.eu,'0'),t.strictEqual(u.timezone,'America/New_York'),t.strictEqual(u.city,'New York'),t.ok(u.ll),t.strictEqual(u.metro,501),t.strictEqual(u.area,5)})),it('should match data for IPv4 - JP',(function(){const u=o.lookup('210.138.184.59');t.strictEqual(void 0!==u.range,!0),t.strictEqual(u.country,'JP'),t.strictEqual(u.region,'13'),t.strictEqual(u.eu,'0'),t.strictEqual(u.timezone,'Asia/Tokyo'),t.strictEqual(u.city,'Chiyoda-ku'),t.ok(u.ll),t.strictEqual(u.metro,0),t.strictEqual(u.area,200)})),it('should match data for IPv4 - PL',(function(){const u=o.lookup('104.113.255.255');t.strictEqual(void 0!==u.range,!0),t.strictEqual(u.country,'PL'),t.strictEqual(u.region,'14'),t.strictEqual(u.eu,'1'),t.strictEqual(u.timezone,'Europe/Warsaw'),t.strictEqual(u.city,'Warsaw'),t.ok(u.ll),t.strictEqual(u.metro,0),t.strictEqual(u.area,20)})),it('should match data for IPv4 - RU',(function(){const u=o.lookup('109.108.63.255');t.strictEqual(void 0!==u.range,!0),t.strictEqual(u.country,'RU'),t.strictEqual(u.region,'IVA'),t.strictEqual(u.eu,'0'),t.strictEqual(u.timezone,'Europe/Moscow'),t.strictEqual(u.city,'Kineshma'),t.ok(u.ll),t.strictEqual(u.metro,0),t.strictEqual(u.area,200)}))})),describe('#testDataIP6()',(function(){it('should match data for IPv6',(function(){const u=o.lookup('2001:1c04:400::1');t.strictEqual(void 0!==u.range,!0),t.strictEqual(u.country,'NL'),t.strictEqual(u.region,'NH'),t.strictEqual(u.eu,'1'),t.strictEqual(u.timezone,'Europe/Amsterdam'),t.strictEqual(u.city,'Zandvoort'),t.ok(u.ll),t.strictEqual(u.metro,0),t.strictEqual(u.area,5)})),it('should match data for IPv4 - JP',(function(){const u=o.lookup('2400:8500:1302:814:a163:44:173:238f');t.strictEqual(void 0!==u.range,!0),t.strictEqual(u.country,'JP'),t.strictEqual(u.region,''),t.strictEqual(u.eu,'0'),t.strictEqual(u.timezone,'Asia/Tokyo'),t.strictEqual(u.city,''),t.ok(u.ll),t.strictEqual(u.metro,0),t.strictEqual(u.area,500)})),it('should match data for IPv4 - JP',(function(){const u=o.lookup('1.79.255.115');t.strictEqual(void 0!==u.range,!0),t.strictEqual(u.country,'JP'),t.strictEqual(u.region,''),t.strictEqual(u.eu,'0'),t.strictEqual(u.timezone,'Asia/Tokyo'),t.strictEqual(u.city,''),t.ok(u.ll),t.strictEqual(u.metro,0),t.strictEqual(u.area,500)}))})),describe('#testUTF8()',(function(){it('should return UTF8 city name',(function(){const u=o.lookup('2.139.175.1');t.ok(u),t.strictEqual(u.city,'Barbera Del Valles')}))})),describe('#testMetro()',(function(){it('should match metro data',(function(){const u=o.lookup('23.240.63.68');t.strictEqual(u.metro,803)}))})),describe('#testIPv4MappedIPv6()',(function(){it('should match IPv4 mapped IPv6 data',(function(){const u=o.lookup('195.16.170.74');t.strictEqual(u.metro,0)}))})),describe('#testSyncReload()',(function(){it('should reload data synchronously',(function(){const u=o.lookup('75.82.117.180');t.notStrictEqual(u,null);const l=o.lookup('::ffff:173.185.182.82');t.notStrictEqual(l,null),o.clear();const c=o.lookup('75.82.117.180');t.strictEqual(c,null);const r=o.lookup('::ffff:173.185.182.82');t.strictEqual(r,null),o.reloadDataSync();const a=o.lookup('75.82.117.180');t.deepStrictEqual(u,a);const i=o.lookup('::ffff:173.185.182.82');t.deepStrictEqual(l,i)}))})),describe('#testAsyncReload()',(function(){it('should reload data asynchronously',(function(u){const l=o.lookup('75.82.117.180');t.notStrictEqual(l,null);const c=o.lookup('::ffff:173.185.182.82');t.notStrictEqual(c,null),o.clear();const r=o.lookup('75.82.117.180');t.strictEqual(r,null);const a=o.lookup('::ffff:173.185.182.82');t.strictEqual(a,null),o.reloadData((function(){const r=o.lookup('75.82.117.180');t.deepStrictEqual(l,r);const a=o.lookup('::ffff:173.185.182.82');t.deepStrictEqual(c,a),u()}))}))})),describe('#testInvalidIP()',(function(){it('should return null for an invalid IP address',(function(){const u=o.lookup('invalid_ip_address');t.strictEqual(u,null)}))})),describe('#testEmptyIP()',(function(){it('should return null for an empty IP address',(function(){const u=o.lookup('');t.strictEqual(u,null)}))})),describe('#testNullIP()',(function(){it('should return null for a null IP address',(function(){const u=o.lookup(null);t.strictEqual(u,null)}))})),describe('#testUnknownIP()',(function(){it('should return null for an unknown IP address',(function(){const u=o.lookup('192.168.1.1');t.strictEqual(u,null)}))})),describe('#testNoDataForIP()',(function(){it('should return null for an IP address with no data',(function(){const u=o.lookup('203.0.113.0');t.strictEqual(u,null)}))})),describe('#testSpecialCharactersIP()',(function(){it('should return null for an IP address with special characters',(function(){const u=o.lookup('1.2.3.@');t.strictEqual(u,null)}))}))}));