जांचें कि क्या फ़्लटर ऐप पर इंटरनेट कनेक्शन उपलब्ध है


99

मेरे पास निष्पादन के लिए एक नेटवर्क कॉल है। लेकिन ऐसा करने से पहले मुझे यह जांचना होगा कि डिवाइस में इंटरनेट कनेक्टिविटी है या नहीं।

यह वही है जो मैंने अभी तक किया है:

  var connectivityResult = new Connectivity().checkConnectivity();// User defined class
    if (connectivityResult == ConnectivityResult.mobile ||
        connectivityResult == ConnectivityResult.wifi) {*/
    this.getData();
    } else {
      neverSatisfied();
    }

उपरोक्त विधि काम नहीं कर रही है।

जवाबों:


193

कनेक्टिविटी प्लगइन अपने डॉक्स में कहा गया है कि यह केवल जानकारी प्रदान करता है, अगर वहाँ एक नेटवर्क कनेक्शन है, लेकिन अगर नेटवर्क इंटरनेट से जुड़ा है नहीं

ध्यान दें कि एंड्रॉइड पर, यह इंटरनेट से कनेक्शन की गारंटी नहीं देता है। उदाहरण के लिए, ऐप में वाईफाई की सुविधा हो सकती है, लेकिन यह वीपीएन या होटल वाईफाई हो सकता है, जिसमें कोई एक्सेस न हो।

आप उपयोग कर सकते हैं

import 'dart:io';
...
try {
  final result = await InternetAddress.lookup('google.com');
  if (result.isNotEmpty && result[0].rawAddress.isNotEmpty) {
    print('connected');
  }
} on SocketException catch (_) {
  print('not connected');
}

2
मुझे त्रुटि मिल रही है "इंटरनेट के अंदर कोई खाली घोषित नहीं किया गया है"
रिम्स सुरेश

2
क्या इसे पृष्ठभूमि में हासिल किया जा सकता है? जैसे मेरे पास निष्पादन के लिए लंबित कार्यों की एक कतार है और इंटरनेट के लिए प्रतीक्षा कर रहा है लेकिन ऐप बंद है?
विडोर विस्त्रोम

61
कृपया ध्यान दें कि google.com चीन में अंदर पहुंच योग्य नहीं है और जैसे कि चीन में इस्तेमाल होने पर यह उदाहरण लटका रहेगा। अपने दर्शकों का विस्तार करने के लिए कृपया google.com का उपयोग करने से बचें और इसके बजाय example.com का उपयोग करें। अंतिम परिणाम = प्रतीक्षा करें InternetAddress.lookup ('example.com');
ओटबॉस

4
यह मेरे लिए काम नहीं करता if (result.isNotEmpty && result[0].rawAddress.isNotEmpty)है जब वाईफाई है, लेकिन इंटरनेट कनेक्शन नहीं है।
डेन्न

5
ओह, हाँ, मैं इस बारे में पूरी तरह से भूल गया! वास्तव में मुझे लगता है कि मैं इसका उपयोग awaitकर सकता हूं, मैं इसके .timeoutबाद सिर्फ एपेंड कर सकता हूं lookup()
मिशेल फ़िनस्टीन

73

किसी और के लिए जो यहाँ भूमि मैं गुंटर Zöchbauer के जवाब में जोड़ना चाहते हैं यह मेरे लिए एक उपयोगिता को लागू करने के लिए समाधान था यह जानने के लिए कि इंटरनेट है या नहीं और किसी चीज की परवाह किए बिना।

अस्वीकरण:

मैं डार्ट और स्पंदन दोनों के लिए नया हूं, इसलिए यह सबसे अच्छा तरीका नहीं हो सकता है, लेकिन प्रतिक्रिया प्राप्त करना पसंद करेंगे।


Flutter_connectivity और Günter Zöchbauer का कनेक्शन परीक्षण

मेरी आवश्यकताएं

मैं कनेक्शन की जाँच करने के लिए कहीं भी बार-बार कोड का एक गुच्छा नहीं चाहता था और मैं चाहता था कि यह स्वचालित रूप से घटकों या किसी अन्य चीज को अपडेट करे जो कि जब भी कोई परिवर्तन होता है, तो कनेक्शन के बारे में परवाह करता था।

ConnectionStatusSingleton

पहले हम एक सिंगलटन सेटअप करते हैं। यदि आप इस पैटर्न से अपरिचित हैं, तो उनके बारे में बहुत सारी अच्छी जानकारी ऑनलाइन है। लेकिन सार यह है कि आप अनुप्रयोग जीवन चक्र के दौरान एक वर्ग का एक ही उदाहरण बनाना चाहते हैं और कहीं भी इसका उपयोग करने में सक्षम हो सकते हैं।

यह सिंगलटन flutter_connectivityकनेक्टिविटी में बदलाव के लिए हुक करता है और सुनता है, फिर नेटवर्क कनेक्शन का परीक्षण करता है, फिर किसी StreamControllerभी चीज़ को अपडेट करने के लिए उपयोग करता है।

यह इस तरह दिख रहा है:

import 'dart:io'; //InternetAddress utility
import 'dart:async'; //For StreamController/Stream

import 'package:connectivity/connectivity.dart';

class ConnectionStatusSingleton {
    //This creates the single instance by calling the `_internal` constructor specified below
    static final ConnectionStatusSingleton _singleton = new ConnectionStatusSingleton._internal();
    ConnectionStatusSingleton._internal();

    //This is what's used to retrieve the instance through the app
    static ConnectionStatusSingleton getInstance() => _singleton;

    //This tracks the current connection status
    bool hasConnection = false;

    //This is how we'll allow subscribing to connection changes
    StreamController connectionChangeController = new StreamController.broadcast();

    //flutter_connectivity
    final Connectivity _connectivity = Connectivity();

    //Hook into flutter_connectivity's Stream to listen for changes
    //And check the connection status out of the gate
    void initialize() {
        _connectivity.onConnectivityChanged.listen(_connectionChange);
        checkConnection();
    }

    Stream get connectionChange => connectionChangeController.stream;

    //A clean up method to close our StreamController
    //   Because this is meant to exist through the entire application life cycle this isn't
    //   really an issue
    void dispose() {
        connectionChangeController.close();
    }

    //flutter_connectivity's listener
    void _connectionChange(ConnectivityResult result) {
        checkConnection();
    }

    //The test to actually see if there is a connection
    Future<bool> checkConnection() async {
        bool previousConnection = hasConnection;

        try {
            final result = await InternetAddress.lookup('google.com');
            if (result.isNotEmpty && result[0].rawAddress.isNotEmpty) {
                hasConnection = true;
            } else {
                hasConnection = false;
            }
        } on SocketException catch(_) {
            hasConnection = false;
        }

        //The connection status changed send out an update to all listeners
        if (previousConnection != hasConnection) {
            connectionChangeController.add(hasConnection);
        }

        return hasConnection;
    }
}

प्रयोग

प्रारंभ

पहले हमें यह सुनिश्चित करना होगा कि हम अपने सिंगलटन के इनिशियलाइज़ को कॉल करें। लेकिन केवल एक बार। यह आपके ऊपर है लेकिन मैंने इसे अपने ऐप में किया है main():

void main() {
    ConnectionStatusSingleton connectionStatus = ConnectionStatusSingleton.getInstance();
    connectionStatus.initialize();

    runApp(MyApp());

    //Call this if initialization is occuring in a scope that will end during app lifecycle
    //connectionStatus.dispose();   
}

में Widgetया कहीं और

import 'dart:async'; //For StreamSubscription

...

class MyWidgetState extends State<MyWidget> {
    StreamSubscription _connectionChangeStream;

    bool isOffline = false;

    @override
    initState() {
        super.initState();

        ConnectionStatusSingleton connectionStatus = ConnectionStatusSingleton.getInstance();
        _connectionChangeStream = connectionStatus.connectionChange.listen(connectionChanged);
    }

    void connectionChanged(dynamic hasConnection) {
        setState(() {
            isOffline = !hasConnection;
        });
    }

    @override
    Widget build(BuildContext ctxt) {
        ...
    }
}

आशा है कि किसी और को यह उपयोगी लगता है!


उदाहरण github repo: https://github.com/dennmat/flutter-connectiontest-example

परिणाम देखने के लिए एमुलेटर में हवाई जहाज मोड को टॉगल करें


2
कोड का परीक्षण किया और यह मेरे लिए काम कर रहा है मुझे मदद करने के लिए अधिक जानकारी की आवश्यकता होगी।
dennmat

3
आह, ठीक है मैं इसे देखता हूं। तो आपके भविष्य के संदर्भ के लिए आपके द्वारा पोस्ट की जा रही त्रुटि केवल उस फ़ाइल को खोलने की कोशिश करने वाले संपादक की है जहां यह लगता है कि त्रुटि हुई है। असली त्रुटि आपके संपादकों के डिबग कंसोल / स्टैक ट्रेस पैनल में उपलब्ध होनी चाहिए। इसलिए मुझे लगता है कि रनएप रिटर्न मुझे लगता है कि यह कार्यक्रमों की संपूर्णता के लिए चलेगा। यह देखना मुख्य रूप से है कि डिस्पोज़ वास्तव में आवश्यक नहीं है, इसलिए connectionStatus.dispose()यह मान लें कि आप इसे ऊपर की main()तरह सेट कर रहे हैं । पोस्ट को अपडेट करेंगे और जीथब उदाहरण से लिंक करेंगे।
dennmat

1
बस यह पता लगाने के लिए कि वाईफाई या सेल्यूलर स्विच किया जा रहा है या नहीं, आपको केवल फ़्लटर कनेक्टिविटी चाहिए। यह आवरण स्विच होने के बाद कनेक्शन की जाँच करता है। लेकिन हर नेटवर्क परिवर्तन के प्रति सतर्क नहीं होंगे। यदि आप एमुलेटर टॉगल कर रहे हैं तो हवाई जहाज मोड इंटरनेट कनेक्शन खोने का सबसे आसान तरीका है। यदि आप एक वास्तविक डिवाइस पर हैं, तो आपको यह सुनिश्चित करना होगा कि आप अभी भी डेटा के साथ मोबाइल नेटवर्क से कनेक्ट नहीं थे।
डेन्मेट

1
इसके लिए कुछ विकल्प हैं, आप बार-बार परीक्षण करने के लिए टाइमर का उपयोग करने के लिए ऊपर संशोधित कर सकते हैं। या सिर्फ टाइमर उपयोगिता का उपयोग करके अक्सर परीक्षण करें। देखें: api.dartlang.org/stable/2.1.0/dart-async/Timer-class.html एक अन्य विकल्प आपके द्वारा भेजे जाने वाले प्रत्येक अनुरोध से पहले कनेक्शन का परीक्षण कर रहा है। यद्यपि ऐसा लगता है कि आप वेबसोकेट जैसी किसी चीज़ की तलाश में हैं। वैसे भी सौभाग्य
dennmat

3
क्या हमें विजेट के निपटान () फ़ंक्शन में सदस्यता रद्द नहीं करनी चाहिए? मैं देख रहा हूँ यह अन्य StreamController उदाहरणों में यहाँ किया गया है: stackoverflow.com/questions/44788256/updating-data-in-flutter
Oren

41

यहाँ छवि विवरण दर्ज करें

पूर्ण उदाहरण इंटरनेट कनेक्टिविटी और इसके स्रोत के एक श्रोता को प्रदर्शित करता है।

क्रेडिट: कनेक्टिविटी और गुंटर ज़ोचबॉयर

import 'dart:async';
import 'dart:io';
import 'package:connectivity/connectivity.dart';
import 'package:flutter/material.dart';

void main() => runApp(MaterialApp(home: HomePage()));

class HomePage extends StatefulWidget {
  @override
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
  Map _source = {ConnectivityResult.none: false};
  MyConnectivity _connectivity = MyConnectivity.instance;

  @override
  void initState() {
    super.initState();
    _connectivity.initialise();
    _connectivity.myStream.listen((source) {
      setState(() => _source = source);
    });
  }

  @override
  Widget build(BuildContext context) {
    String string;
    switch (_source.keys.toList()[0]) {
      case ConnectivityResult.none:
        string = "Offline";
        break;
      case ConnectivityResult.mobile:
        string = "Mobile: Online";
        break;
      case ConnectivityResult.wifi:
        string = "WiFi: Online";
    }

    return Scaffold(
      appBar: AppBar(title: Text("Internet")),
      body: Center(child: Text("$string", style: TextStyle(fontSize: 36))),
    );
  }

  @override
  void dispose() {
    _connectivity.disposeStream();
    super.dispose();
  }
}

class MyConnectivity {
  MyConnectivity._internal();

  static final MyConnectivity _instance = MyConnectivity._internal();

  static MyConnectivity get instance => _instance;

  Connectivity connectivity = Connectivity();

  StreamController controller = StreamController.broadcast();

  Stream get myStream => controller.stream;

  void initialise() async {
    ConnectivityResult result = await connectivity.checkConnectivity();
    _checkStatus(result);
    connectivity.onConnectivityChanged.listen((result) {
      _checkStatus(result);
    });
  }

  void _checkStatus(ConnectivityResult result) async {
    bool isOnline = false;
    try {
      final result = await InternetAddress.lookup('example.com');
      if (result.isNotEmpty && result[0].rawAddress.isNotEmpty) {
        isOnline = true;
      } else
        isOnline = false;
    } on SocketException catch (_) {
      isOnline = false;
    }
    controller.sink.add({result: isOnline});
  }

  void disposeStream() => controller.close();
}

फायरबेस के माध्यम से, एसडीके क्या यह संभव है?
LOG_TAG

@LOG_TAG आपको इसके लिए Firebase का उपयोग करने की आवश्यकता नहीं है।
CopsOnRoad

1
@CopsOnRoad आपका बहुत बहुत धन्यवाद। आपने मेरा समय बचाया।
निमिषा रानीपा

मानचित्र _source = {ConnectivityResult.none: false}; आपने यहाँ "झूठे" का इस्तेमाल क्यों किया
फारुक आयुदिन

@CopsOnRoad धन्यवाद! मैंने इस पद्धति का उपयोग किया है, लेकिन यह विधि मुझे पहली बार NoInternetConnection देती है! मुझे पहले क्यों नहीं दिया? यह मेरा डिबग प्रिंट है: connectResult.none कनेक्टिविटी।
फारुक आयुदिन

23

मैंने पाया कि कनेक्टिविटी पैकेज का उपयोग करना केवल यह बताने के लिए पर्याप्त नहीं था कि इंटरनेट उपलब्ध था या नहीं। एंड्रॉइड में यह केवल यह जांचता है कि क्या WIFI है या यदि मोबाइल डेटा चालू है, तो यह एक वास्तविक इंटरनेट कनेक्शन की जांच नहीं करता है। मेरे परीक्षण के दौरान, यहां तक ​​कि मोबाइल सिग्नल के साथ ConnectivityResult.mobile सच नहीं होगा।

IOS के साथ मेरे परीक्षण में पाया गया कि कनेक्टिविटी प्लगइन सही ढंग से पता लगाता है कि क्या कोई इंटरनेट कनेक्शन है जब फोन में कोई संकेत नहीं है, तो समस्या केवल एंड्रॉइड के साथ थी।

मुझे जो समाधान मिला वह कनेक्टिविटी पैकेज के साथ data_connection_checker पैकेज का उपयोग करना था । यह सिर्फ यह सुनिश्चित करता है कि कुछ विश्वसनीय पतों के लिए अनुरोध करके एक इंटरनेट कनेक्शन है, चेक के लिए डिफ़ॉल्ट टाइमआउट लगभग 10 सेकंड है।

मेरा समाप्त हो गया है इनरनेट फ़ंक्शन कुछ इस तरह दिखता है:

  Future<bool> isInternet() async {
    var connectivityResult = await (Connectivity().checkConnectivity());
    if (connectivityResult == ConnectivityResult.mobile) {
      // I am connected to a mobile network, make sure there is actually a net connection.
      if (await DataConnectionChecker().hasConnection) {
        // Mobile data detected & internet connection confirmed.
        return true;
      } else {
        // Mobile data detected but no internet connection found.
        return false;
      }
    } else if (connectivityResult == ConnectivityResult.wifi) {
      // I am connected to a WIFI network, make sure there is actually a net connection.
      if (await DataConnectionChecker().hasConnection) {
        // Wifi detected & internet connection confirmed.
        return true;
      } else {
        // Wifi detected but no internet connection found.
        return false;
      }
    } else {
      // Neither mobile data or WIFI detected, not internet connection found.
      return false;
    }
  }

if (await DataConnectionChecker().hasConnection)भाग दोनों मोबाइल और वाईफाई कनेक्शन के लिए एक ही है और शायद एक अलग कार्य करने के लिए ले जाया जाना चाहिए। मैंने ऐसा यहां नहीं किया है ताकि इसे और अधिक पठनीय बना सकूं।

यह मेरा पहला स्टैक ओवरफ्लो उत्तर है, आशा है कि यह किसी की मदद करता है।


1
Stackoverflow में आपका स्वागत है। बस सोच रहा था, सिर्फ await DataConnectionChecker().hasConnectionपहली जगह का उपयोग करने पर क्या फायदा है?
हरबर्ट

2
एकमात्र कारण यह है कि IOS पर कनेक्टिविटी पैकेज बहुत तुरंत बता सकता है कि कोई कनेक्शन नहीं है। यदि मैंने अभी data_connection_checker पैकेज का उपयोग किया है, तो IOS पर एप्लिकेशन को प्रतीक्षा करनी होगी जब तक कि http अनुरोध यह 10 मिनट के आसपास, समय पर वापस करने से पहले, झूठे वापस आने से पहले। हालांकि यह कुछ मामलों में स्वीकार्य हो सकता है। कनेक्टिविटी पैकेज यह भी बता सकता है कि क्या आप WIFI या मोबाइल डेटा का उपयोग कर रहे हैं, जिसे मुझे यहां जानने की आवश्यकता नहीं है, लेकिन यह जानना उपयोगी हो सकता है।
11

यह उपरोक्त कोड में कुछ सिंटैक्स संशोधन के साथ पूरी तरह से काम करता है। 1. आपको भविष्य <bool> को भविष्य <bool>) में बदलने की आवश्यकता है, क्योंकि प्रकार लोअरकेस हैं। 2. 4 वें अंतिम रिटर्न स्टेटमेंट के लिए अर्धविराम (;) जोड़ें।
TDM

धन्यवाद TDM, मैंने आपके संशोधनों के साथ उत्तर संपादित किया है।
10

20

का उपयोग करते हुए

dependencies:
  connectivity: ^0.4.2

हमें रिसॉइसेस से जो मिला है

      import 'package:connectivity/connectivity.dart';

      Future<bool> check() async {
        var connectivityResult = await (Connectivity().checkConnectivity());
        if (connectivityResult == ConnectivityResult.mobile) {
          return true;
        } else if (connectivityResult == ConnectivityResult.wifi) {
          return true;
        }
        return false;
      }

भविष्य मेरे लिए थोड़ा समस्याग्रस्त है, हमें इसे हर बार लागू करना होगा जैसे:

check().then((intenet) {
      if (intenet != null && intenet) {
        // Internet Present Case
      }
      // No-Internet Case
    });

तो इस समस्या को हल करने के लिए मैंने एक वर्ग बनाया है जो बूलियन isNetworkPresent पैरामीटर के साथ एक फ़ंक्शन को इस तरह स्वीकार करता है

methodName(bool isNetworkPresent){}

और यूटिलिटी क्लास है

import 'package:connectivity/connectivity.dart';

class NetworkCheck {
  Future<bool> check() async {
    var connectivityResult = await (Connectivity().checkConnectivity());
    if (connectivityResult == ConnectivityResult.mobile) {
      return true;
    } else if (connectivityResult == ConnectivityResult.wifi) {
      return true;
    }
    return false;
  }

  dynamic checkInternet(Function func) {
    check().then((intenet) {
      if (intenet != null && intenet) {
        func(true);
      }
      else{
    func(false);
  }
    });
  }
}

और कनेक्टिविटी-चेक उपयोगिता का उपयोग करने के लिए

  fetchPrefrence(bool isNetworkPresent) {
    if(isNetworkPresent){

    }else{

    }
  }

मैं इस वाक्यविन्यास का उपयोग करूंगा

NetworkCheck networkCheck = new NetworkCheck();
networkCheck.checkInternet(fetchPrefrence)

6

मैंने एक पैकेज बनाया है (मुझे लगता है) इस मुद्दे के साथ मज़बूती से पेश आता है।

पब पर पैकेज ।देव

GitHub पर पैकेज

चर्चा का बहुत स्वागत है। आप GitHub पर समस्या ट्रैकर का उपयोग कर सकते हैं।


मुझे नहीं लगता कि यह नीचे एक विश्वसनीय तरीका है:


@ ऑरेन के उत्तर में कुछ जोड़ना चाहते हैं : आपको वास्तव में एक और कैच जोड़ना चाहिए, जो अन्य सभी अपवादों को पकड़ेगा (बस सुरक्षित रहने के लिए), या केवल अपवाद प्रकार को पूरी तरह से हटा दें और एक कैच का उपयोग करें, जो सभी अपवादों से संबंधित है:

मामला एक:

try {
  await Firestore.instance
    .runTransaction((Transaction tx) {})
    .timeout(Duration(seconds: 5));
  hasConnection = true;
} on PlatformException catch(_) { // May be thrown on Airplane mode
  hasConnection = false;
} on TimeoutException catch(_) {
  hasConnection = false;
} catch (_) {
  hasConnection = false;
}

या और भी सरल ...

केस 2:


try {
  await Firestore.instance
    .runTransaction((Transaction tx) {})
    .timeout(Duration(seconds: 5));
  hasConnection = true;
} catch (_) {
  hasConnection = false;
}

5

मैंने विजेट स्टेट के लिए बेस क्लास बनाया

उपयोग के बजाय State<LoginPage>उपयोग करें BaseState<LoginPage> तो बस बूलियन चर isOnline का उपयोग करें

Text(isOnline ? 'is Online' : 'is Offline')

सबसे पहले, कनेक्टिविटी प्लगइन जोड़ें:

dependencies:
  connectivity: ^0.4.3+2

फिर BaseState वर्ग जोड़ें

import 'dart:async';
import 'dart:io';
import 'package:flutter/services.dart';

import 'package:connectivity/connectivity.dart';
import 'package:flutter/widgets.dart';

/// a base class for any statful widget for checking internet connectivity
abstract class BaseState<T extends StatefulWidget> extends State {

  void castStatefulWidget();

  final Connectivity _connectivity = Connectivity();

  StreamSubscription<ConnectivityResult> _connectivitySubscription;

  /// the internet connectivity status
  bool isOnline = true;

  /// initialize connectivity checking
  /// Platform messages are asynchronous, so we initialize in an async method.
  Future<void> initConnectivity() async {
    // Platform messages may fail, so we use a try/catch PlatformException.
    try {
      await _connectivity.checkConnectivity();
    } on PlatformException catch (e) {
      print(e.toString());
    }

    // If the widget was removed from the tree while the asynchronous platform
    // message was in flight, we want to discard the reply rather than calling
    // setState to update our non-existent appearance.
    if (!mounted) {
      return;
    }

    await _updateConnectionStatus().then((bool isConnected) => setState(() {
          isOnline = isConnected;
        }));
  }

  @override
  void initState() {
    super.initState();
    initConnectivity();
    _connectivitySubscription = Connectivity()
        .onConnectivityChanged
        .listen((ConnectivityResult result) async {
      await _updateConnectionStatus().then((bool isConnected) => setState(() {
            isOnline = isConnected;
          }));
    });
  }

  @override
  void dispose() {
    _connectivitySubscription.cancel();
    super.dispose();
  }

  Future<bool> _updateConnectionStatus() async {
    bool isConnected;
    try {
      final List<InternetAddress> result =
          await InternetAddress.lookup('google.com');
      if (result.isNotEmpty && result[0].rawAddress.isNotEmpty) {
        isConnected = true;
      }
    } on SocketException catch (_) {
      isConnected = false;
      return false;
    }
    return isConnected;
  }
}

और आपको इस तरह से अपने राज्य में विजेट डालना होगा

@override
  void castStatefulWidget() {
    // ignore: unnecessary_statements
    widget is StudentBoardingPage;
  }

2
मैं इस वर्ग का उपयोग कैसे कर सकता हूं?
DolDurma

@DolDurma बस इसे जोड़ें और इसे फिर स्टेट करें <LoginPage> के बजाय BaseState <LoginPage> का उपयोग करें और फिर बूलियन वैरिएबल isOnline
amorenew

इस कोड के साथ मैं से valiables नहीं मिल सकता है widget। उदाहरण के लिए: RegisterBloc get _registerBloc => widget.registerBloc;मुझे यह त्रुटि error: The getter 'registerBloc' isn't defined for the class 'StatefulWidget'. (undefined_getter at lib\screens\fragmemt_register\view\register_mobile_number.dart:29)देखने को मिलती है, यह देखें:class _FragmentRegisterMobileNumberState extends BaseState<FragmentRegisterMobileNumber> with SingleTickerProviderStateMixin { RegisterBloc get _registerBloc => widget.registerBloc;
DolDurma

@DolDurma मुझे यकीन नहीं है कि एक GitHub नमूने के बिना क्या समस्या है क्योंकि यह जानकारी पर्याप्त नहीं है
amorenew

1
कृपया इस रेपो की जांच करें और मुझे बताएं कि मैं is_onlineकंसोल में लॉग इन करने के लिए कैसे उपयोग कर सकता हूं github.com/MahdiPishguy/flutter-connectivity-sample
DolDurma

3

@Dennmatt के उत्तर के बाद , मैंने देखा कि InternetAddress.lookupसफल परिणाम वापस आ सकते हैं भले ही इंटरनेट कनेक्शन बंद हो - मैंने अपने सिम्युलेटर से अपने होम वाईफाई से कनेक्ट करके इसका परीक्षण किया, और फिर अपने राउटर के केबल को डिस्कनेक्ट कर दिया। मुझे लगता है कि इसका कारण यह है कि राउटर डोमेन-लुकअप परिणामों को कैश करता है, इसलिए इसे प्रत्येक लुकअप अनुरोध पर DNS सर्वर को क्वेरी नहीं करना पड़ता है।

वैसे भी, अगर आप मेरी तरह फायरस्टार का उपयोग करते हैं, तो आप खाली लेनदेन के साथ कोशिश-सॉकेटएक्सपेप्शन-कैच ब्लॉक की जगह ले सकते हैं और टाइमआउट एक्सेप्शन को पकड़ सकते हैं:

try {
  await Firestore.instance.runTransaction((Transaction tx) {}).timeout(Duration(seconds: 5));
  hasConnection = true;
} on PlatformException catch(_) { // May be thrown on Airplane mode
  hasConnection = false;
} on TimeoutException catch(_) {
  hasConnection = false;
}

इसके अलावा, कृपया ध्यान दें कि previousConnectionयह async intenet-check से पहले सेट किया गया है, इसलिए सैद्धांतिक रूप से अगर checkConnection()इसे कम समय में कई बार कहा जाता है , तो hasConnection=trueएक पंक्ति में कई या एक पंक्ति में कई हो सकते हैं hasConnection=false। मुझे यकीन नहीं है कि @dennmatt ने इसे उद्देश्य पर किया था या नहीं, लेकिन हमारे उपयोग-मामले में कोई दुष्प्रभाव नहीं थे ( setStateकेवल एक ही मूल्य के साथ दो बार कहा गया था)।


3

कनेक्टिविटी: पैकेज वास्तविक इंटरनेट कनेक्शन की गारंटी नहीं देता है (इंटरनेट एक्सेस के बिना सिर्फ वाईफाई कनेक्शन हो सकता है)।

प्रलेखन से उद्धरण:

ध्यान दें कि एंड्रॉइड पर, यह इंटरनेट से कनेक्शन की गारंटी नहीं देता है। उदाहरण के लिए, ऐप में वाईफाई की सुविधा हो सकती है, लेकिन यह वीपीएन या होटल वाईफाई हो सकता है, जिसमें कोई एक्सेस न हो।

अगर आपको वास्तव में www इंटरनेट से कनेक्शन की जांच करने की आवश्यकता है तो बेहतर विकल्प होगा

data_connection_checker पैकेज


1

यहाँ मेरा समाधान है यह इंटरनेट कनेक्टिविटी और साथ ही डेटा कनेक्शन की जाँच करता है मुझे आशा है कि आप इसे पसंद करेंगे।

सबसे पहले अपने pubsec.yaml में निर्भरता जोड़ें
dependencies:        
    data_connection_checker:
और यहाँ मेरे समाधान का main.dart है
import 'dart:async';

import 'package:data_connection_checker/data_connection_checker.dart';
import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: "Data Connection Checker",
      home: HomePage(),
    );
  }
}

class HomePage extends StatefulWidget {
  @override
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
  StreamSubscription<DataConnectionStatus> listener;

  var Internetstatus = "Unknown";

  @override
  void initState() {
    // TODO: implement initState
    super.initState();
//    _updateConnectionStatus();
      CheckInternet();
  }

  @override
  void dispose() {
    // TODO: implement dispose
    listener.cancel();
    super.dispose();
  }

  CheckInternet() async {
    // Simple check to see if we have internet
    print("The statement 'this machine is connected to the Internet' is: ");
    print(await DataConnectionChecker().hasConnection);
    // returns a bool

    // We can also get an enum instead of a bool
    print("Current status: ${await DataConnectionChecker().connectionStatus}");
    // prints either DataConnectionStatus.connected
    // or DataConnectionStatus.disconnected

    // This returns the last results from the last call
    // to either hasConnection or connectionStatus
    print("Last results: ${DataConnectionChecker().lastTryResults}");

    // actively listen for status updates
    listener = DataConnectionChecker().onStatusChange.listen((status) {
      switch (status) {
        case DataConnectionStatus.connected:
          Internetstatus="Connectd TO THe Internet";
          print('Data connection is available.');
          setState(() {

          });
          break;
        case DataConnectionStatus.disconnected:
          Internetstatus="No Data Connection";
          print('You are disconnected from the internet.');
          setState(() {

          });
          break;
      }
    });

    // close listener after 30 seconds, so the program doesn't run forever
//    await Future.delayed(Duration(seconds: 30));
//    await listener.cancel();
    return await await DataConnectionChecker().connectionStatus;
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text("Data Connection Checker"),
      ),
      body: Container(
        child: Center(
          child: Text("$Internetstatus"),
        ),
      ),
    );
  }
}

1

मेरे पास प्रस्तावित समाधान के साथ एक मुद्दा था, lookupहमेशा अपेक्षित मूल्य वापस नहीं करता है।

यह डीएनएस कैशिंग के कारण है, कॉल का मूल्य कैश किया गया है और अगली कोशिश पर एक उचित कॉल करने का इरादा है यह कैश्ड मान को वापस देता है। बेशक यह यहां एक मुद्दा है क्योंकि इसका मतलब है कि अगर आप कनेक्टिविटी खो देते हैं और कॉल करते हैं तो lookupयह कैश मूल्य को वापस कर सकता है जैसे कि आपके पास इंटरनेट था, और इसके विपरीत, यदि आप अपने इंटरनेट को फिर से कनेक्ट करते हैंlookup वापस लौटा दिया है यह अभी भी अवधि के लिए शून्य हो जाएगा। कैश, जो कुछ मिनट हो सकता है, भले ही आपके पास अभी इंटरनेट हो।

TL; DR: lookupकुछ लौटाना जरूरी नहीं है कि आपके पास इंटरनेट है, और यह कुछ भी वापस नहीं करता है जरूरी नहीं कि आपके पास इंटरनेट नहीं है। यह विश्वसनीय नहीं है।

मैंने data_connection_checkerप्लगइन से प्रेरणा लेकर निम्नलिखित समाधान लागू किया है :

 /// If any of the pings returns true then you have internet (for sure). If none do, you probably don't.
  Future<bool> _checkInternetAccess() {
    /// We use a mix of IPV4 and IPV6 here in case some networks only accept one of the types.
    /// Only tested with an IPV4 only network so far (I don't have access to an IPV6 network).
    final List<InternetAddress> dnss = [
      InternetAddress('8.8.8.8', type: InternetAddressType.IPv4), // Google
      InternetAddress('2001:4860:4860::8888', type: InternetAddressType.IPv6), // Google
      InternetAddress('1.1.1.1', type: InternetAddressType.IPv4), // CloudFlare
      InternetAddress('2606:4700:4700::1111', type: InternetAddressType.IPv6), // CloudFlare
      InternetAddress('208.67.222.222', type: InternetAddressType.IPv4), // OpenDNS
      InternetAddress('2620:0:ccc::2', type: InternetAddressType.IPv6), // OpenDNS
      InternetAddress('180.76.76.76', type: InternetAddressType.IPv4), // Baidu
      InternetAddress('2400:da00::6666', type: InternetAddressType.IPv6), // Baidu
    ];

    final Completer<bool> completer = Completer<bool>();

    int callsReturned = 0;
    void onCallReturned(bool isAlive) {
      if (completer.isCompleted) return;

      if (isAlive) {
        completer.complete(true);
      } else {
        callsReturned++;
        if (callsReturned >= dnss.length) {
          completer.complete(false);
        }
      }
    }

    dnss.forEach((dns) => _pingDns(dns).then(onCallReturned));

    return completer.future;
  }

  Future<bool> _pingDns(InternetAddress dnsAddress) async {
    const int dnsPort = 53;
    const Duration timeout = Duration(seconds: 3);

    Socket socket;
    try {
      socket = await Socket.connect(dnsAddress, dnsPort, timeout: timeout);
      socket?.destroy();
      return true;
    } on SocketException {
      socket?.destroy();
    }
    return false;
  }

पूरा करने _checkInternetAccessके timeoutलिए कॉल की अवधि पूरी होने में (यहाँ पर 3 सेकंड), और अगर हम किसी भी DNS तक पहुँच सकते हैं तो यह पहले जैसे ही पूरा हो जाएगा, दूसरों की प्रतीक्षा किए बिना (जैसा कि एक तक पहुँचने के लिए पर्याप्त है) पता है आपके पास इंटरनेट है)। सभी को फोन किया_pingDns समानांतर में किए जाते हैं।

यह IPV4 नेटवर्क पर अच्छी तरह से काम करता है, और जब मैं इसे IPV6 नेटवर्क पर परीक्षण नहीं कर सकता (मुझे एक तक पहुंच नहीं है) मुझे लगता है कि इसे अभी भी काम करना चाहिए। यह रिलीज़ मोड बिल्ड पर भी काम करता है, लेकिन मुझे अभी भी ऐप्पल को अपना ऐप सबमिट करना है ताकि यह देखा जा सके कि उन्हें इस समाधान के साथ कोई समस्या मिलती है या नहीं।

यह अधिकांश देशों (चीन सहित) में भी काम करना चाहिए, यदि यह एक में काम नहीं करता है तो आप एक डीएनएस को उस सूची में जोड़ सकते हैं जो आपके लक्षित देश से सुलभ है।


1

मैं अंततः ( हालांकि अनिच्छा से ) इस प्रश्न के पिछले उत्तर में @abernee द्वारा दिए गए समाधान पर बस गया । मैं हमेशा अपनी परियोजनाओं में संभव के रूप में कुछ बाहरी पैकेजों का उपयोग करता हूं - जैसा कि मुझे पता है कि मेरे द्वारा बनाए गए सॉफ़्टवेयर में विफलता के केवल बाहरी पैकेज [संभावित] बिंदु हैं। तो सिर्फ इस तरह से एक सरल कार्यान्वयन के लिए TWO बाहरी पैकेज से लिंक करना मेरे लिए आसान नहीं था ।

फिर भी, मैंने abernee का कोड लिया और इसे दुबला और अधिक समझदार बनाने के लिए इसे संशोधित किया। समझदार मेरा मतलब है कि वह अपने समारोह में कनेक्टिविटी पैकेज की शक्ति का उपभोग करता है, लेकिन फिर इस पैकेज (यानी नेटवर्क पहचान) से सबसे मूल्यवान आउटपुट वापस नहीं करके इसे आंतरिक रूप से बर्बाद करता है। तो यहाँ अबर्नी के समाधान का संशोधित संस्करण है:

import 'package:connectivity/connectivity.dart';
import 'package:data_connection_checker/data_connection_checker.dart';


// 'McGyver' - the ultimate cool guy (the best helper class any app can ask for).
class McGyver {

  static Future<Map<String, dynamic>> checkInternetAccess() async {
    //* ////////////////////////////////////////////////////////////////////////////////////////// *//
    //*   INFO: ONLY TWO return TYPES for Map 'dynamic' value => <bool> and <ConnectivityResult>   *//
    //* ////////////////////////////////////////////////////////////////////////////////////////// *//
    Map<String, dynamic> mapCon;
    final String isConn = 'isConnected', netType = 'networkType';
    ConnectivityResult conRes = await (Connectivity().checkConnectivity());
    switch (conRes) {
      case ConnectivityResult.wifi:   //* WiFi Network: true !!
        if (await DataConnectionChecker().hasConnection) {   //* Internet Access: true !!
          mapCon = Map.unmodifiable({isConn: true, netType: ConnectivityResult.wifi});
        } else {
          mapCon = Map.unmodifiable({isConn: false, netType: ConnectivityResult.wifi});
        }
        break;
      case ConnectivityResult.mobile:   //* Mobile Network: true !!
        if (await DataConnectionChecker().hasConnection) {   //* Internet Access: true !!
          mapCon = Map.unmodifiable({isConn: true, netType: ConnectivityResult.mobile});
        } else {
          mapCon = Map.unmodifiable({isConn: false, netType: ConnectivityResult.mobile});
        }
        break;
      case ConnectivityResult.none:   //* No Network: true !!
        mapCon = Map.unmodifiable({isConn: false, netType: ConnectivityResult.none});
        break;
    }
    return mapCon;
  }

}

फिर आप अपने कोड में कहीं से भी एक साधारण कॉल के माध्यम से इस स्थिर फ़ंक्शन का उपयोग करेंगे:

bool isConn; ConnectivityResult netType;
McGyver.checkInternetAccess().then(
  (mapCIA) {  //* 'mapCIA' == amalgamation for 'map' from 'CheckInternetAccess' function result.
    debugPrint("'mapCIA' Keys: ${mapCIA.keys}");
    isConn = mapCIA['isConnected'];
    netType = mapCIA['networkType'];
  }
);
debugPrint("Internet Access: $isConn   |   Network Type: $netType");

यह एक अफ़सोस की बात है कि आपको अपने फ़्लटर प्रोजेक्ट में यह बहुत ही बुनियादी कार्यक्षमता प्राप्त करने के लिए TWO EXTERNAL PACKAGES से लिंक करना होगा - लेकिन मुझे लगता है कि अब हमारे लिए यह सबसे अच्छा है। मैं वास्तव में पसंद करते हैं डेटा कनेक्शन परीक्षक से अधिक पैकेज कनेक्टिविटी पैकेज - लेकिन (यह पोस्टिंग के समय) पूर्व कि बहुत महत्वपूर्ण याद आ रही थी नेटवर्क पहचान सुविधा है कि मैं कनेक्टिविटी पैकेज से की आवश्यकता है। यही कारण है कि मैं इस दृष्टिकोण पर [अस्थायी रूप से] चूक गया।


0

बस फ़्लटर में कनेक्टिविटी पैकेज का उपयोग करके कोड को सरल बनाने की कोशिश की जा रही है ।

import 'package:connectivity/connectivity.dart';

var connectivityResult = await (Connectivity().checkConnectivity());
if (connectivityResult == ConnectivityResult.mobile) {
  // I am connected to a mobile network.
} else if (connectivityResult == ConnectivityResult.wifi) {
  // I am connected to a wifi network.
} else {
  // I am not connected to the internet
}

Android पर इसके साथ समस्या यह है कि सिर्फ इसलिए कि आप वाईफ़ाई या मोबाइल के माध्यम से जुड़े हुए हैं, इसका मतलब यह नहीं है कि आप इंटरनेट से जुड़े हैं।
मेगाडेक

1
@Megadec दुख की बात है हाँ ही समस्या है :(
devDeejay

0

देर से जवाब, लेकिन जाँच करने के लिए इस पैकेज का उपयोग करें। पैकेज का नाम: data_connection_checker

आप में pubspec.yuml फ़ाइल:

dependencies:
    data_connection_checker: ^0.3.4

कनेक्शन नामक एक फ़ाइल बनाएँ। पैकेज आयात करें:

import 'package:data_connection_checker/data_connection_checker.dart';

जांचें कि इंटरनेट कनेक्शन है या नहीं:

print(await DataConnectionChecker().hasConnection);

0

मैंने इंटरनेट एक्सेस की जांच करने के लिए data_connection_checker पैकेज का उपयोग किया, भले ही वाईफाई या मोबाइल द्वारा उपलब्ध कनेक्शन, यह अच्छी तरह से काम करता है: यहां कनेक्शन की जांच करने के लिए कोड है:

bool result = await DataConnectionChecker().hasConnection;
if(result == true) {
   print('YAY! Free cute dog pics!');
} else {
   print('No internet :( Reason:');
   print(DataConnectionChecker().lastTryResults);
}

यदि आप अधिक जानकारी चाहते हैं तो पैकेज पर जाएं। डेटा कनेक्शन परीक्षक पैकेज


0

मुझे स्वीकृत उत्तर से कुछ समस्या हो रही है, लेकिन ऐसा लगता है कि यह दूसरों के लिए उत्तर को हल करता है। मैं एक ऐसा समाधान चाहूंगा जिसे यूआरएल द्वारा उपयोग की जाने वाली प्रतिक्रिया मिल सके, इसलिए मैंने सोचा कि http उस कार्यक्षमता के लिए बहुत अच्छा होगा, और उसके लिए मुझे यह उत्तर वास्तव में मददगार लगा। मैं HTTP रिक्वेस्ट (स्पंदन / डार्ट) का उपयोग करके इंटरनेट कनेक्टिविटी की जांच कैसे करूं?

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.