Czy Secure.ANDROID_ID jest unikalne dla każdego urządzenia?

81

Używam tego połączenia:

Secure.getString(getApplicationContext().getContentResolver(), Secure.ANDROID_ID);

Aby uzyskać identyfikator UID dla urządzenia. Myślę jednak, że otrzymuję ten sam identyfikator z wielu urządzeń. Czy to powinno być możliwe?

Ten identyfikator to: 9774d56d682e549c i najwyraźniej występuje problem z kilkoma urządzeniami zwracającymi ten identyfikator http://code.google.com/p/android/issues/list?cursor=10603&updated=10603&ts=1295993403

FoamyGuy
źródło
Po sprawdzeniu danego identyfikatora i obejrzeniu wątku na jego temat jestem pewien. Na początku pomyślałem, że możliwe, że urządzenie zwróciło zero i gdzieś umieściłem je jako domyślne. Ale tak nie jest. Wiem na pewno, że otrzymuję tę samą wartość na wielu urządzeniach.
FoamyGuy
1
Znalazłem idealne: stackoverflow.com/a/16929647/1318946
Pratik Butani
W przypadkach, w których nie jest unikalna, użyj tej biblioteki, która jest dostarczana z Identity.getDeviceId (kontekst) .
krakanie

Odpowiedzi:

47

Sprawdzić w tym wątku ,. Należy jednak zachować ostrożność, ponieważ zostało udokumentowane jako „może ulec zmianie po przywróceniu ustawień fabrycznych”. Używaj na własne ryzyko i można go łatwo zmienić na zrootowanym telefonie. Wygląda również na to, że niektórzy producenci mieli problemy z telefonami mającymi podwójny wątek numerów . W zależności od tego, co próbujesz zrobić, prawdopodobnie nie użyłbym tego jako UID.

ninjasense
źródło
19
szkoda, że ​​implementacja ANDROID_ID jest taka ... kiepska! Sądząc po dokumentacji Google, intencją był trwalszy identyfikator: A 64-bit number (as a hex string) that is randomly generated on the device's first boot and should remain constant for the lifetime of the device
Someone Somewhere
3
Zgodnie z linkiem do wątku „Ponadto w popularnym telefonie dużego producenta wystąpił co najmniej jeden szeroko obserwowany błąd, w którym każda instancja ma ten sam ANDROID_ID”. Lepiej tego nie używać
Muhammad Riyaz.
2
To było od 2011 roku podczas Froyo. Teraz to nie ma znaczenia.
Aubtin Samai
A co z kopią zapasową / przywracaniem urządzenia lub klonowaniem urządzenia? masz pojęcie o możliwości posiadania tego samego ANDROID_ID? zakładając oczywiście, że urządzenie nie jest zrootowane.
FunkSoulBrother
39

Z Androidem O zmieni się zachowanie ANDROID_ID. ANDROID_ID będzie różny w zależności od aplikacji i użytkownika w telefonie.

Zaczerpnięte z: https://android-developers.googleblog.com/2017/04/changes-to-device-identifiers-in.html

Identyfikator Androida

W wersji O identyfikator Androida (Settings.Secure.ANDROID_ID lub SSAID) ma inną wartość dla każdej aplikacji i każdego użytkownika na urządzeniu. Deweloperzy, którzy potrzebują identyfikatora w zakresie urządzenia, powinni zamiast tego używać identyfikatora możliwego do zresetowania, takiego jak identyfikator wyświetlania reklam, co zapewnia użytkownikom większą kontrolę. Identyfikator reklam zawiera również ustawienie widoczne dla użytkownika, które ogranicza śledzenie reklam.

Dodatkowo w systemie Android O:

  • Wartość ANDROID_ID nie zmieni się po odinstalowaniu / ponownej instalacji pakietu, o ile nazwa pakietu i klucz podpisywania są takie same. Aplikacje mogą polegać na tej wartości, aby zachować stan podczas ponownych instalacji.
  • Jeśli aplikacja została zainstalowana na urządzeniu z wcześniejszą wersją Androida, identyfikator Androida pozostaje taki sam po zaktualizowaniu urządzenia do systemu Android O, chyba że aplikacja zostanie odinstalowana i ponownie zainstalowana.
  • Wartość identyfikatora Androida zmienia się tylko wtedy, gdy urządzenie jest resetowane do ustawień fabrycznych lub gdy klucz podpisywania zmienia się między
    zdarzeniami odinstalowania i ponownej instalacji.
  • Ta zmiana jest wymagana tylko w przypadku producentów urządzeń, którzy otrzymują usługi Google Play i identyfikator wyświetlania reklam. Inni producenci urządzeń mogą zapewnić alternatywny identyfikator z możliwością resetowania lub nadal zapewniać identyfikator ANDROID.
userM1433372
źródło
Dzięki. Wyciągałem włosy, próbując dowiedzieć się, dlaczego nie otrzymałem reklam testowych w telefonie żony za pomocą identyfikatora (md5'ed) zgłoszonego przez identyfikator urządzenia, a następnie dlaczego nie pasowałoby to do wartości zgłoszonej przez polecenie ustawień powłoki adb. .. Myślałem, że wariuję.
ecv
15

Więc jeśli chcesz czegoś wyjątkowego dla samego urządzenia, TM.getDeviceId() powinno wystarczyć.

Oto kod, który pokazuje, jak uzyskać identyfikator menedżera telefonii. Identyfikator urządzenia z Androidem, którego używasz, może zmienić się w ustawieniach fabrycznych, a niektórzy producenci mają problem z nadaniem unikalnego identyfikatora.

TelephonyManager tm = 
        (TelephonyManager) this.getSystemService(Context.TELEPHONY_SERVICE);
String androidId = Secure.getString(this.getContentResolver(), Secure.ANDROID_ID);
Log.d("ID", "Android ID: " + androidId);
Log.d("ID", "Device ID : " + tm.getDeviceId());

Pamiętaj, aby uzyskać uprawnienia do TelephonyManagerkorzystania z

<uses-permission android:name="android.permission.READ_PHONE_STATE" />
Vincent Vettukal
źródło
3
Tak, użycie metody getDeviceId () również działa. Należy jednak być bardzo ostrożnym, ponieważ może zwrócić wartość zerową. (Na urządzeniach bez modemu 3G / telefonicznego) Rozwiązaniem, którego używam, jest powrót do adresu
MAC
19
Wymaganie READ_PHONE_STATEpozwolenia jest okropne. Użyj ANDROID_IDzamiast tego.
dolmen
tak, może zwrócić wartość null na urządzeniach bez 3g (wiele z nich na rynku), wtedy powinieneś użyć WiFi - jego guid również może być zerowy, dopóki nie włączysz / wyłączysz go przynajmniej raz po ponownym uruchomieniu urządzenia. A jeśli nie ma wifi ... prawdziwy koszmar, na windows ce był GUID dla każdego urządzenia i życie było piękne.
marcinj
okazuje się po tysiącach zapytań, że identyfikator urządzenia, którym jest IMEI, może zostać zduplikowany na fałszywych urządzeniach, stąd nie jest to w pełni dowód. Wracam do używania getSimSerialNumber i ANDROID_ID jako rezerwy.
Ajibola
Android 10 (poziom API 29) dodaje ograniczenia dla identyfikatorów, których nie można zresetować, które obejmują zarówno numer IMEI, jak i numer seryjny. Zanim zaimplementujesz to TM.getDeviceId()podejście, najpierw przyjrzyj się nowym wymaganiom dotyczącym uprawnień dla identyfikatorów urządzeń na urządzeniach z Androidem> = 10.
Ezekiel Sebastine
6

Przeczytałem kilka rzeczy na ten temat i niestety nie należy polegać na ANDROID_ID w celu jednoznacznej identyfikacji pojedynczego urządzenia.

Wydaje się, że nie jest to wymuszone w wymaganiach zgodności Androida, więc producenci wydają się wdrażać go w wybrany przez siebie sposób, w tym niektórzy używają go bardziej jako identyfikatora „modelu” itp.

Należy również pamiętać, że nawet jeśli producent napisał generator, aby uczynić go identyfikatorem UUID (na przykład), nie ma gwarancji, że przetrwa reset do ustawień fabrycznych.

Squonk
źródło
6
Myślę, że z założenia NIE przetrwa resetowania do ustawień fabrycznych, jest to wspomniane gdzieś w dokumentacji. I to jest właściwy sposób implementacji.
Violet Giraffe
Jak więc możemy wygenerować identyfikator GUID?
IgorGanapolsky
6

Istnieje wiele rozwiązań, ale żadne z nich nie jest doskonałe. chodźmy jeden po drugim.

1. Unique Telephony Number (IMEI, MEID, ESN, IMSI)

  • To rozwiązanie wymaga żądania od użytkownika android.permission.READ_PHONE_STATE, co może być trudne do uzasadnienia na podstawie typu złożonej aplikacji.

  • Ponadto to rozwiązanie jest ograniczone do smartfonów, ponieważ tablety nie mają usług telefonicznych. Jedną z zalet jest to, że wartość utrzymuje się do przywrócenia ustawień fabrycznych na urządzeniach.

2. MAC Address

  • Możesz także spróbować uzyskać adres MAC z urządzenia wyposażonego w sprzęt Wi-Fi lub Bluetooth. Ale to rozwiązanie nie jest zalecane, ponieważ nie wszystkie urządzenia mają połączenie Wi-Fi. Nawet jeśli użytkownik ma połączenie Wi-Fi, musi być włączone, aby pobrać dane. W przeciwnym razie wywołanie nie zgłosi adresu MAC.

3. Serial Number

  • Urządzenia bez usług telefonicznych, takie jak tablety, muszą zgłaszać unikalny identyfikator urządzenia, który jest dostępny za pośrednictwem android.os.Build.SERIAL od wersji Androida 2.3 Gingerbread. Niektóre telefony oferujące usługi telefoniczne mogą również definiować numer seryjny. Podobnie jak nie wszystkie urządzenia z Androidem mają numer seryjny, to rozwiązanie nie jest niezawodne.

4. Secure Android ID

  • Przy pierwszym uruchomieniu urządzenia generowana i zapisywana jest losowa wartość. Ta wartość jest dostępna za pośrednictwem Settings.Secure.ANDROID_ID. Jest to liczba 64-bitowa, która powinna pozostać niezmienna przez cały okres eksploatacji urządzenia. ANDROID_ID wydaje się dobrym wyborem dla unikalnego identyfikatora urządzenia, ponieważ jest dostępny dla smartfonów i tabletów.

    String androidId = Settings.Secure.getString(getContentResolver(),Settings.Secure.ANDROID_ID);
    
  • Wartość może się jednak zmienić, jeśli na urządzeniu zostanie przywrócone ustawienia fabryczne. Istnieje również znany błąd związany z popularnym telefonem od producenta, w którym każda instancja ma ten sam ANDROID_ID. Oczywiście rozwiązanie nie jest w 100% niezawodne.

5. Use UUID

  • Ponieważ w przypadku większości aplikacji wymagana jest identyfikacja konkretnej instalacji, a nie urządzenia fizycznego, dobrym rozwiązaniem jest uzyskanie unikalnego identyfikatora użytkownika w przypadku używania klasy UUID. Poniższe rozwiązanie zostało zaprezentowane przez Reto Meier z Google w prezentacji Google I / O:

    private static String uniqueID = null;
    private static final String PREF_UNIQUE_ID = "PREF_UNIQUE_ID";
    public synchronized static String id(Context context) {
       if (uniqueID == null) {
           SharedPreferences sharedPrefs = context.getSharedPreferences(
                   PREF_UNIQUE_ID, Context.MODE_PRIVATE);
           uniqueID = sharedPrefs.getString(PREF_UNIQUE_ID, null);
           if (uniqueID == null) {
               uniqueID = UUID.randomUUID().toString();
               Editor editor = sharedPrefs.edit();
               editor.putString(PREF_UNIQUE_ID, uniqueID);
               editor.commit();
           }
       }    return uniqueID;
    }
    

Zidentyfikowanie konkretnego urządzenia na Androidzie nie jest łatwe. Istnieje wiele dobrych powodów, aby tego uniknąć. Najlepszym rozwiązaniem jest prawdopodobnie zidentyfikowanie konkretnej instalacji za pomocą rozwiązania UUID. kredyt: blog

Radhey
źródło
1

Wystarczy wymienić tutaj alternatywne rozwiązanie, identyfikator reklamowy:

https://support.google.com/googleplay/android-developer/answer/6048248?hl=en

Skopiowano z linku powyżej:

Identyfikator wyświetlania reklam to unikalny identyfikator reklamowy z możliwością resetowania przez użytkownika, udostępniany przez usługi Google Play. Zapewnia użytkownikom lepszą kontrolę i zapewnia programistom prosty, standardowy system umożliwiający dalsze zarabianie na aplikacjach. Umożliwia użytkownikom resetowanie identyfikatorów lub rezygnację ze spersonalizowanych reklam (wcześniej znanych jako reklamy oparte na zainteresowaniach) w aplikacjach Google Play.

Ograniczenia to:

  1. Tylko urządzenia obsługujące Google Play.
  2. Polityka prywatności: https://support.google.com/googleplay/android-developer/answer/113469?hl=en&rd=1#privacy
półkole 21
źródło
Czy to zadziała na telefonach bez Google Play (usług)?
Max Waterman
To nie jest GUID
IgorGanapolsky
0
//Fields
String myID;
int myversion = 0;


myversion = Integer.valueOf(android.os.Build.VERSION.SDK);
if (myversion < 23) {
        TelephonyManager mngr = (TelephonyManager) 
getSystemService(Context.TELEPHONY_SERVICE);
        myID= mngr.getDeviceId();
    }
    else
    {
        myID = 
Settings.Secure.getString(getApplicationContext().getContentResolver(), 
Settings.Secure.ANDROID_ID);
    }

Tak, Secure.ANDROID_ID jest unikalny dla każdego urządzenia.

boraberka
źródło