comparison stream_geoip.t @ 1062:f1cc64e4e67d

Tests: basic tests for stream geoip module.
author Andrey Zelenkov <zelenkov@nginx.com>
date Fri, 14 Oct 2016 15:20:28 +0300
parents
children 6508aa1cf9cb
comparison
equal deleted inserted replaced
1061:83357211563e 1062:f1cc64e4e67d
1 #!/usr/bin/perl
2
3 # (C) Andrey Zelenkov
4 # (C) Nginx, Inc.
5
6 # Tests for stream geoip module.
7
8 ###############################################################################
9
10 use warnings;
11 use strict;
12
13 use Test::More;
14
15 use Socket qw/ $CRLF /;
16
17 BEGIN { use FindBin; chdir($FindBin::Bin); }
18
19 use lib 'lib';
20 use Test::Nginx;
21 use Test::Nginx::Stream qw/ stream /;
22
23 ###############################################################################
24
25 select STDERR; $| = 1;
26 select STDOUT; $| = 1;
27
28 my $t = Test::Nginx->new()->has(qw/stream stream_geoip stream_return ipv6/)
29 ->has('stream_realip')->plan(20);
30
31 $t->write_file_expand('nginx.conf', <<'EOF');
32
33 %%TEST_GLOBALS%%
34
35 daemon off;
36
37 events {
38 }
39
40 stream {
41 set_real_ip_from 127.0.0.1/32;
42
43 geoip_country %%TESTDIR%%/country.dat;
44 geoip_city %%TESTDIR%%/city.dat;
45 geoip_org %%TESTDIR%%/org.dat;
46
47 server {
48 listen 127.0.0.1:8080 proxy_protocol;
49 return "country_code:$geoip_country_code
50 country_code3:$geoip_country_code3
51 country_name:$geoip_country_name
52
53 area_code:$geoip_area_code
54 city_continent_code:$geoip_city_continent_code
55 city_country_code:$geoip_city_country_code
56 city_country_code3:$geoip_city_country_code3
57 city_country_name:$geoip_city_country_name
58 dma_code:$geoip_dma_code
59 latitude:$geoip_latitude
60 longitude:$geoip_longitude
61 region:$geoip_region
62 region_name:$geoip_region_name
63 city:$geoip_city
64 postal_code:$geoip_postal_code
65
66 org:$geoip_org";
67 }
68 }
69
70 EOF
71
72 my $d = $t->testdir();
73
74 # country database:
75 #
76 # "10.0.0.1","10.0.0.1","RU","Russian Federation"
77 # "2001:db8::","2001:db8::","US","United States"
78
79 my $data = '';
80
81 for my $i (0 .. 156) {
82 # skip to offset 32 if 1st bit set in ipv6 address wins
83 $data .= pack_node($i + 1) . pack_node(32), next if $i == 2;
84 # otherwise default to RU
85 $data .= pack_node(0xffffb9) . pack_node(0xffff00), next if $i == 31;
86 # continue checking bits set in ipv6 address
87 $data .= pack_node(0xffff00) . pack_node($i + 1), next
88 if grep $_ == $i, (44, 49, 50, 52, 53, 55, 56, 57);
89 # last bit set in ipv6 address
90 $data .= pack_node(0xffffe1) . pack_node(0xffff00), next if $i == 156;
91 $data .= pack_node($i + 1) . pack_node(0xffff00);
92 }
93
94 $data .= chr(0x00) x 3;
95 $data .= chr(0xFF) x 3;
96 $data .= chr(12);
97
98 $t->write_file('country.dat', $data);
99
100 # city database:
101 #
102 # "167772161","167772161","RU","48","Moscow","119034","55.7543",37.6202",,
103
104 $data = '';
105
106 for my $i (0 .. 31) {
107 $data .= pack_node(32) . pack_node($i + 1), next if $i == 4 or $i == 6;
108 $data .= pack_node(32) . pack_node($i + 2), next if $i == 31;
109 $data .= pack_node($i + 1) . pack_node(32);
110 }
111
112 $data .= chr(42);
113 $data .= chr(185);
114 $data .= pack('Z*', 48);
115 $data .= pack('Z*', 'Moscow');
116 $data .= pack('Z*', 119034);
117 $data .= pack_node(int((55.7543 + 180) * 10000));
118 $data .= pack_node(int((37.6202 + 180) * 10000));
119 $data .= chr(0) x 3;
120 $data .= chr(0xFF) x 3;
121 $data .= chr(2);
122 $data .= pack_node(32);
123
124 $t->write_file('city.dat', $data);
125
126 # organization database:
127 #
128 # "167772161","167772161","Nginx"
129
130 $data = '';
131
132 for my $i (0 .. 31) {
133 $data .= pack_org(32) . pack_org($i + 1), next if $i == 4 or $i == 6;
134 $data .= pack_org(32) . pack_org($i + 2), next if $i == 31;
135 $data .= pack_org($i + 1) . pack_org(32);
136 }
137
138 $data .= chr(42);
139 $data .= pack('Z*', 'Nginx');
140 $data .= chr(0xFF) x 3;
141 $data .= chr(5);
142 $data .= pack_node(32);
143
144 $t->write_file('org.dat', $data);
145 $t->run();
146
147 ###############################################################################
148
149 my %data = stream_pp('10.0.0.1') =~ /(\w+):(.*)/g;
150 is($data{country_code}, 'RU', 'geoip country code');
151 is($data{country_code3}, 'RUS', 'geoip country code 3');
152 is($data{country_name}, 'Russian Federation', 'geoip country name');
153
154 is($data{area_code}, 0, 'geoip area code');
155 is($data{city_continent_code}, 'EU', 'geoip city continent code');
156 is($data{city_country_code}, 'RU', 'geoip city country code');
157 is($data{city_country_code3}, 'RUS', 'geoip city country code 3');
158 is($data{city_country_name}, 'Russian Federation', 'geoip city country name');
159 is($data{dma_code}, 0, 'geoip dma code');
160 is($data{latitude}, 55.7543, 'geoip latitude');
161 is($data{longitude}, 37.6202, 'geoip longitude');
162 is($data{region}, 48, 'geoip region');
163 is($data{region_name}, 'Moscow City', 'geoip region name');
164 is($data{city}, 'Moscow', 'geoip city');
165 is($data{postal_code}, 119034, 'geoip postal code');
166
167 is($data{org}, 'Nginx', 'geoip org');
168
169 like(stream_pp('::ffff:10.0.0.1'), qr/org:Nginx/, 'geoip ipv6 ipv4-mapped');
170
171 %data = stream_pp('2001:db8::') =~ /(\w+):(.*)/g;
172 is($data{country_code}, 'US', 'geoip ipv6 country code');
173 is($data{country_code3}, 'USA', 'geoip ipv6 country code 3');
174 is($data{country_name}, 'United States', 'geoip ipv6 country name');
175
176 ###############################################################################
177
178 sub stream_pp {
179 my ($ip) = @_;
180 my $type = ($ip =~ ':' ? 'TCP6' : 'TCP4');
181 return stream()->io("PROXY $type $ip 127.0.0.1 8080 8080${CRLF}");
182 }
183
184 sub pack_node {
185 substr pack('V', shift), 0, 3;
186 }
187
188 sub pack_org {
189 pack('V', shift);
190 }
191
192 ###############################################################################