sql >> Database teknologi >  >> RDS >> PostgreSQL

Bestem land ud fra IP - IPv6

Jeg tror, ​​jeg har fundet løsningen. Det indebærer først at ændre dataene og derefter massere inputtet. Her er, hvad der virkede.

Først skal dataene konverteres, så alle adresser er fyldte, uden afkortning, med semikolonseparatorer fjernet. Eksempeldataene vist i mit spørgsmål er konverteret til:

 t_start                          | t_end                            | t_country_code
----------------------------------+----------------------------------+----------------
 00000000000000000000000000000000 | 00ffffffffffffffffffffffffffffff | ZZ
 01000000000000000000000000000000 | 01ffffffffffffffffffffffffffffff | ZZ
...
 20000000000000000000000000000000 | 2000ffffffffffffffffffffffffffff | ZZ
...
 20011200000000000000000000000000 | 20011200ffffffffffffffffffffffff | MX
...

Dette er hvad der er gemt i databasen.

Det næste trin var at konvertere IP-adressen modtaget i koden til at være i samme format. Dette gøres i PHP med følgende kode (antag at $ip_address er den indgående IPv6-adresse):

$addr_bin = inet_pton($ip_address);                                                                                                              
$bytes = unpack('n*', $addr_bin);
$ip_address = implode('', array_map(function ($b) {return sprintf("%04x", $b); }, $bytes));

Nu variabel $ip_adress vil indeholde den fulde IPv6-adresse, for eksempel

:: => 00000000000000000000000000000000
2001:1200::ab => 200112000000000000000000000000ab

og så videre.

Nu kan du blot sammenligne denne fulde adresse med intervallerne i databasen. Jeg tilføjede en anden funktion til databasen til at håndtere IPv6-adresser, som ser sådan ud:

CREATE OR REPLACE FUNCTION get_country_for_ipv6(character varying)
  RETURNS character varying AS
$BODY$
declare
    ip  ALIAS for $1;
    ccode   varchar;
begin
    select into ccode t_country_code from ipv6_to_country where addr between n_from and n_to limit 1;
    if ccode is null then
        ccode := '';
    end if;
    return ccode;
end;$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;

Til sidst tilføjede jeg i min php-kode koden, der kalder den ene eller den anden Postgres-funktion baseret på input ip_address.



  1. django - samle json-feltspecifikke nøgler og rækkefølge efter aggregeringen

  2. Databasetabel eksisterer ikke ifølge android studio compiler

  3. javafx Tabelvisning viser ikke data fra databasen

  4. Test af Oracle to_date-funktionen