سلام دوستان و اساتید عزیز
من پروژه قبلم روش چک اتصال به سرور رو از نظر خودم خیلی بد نوشتم و میخام توی پروژه جدیدم یه روش بهینه و سریع تری رو برای این کار انتخاب و پیاده سازی کنم.
اگه میشه توضیحاتی درباره این که چطوری اتصال به سرور رو چک کنم که سرعتش بهینه ترین باشه؟
قبل از هر کاری باید مجوز ACCESS_NETWORK_STATE و INTERNET رو به برنامه بدین (توی مانیفست) :
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
حالا با این متد میتونین وضعیت اتصال به اینترنت رو بررسی کنید:
public static boolean isOnline() {
ConnectivityManager connectivityManager = (ConnectivityManager) CONTEXT.getSystemService(CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = connectivityManager.getActiveNetworkInfo();
if (networkInfo == null || !networkInfo.isConnected()) {
return false;
}
try {
Process ipProcess = Runtime.getRuntime().exec("/system/bin/ping -c 1 8.8.8.8");
if (ipProcess.waitFor() != 0) {
return false;
}
} catch (IOException | InterruptedException e) {
e.printStackTrace();
}
return true;
}
من خودم شخصاً از این متد توی کلاس App استفاده میکنم. مثالی از نحوهی فراخوانی:
if (App.isOnline()) {
// ...
} else {
Toast.makeText(this, "There is no internet connection available...", Toast.LENGTH_SHORT).show();
}
ACCESS_NETWORK_STATE برای این در اندروید 6 نیازی به گرفتن ران تایم پرمیشن نیست؟
و ایا میشه اینی که شما پینگ گرفتید از 8.8.8.8 از سرور خودمون بگیریم؟
اگه این کار رو بکنیم چه مشکلاتی احتمالش هستش به وجود بیاد؟
خیر این مجوز نیاز به گرفتن Runtime نداره. این تاپیک رو بخونید:
پرمیشن ها در اندروید 6
آدرس IP که نوشتم یعنی 8.8.8.8 متعلق به گوگل هست و معمولاً خیلی سریعتر از سایتهای عادی جواب میده ولی مشکلی نداره که بجاش سایت خودتون رو بنویسید.
داخل یک اکتیویتی این متد رو نوشتم و داخل شرط if (isOnline()) یه درخواست با والی به سرور ارسال کردم که یک آرای جیسون نسبتا کوچکی(اطلاعات 40 سطر 4 ستونه که هرکدوم شامل حداکثر200 کاراکتر هست) رو دریافت میکنم و در ریسایکلر ویو نمایش میدم.و برای else یه توست میدم که "اتصال برقرار نیست" .
سوال اینجاست که وقتی کد رو تست میکنم(بارها و با دستگاههای مختلف تست شده) هم توست رو نشون میده و هم اطلاعات رو دریافت میکنه و ریسایکلر ویو رو پر میکنه و نشون میده.
(در استفاده های دیگه ای از همین متد ،گاها false برمیگرده در حالی که اتصال برقرار هست)
چرا؟
لطفا راهنمایی بفرمایید که ضعف پیاده سازی بنده چی میتونه باشه؟
ممکنه در اون لحظه Timeout داشته باشین. بهتره زمان انتظار رو برای چککردن افزایش بدین. اگه جواب زودتر رسید که خوب حله ولی اگه دیرتر رسید، حداقل تا 10 ثانیه (با توجه به سرعت اینترنت در نقاط مختلف کشور و اپراتورهای مختلف و...) بعنوان زمان انتظار داشته باشین.
ممکنه راجع به ست کردن زمان انتظار بیشتر توضیح بدین.
منظورتون استفاده از broadcast برای اینکه وقتی اتصال برقرار شد اطلاع بده و بعد رکوئست بفرستم ؟و یا مثلا استفاده از ترد و sleep تا وقتی که اتصال برقرار شه و بعد ارسال رکوئست ؟
منظورم اینه که وقتی درخواست اتصال به سرور میدین میتونین زمان انتظار رو مشخص کنین. این زمان رو بیشتر از حالت پیشفرض تعریف کنید.
(10-01-1398، 10:54 ق.ظ)ADMIN نوشته: [ -> ]منظورم اینه که وقتی درخواست اتصال به سرور میدین میتونین زمان انتظار رو مشخص کنین. این زمان رو بیشتر از حالت پیشفرض تعریف کنید.
اول تشکر از شما
الان حداقل 18,000 میلی ثانیه است و حتی 40,000 .
احتمالا مشکل از نحوه پیاده سازی و کدهای منه. با اینکه سینگلتون رکوئست ها رو به صف درخواست های والی اضافه میکنم ولی فکر میکنم یه جای کارم اشتباه یا ناقصه.شاید لازمه گاهی بعضی از رکوئستها رو از صف اجرا حذف کنم؟
اول لاگ سرور رو چک کنید. ممکنه سرورتون مشکلی داره و واقعاً جواب رو در زمان مقرر نمیفرسته. بعد هم پیشنهاد میکنم از Retrofit استفاده کنید. درنهایت بهتره که بهسمت استفاده از روشها و فناوریهای نوین و بروزتر مثل LiveData حرکت کنید.