Próbuję nawiązywać połączenia HTTPS, używając HttpClient
lib, ale problem polega na tym, że certyfikat nie jest podpisany przez uznany urząd certyfikacji (CA), taki jak Verisign , GlobalSIgn itp., Wymieniony na zestawie zaufanych certyfikatów Androida, Ciągle dostaję javax.net.ssl.SSLException: Not trusted server certificate
.
Widziałem rozwiązania, w których po prostu akceptujesz wszystkie certyfikaty, ale co jeśli chcę zapytać użytkownika?
Chcę uzyskać okno dialogowe podobne do okna przeglądarki, pozwalające użytkownikowi zdecydować, czy kontynuować, czy nie. Najlepiej, gdybym korzystał z tego samego magazynu certyfikatów co przeglądarka. Jakieś pomysły?
Odpowiedzi:
Pierwszą rzeczą, którą musisz zrobić, jest ustawienie poziomu weryfikacji. Takie poziomy to nie tyle:
Chociaż metoda setHostnameVerifier () jest przestarzała dla nowej biblioteki Apache, ale dla wersji w Android SDK jest normalna. Więc bierzemy
ALLOW_ALL_HOSTNAME_VERIFIER
i ustawiamy to w fabryce metodySSLSocketFactory.setHostnameVerifier()
.Następnie musisz ustawić naszą fabrykę dla protokołu na https. Aby to zrobić, po prostu wywołaj
SchemeRegistry.register()
metodę.Następnie musisz utworzyć plik
DefaultHttpClient
zSingleClientConnManager
. Również w poniższym kodzie możesz zobaczyć, że domyślnie użyje również naszej flagi (ALLOW_ALL_HOSTNAME_VERIFIER
) według metodyHttpsURLConnection.setDefaultHostnameVerifier()
Poniższy kod działa u mnie:
źródło
org.apache.http.conn.ssl.SSLSocketFactory
dlaczego chcę używaćjavax.net.ssl.HttpsURLConnection
?Aby uzyskać bezpieczne połączenie od urzędów certyfikacji, które nie są uważane za zaufane przez platformę Android, wymagane są następujące główne kroki.
Zgodnie z prośbą wielu użytkowników, odtworzyłem tutaj najważniejsze części z mojego artykułu na blogu :
java.net.ssl.HttpsURLConnection
(łatwiejszy do zrozumienia, bardziej wydajny)Złap certyfikaty
Musisz uzyskać wszystkie certyfikaty, które tworzą łańcuch od certyfikatu punktu końcowego przez całą drogę do głównego urzędu certyfikacji. Oznacza to wszystkie (jeśli są obecne) certyfikaty pośredniego urzędu certyfikacji, a także certyfikat głównego urzędu certyfikacji. Nie musisz uzyskiwać certyfikatu punktu końcowego.
Utwórz magazyn kluczy
Pobierz dostawcę BouncyCastle i zapisz go w znanej lokalizacji. Upewnij się również, że możesz wywołać polecenie keytool (zwykle znajduje się w folderze bin instalacji JRE).
Teraz zaimportuj uzyskane certyfikaty (nie importuj certyfikatu punktu końcowego) do magazynu kluczy w formacie BouncyCastle.
Nie testowałem tego, ale myślę, że kolejność importu certyfikatów jest ważna. Oznacza to, że najpierw należy zaimportować najniższy certyfikat pośredniego urzędu certyfikacji, a następnie aż do certyfikatu głównego urzędu certyfikacji.
Za pomocą następującego polecenia zostanie utworzony nowy magazyn kluczy (jeśli nie jest jeszcze obecny) z hasłem mysecret i zostanie zaimportowany certyfikat pośredniego ośrodka CA. Zdefiniowałem również dostawcę BouncyCastle, gdzie można go znaleźć w moim systemie plików i formacie magazynu kluczy. Wykonaj to polecenie dla każdego certyfikatu w łańcuchu.
Sprawdź, czy certyfikaty zostały poprawnie zaimportowane do magazynu kluczy:
Powinien wyprowadzić cały łańcuch:
Teraz możesz skopiować magazyn kluczy jako surowiec w aplikacji na Androida pod
res/raw/
Użyj magazynu kluczy w swojej aplikacji
Przede wszystkim musimy stworzyć niestandardowego Apache HttpClient, który używa naszego magazynu kluczy do połączeń HTTPS:
Stworzyliśmy nasz niestandardowy HttpClient, teraz możemy go używać do bezpiecznych połączeń. Na przykład, gdy wykonujemy wywołanie GET do zasobu REST:
Otóż to ;)
źródło
/res/raw/mykeystore.bks
, chociaż nie mogę rozwiązać odniesienia do niego. jak to rozwiązać?Jeśli masz niestandardowy / samopodpisany certyfikat na serwerze, którego nie ma na urządzeniu, możesz użyć poniższej klasy, aby go załadować i używać po stronie klienta w systemie Android:
Umieść
*.crt
plik certyfikatu w/res/raw
, aby był dostępny zR.raw.*
Użyj poniższej klasy, aby uzyskać
HTTPClient
lub,HttpsURLConnection
która będzie miała fabrykę gniazd używającą tego certyfikatu:Kluczowe punkty:
Certificate
obiekty są generowane z.crt
plików.KeyStore
jest wartość domyślna .keyStore.setCertificateEntry("ca", cert)
dodaje certyfikat do magazynu kluczy pod aliasem „ca”. Modyfikujesz kod, aby dodać więcej certyfikatów (pośredni urząd certyfikacji itp.).SSLSocketFactory
który może być następnie użyty przezHTTPClient
lubHttpsURLConnection
.SSLSocketFactory
można skonfigurować dalej, na przykład w celu pominięcia weryfikacji nazwy hosta itp.Więcej informacji na: http://developer.android.com/training/articles/security-ssl.html
źródło
.crt
pliki? Pobrać z serwera?Byłem sfrustrowany próbą połączenia mojej aplikacji na Androida z usługą RESTful przy użyciu protokołu HTTPS. Byłem też trochę zirytowany wszystkimi odpowiedziami, które sugerowały całkowite wyłączenie sprawdzania certyfikatów. Jeśli to zrobisz, jaki jest sens HTTPS?
Po dłuższym googlowaniu na ten temat w końcu znalazłem to rozwiązanie, w którym nie są potrzebne zewnętrzne jary, tylko Android API. Podziękowania dla Andrew Smitha, który opublikował go w lipcu 2014 roku
To działało dobrze dla mojej makiety aplikacji.
źródło
import java.security.cert.X509Certificate;
Najlepsza odpowiedź mi nie pomogła. Po pewnym dochodzeniu znalazłem wymagane informacje na temat „Android Developer”: https://developer.android.com/training/articles/security-ssl.html#SelfSigned
Utworzenie pustej implementacji X509TrustManager załatwiło sprawę:
Należy pamiętać, że ta pusta implementacja TustManager to tylko przykład, a używanie jej w środowisku produkcyjnym spowodowałoby poważne zagrożenie bezpieczeństwa!
źródło
Google zaleca używanie Android Volley do połączeń HTTP / HTTPS , ponieważ
HttpClient
jest on przestarzały. Znasz więc właściwy wybór :).A także NIGDY NUKE certyfikatów SSL (NIGDY !!!).
Nuke SSL Certificates jest całkowicie sprzeczny z celem SSL, którym jest promowanie bezpieczeństwa . Nie ma sensu używać SSL, jeśli planujesz zbombardować wszystkie otrzymane certyfikaty SSL. Lepszym rozwiązaniem byłoby niestosowanie SSL lub lepszym rozwiązaniem byłoby utworzenie niestandardowej
TrustManager
aplikacji + przy użyciu Android Volley dla połączeń HTTP / HTTPS.Oto Gist, który utworzyłem, z podstawową aplikacją logowania, wykonującą połączenia HTTPS, przy użyciu certyfikatu z podpisem własnym po stronie serwera, zaakceptowanego w aplikacji.
Oto kolejna treść, która może pomóc w tworzeniu samopodpisanych certyfikatów SSL do konfiguracji na serwerze, a także korzystania z certyfikatu w aplikacji. Bardzo ważne: musisz skopiować plik .crt, który został wygenerowany przez powyższy skrypt, do katalogu „raw” z projektu Android.
źródło
Oto jak możesz dodać dodatkowe certyfikaty do swojego magazynu kluczy, aby uniknąć tego problemu: Ufanie wszystkim certyfikatom przy użyciu HttpClient przez HTTPS
Nie będzie monitował użytkownika, tak jak pytasz, ale zmniejszy prawdopodobieństwo, że użytkownik napotka błąd „Niezaufany certyfikat serwera”.
źródło
Najprostszy sposób na utworzenie certyfikatu SSL
Otwórz Firefoksa (przypuszczam, że jest to również możliwe z Chrome, ale jest mi łatwiej z FF)
Odwiedź swoją witrynę programistyczną, korzystając z certyfikatu SSL z podpisem własnym.
Kliknij certyfikat (obok nazwy strony)
Kliknij „Więcej informacji”
Kliknij „Wyświetl certyfikat”
Kliknij „Szczegóły”
Kliknij „Eksportuj ...”
Wybierz „Certyfikat X.509 z łańcuchem (PEM)”, wybierz folder i nazwę, aby go zapisać i kliknij „Zapisz”
Przejdź do wiersza poleceń, do katalogu, w którym pobrałeś plik pem i wykonaj polecenie „openssl x509 -inform PEM -outform DM -in .pem -out .crt”
Skopiuj plik .crt do katalogu głównego folderu / sdcard na urządzeniu z systemem Android W urządzeniu z systemem Android: Ustawienia> Zabezpieczenia> Zainstaluj z pamięci.
Powinien wykryć certyfikat i umożliwić dodanie go do urządzenia. Przejdź do witryny programistycznej.
Za pierwszym razem powinien poprosić o potwierdzenie wyjątku bezpieczeństwa. To wszystko.
Certyfikat powinien działać z każdą przeglądarką zainstalowaną na Twoim Androidzie (Browser, Chrome, Opera, Dolphin ...)
Pamiętaj, że jeśli obsługujesz swoje pliki statyczne z innej domeny (wszyscy jesteśmy sukami szybkości stron), musisz również dodać certyfikat dla tej domeny.
źródło
Napisałem małą bibliotekę ssl-utils-android, aby ufać konkretnemu certyfikatowi na Androida.
Możesz po prostu załadować dowolny certyfikat, podając nazwę pliku z katalogu zasobów.
Stosowanie:
źródło
Żadna z tych poprawek nie działała na mojej platformie deweloperskiej ukierunkowanej na SDK 16, wydanie 4.1.2, więc znalazłem obejście.
Moja aplikacja przechowuje dane na serwerze przy użyciu „ http://www.example.com/page.php?data=somedata ”
Ostatnio page.php został przeniesiony na „ https://www.secure-example.com/page.php ” i ciągle otrzymuję „javax.net.ssl.SSLException: Not trust server certificate”.
Zamiast akceptować wszystkie certyfikaty tylko dla jednej strony, zaczynając od tego przewodnika rozwiązałem swój problem pisząc własną stronę page.php opublikowaną pod adresem " http://www.example.com/page.php "
źródło
19 stycznia 2020 Certyfikat z podpisem własnym POPRAWKA PROBLEMU:
Aby odtworzyć wideo, obraz, wywołać usługę internetową dla dowolnego certyfikatu z podpisem własnym lub połączyć się z dowolnym niezabezpieczonym adresem URL, po prostu wywołaj tę metodę przed wykonaniem jakiejkolwiek czynności, rozwiąże to problem dotyczący problemu z certyfikatem:
KOD KOTLIN
źródło
Może to będzie pomocne ... działa na klientach java używających certyfikatów z podpisem własnym (nie ma sprawdzenia certyfikatu). Bądź ostrożny i używaj go tylko w przypadku programowania, ponieważ nie jest to wcale bezpieczne!
Jak zignorować błędy certyfikatów SSL w Apache HttpClient 4.0
Mam nadzieję, że będzie działać na Androidzie po prostu dodając bibliotekę HttpClient ... powodzenia !!
źródło
Jest to problem wynikający z braku obsługi SNI (Server Name Identification) w A, ndroid 2.x. Zmagałem się z tym problemem przez tydzień, aż trafiłem na następujące pytanie, które nie tylko daje dobre tło problemu, ale także zapewnia działające i skuteczne rozwiązanie pozbawione jakichkolwiek luk w zabezpieczeniach.
Błąd „Brak certyfikatu równorzędnego” w systemie Android 2.3, ale NIE w wersji 4
źródło