2012-02-22 16 views
8

हम एक ऐसे अनुप्रयोग को विकसित कर रहे हैं जो पीसी पर स्थापित होगा और यह कुछ पृष्ठभूमि अपलोड करेगा और हमारे सर्वर से/डाउनलोड करेगा। आवश्यकता में से एक यह पता लगाने के लिए है कि इंटरनेट कनेक्शन वर्तमान में व्यस्त है (50% उपयोग से ऊपर कहें) और यदि ऐसा है, तो इसे बैक-ऑफ करने और किसी अन्य समय की कोशिश करने की आवश्यकता है। मुख्य कारण यह है कि ऐप उपयोगकर्ता अनुभव के साथ हस्तक्षेप नहीं करता है अगर वे गेमिंग के बीच में हैं, ऑनलाइन मूवी देख रहे हैं या आक्रामक रूप से फाइलें डाउनलोड कर रहे हैंपता लगाना कि इंटरनेट कनेक्शन व्यस्त है

Google और निश्चित रूप से SO पर बहुत सोच और शोध के बाद, मैं अभी भी ' टी को कार्यान्वित करने के तरीके पर एक अच्छा तरीका नहीं मिला, इसलिए इसे यहां फेंकने का फैसला किया। आवेदन सी ​​#, .NET 4.0 में लागू किया गया है और मैं सभी प्रकार के प्रतिक्रियाओं की तलाश में हूं - या तो सी # या अन्य भाषाओं में कार्यान्वयन, छद्म तर्क या कैसे हासिल किया जाए इस पर दृष्टिकोण - स्थानीय पीसी पर इंटरनेट यातायात उपयोग को मापना पर्याप्त सटीकता

प्रयास के दोहराव से बचने के लिए, अब तक मैं इन की कोशिश की है (और क्यों वे उपयुक्त नहीं हैं)

  • उपयोग WMI नेटवर्क आंकड़ा पाने के लिए। इस दृष्टिकोण को संदर्भ के रूप में संदर्भित करने के बाद से अधिकांश एसओ पोस्ट और समाधान, लेकिन यह हमारी आवश्यकता को पूरा नहीं करता है क्योंकि उपयोग के लिए नेटवर्क इंटरफ़ेस क्षमता (जैसे 1 जीबी ईथरनेट कार्ड) के माध्यम से भेजे गए/प्राप्त बाइट्स को मापने के लिए लैन यातायात के लिए एक अच्छा उपाय मिलेगा लेकिन इंटरनेट यातायात के लिए नहीं (जहां वास्तविक इंटरनेट बैंडविड्थ केवल 8 एमबीपीएस कह सकता है)
  • .NET नेटवर्क सूचना सांख्यिकी या प्रदर्शन काउंटर का उपयोग उपर्युक्त उपरोक्त समान रीडिंग्स के समान ही कमियां हैं
  • आईसीएमपी (पिंग) का उपयोग करें और आरटीटी मापें। यह सुझाव दिया गया था कि 400 एमएम आरटीटी को व्यस्त नेटवर्क के लिए धीमा और अच्छा संकेत माना जाता है, हालांकि मुझे बताया गया था कि मॉडेम के साथ उपयोगकर्ता (हाँ हमें इसका समर्थन करना होगा), रिवर्स प्रॉक्सी या माइक्रोवेव लिंक का उपयोग अक्सर ऊपर पिंग मिलता है, इसलिए अच्छा नहीं माप
  • ज्ञात फ़ाइल डाउनलोड करना शुरू करें और गति को मापें - यह स्वयं यातायात उत्पन्न करता है जिसे हम टालने की कोशिश कर रहे हैं, भले ही यह जांच अक्सर पर्याप्त हो, तो हमारा आवेदन बहुत से इंटरनेट यातायात को समाप्त कर देगा - जो फिर से आदर्श नहीं है
  • एमओडी: बिट्स का उपयोग करना - इस सेवा हमारे मामले में, उपयोगकर्ता पीसी पर अक्षम किया जा सकता है समूह नीति में परिवर्तन की आवश्यकता है और सर्वर मान आईआईएस (कस्टम विन्यास के साथ) होने के लिए और हमारे सर्वर नहीं है IIS

तो यहां यह है, मैं सब उलझन में हूं और कुछ सलाह ढूंढ रहा हूं। मैंने प्रश्न पाठ को हाइलाइट किया ताकि आप लोग इसे पढ़ना न भूलें और सोचें कि सवाल क्या है। धन्यवाद।

+0

सही समाधान राउटर पर क्यूओएस होगा। दयालुता कि अधिकांश उपभोक्ता राउटर चूसते हैं। – CodesInChaos

+1

एक आम समस्या की तरह लगता है, लेकिन ऐसा कोई सामान्य समाधान नहीं लगता है :( –

+1

क्योंकि पीसी स्तर पर समस्या हल करना असंभव है। आपका सॉफ़्टवेयर यह नहीं जानता कि एक ही राउटर का उपयोग करके कोई और ट्रैफिक कितना ट्रैफिक कर रहा है। – CodesInChaos

उत्तर

5

आप राउटर से पूछने के लिए यूपीएनपी का उपयोग कर सकते हैं, और नेटवर्क पर भेजे गए बाइट्स की संख्या को पुनः प्राप्त कर सकते हैं। यह निर्धारित करने के लिए कि गतिविधि क्या है, आप राउटर पर इस मान को जांचते रह सकते हैं। दुर्भाग्यवश यह कार्यक्षमता अच्छी तरह से प्रलेखित नहीं प्रतीत होती है, लेकिन सी # अनुप्रयोग के भीतर यूपीएनपी संचार कार्यक्षमता को कार्यान्वित करना संभव है। आपको राउटर (यूपीएनपी खोज) के लिए क्वेरी करने के लिए यूडीपी का उपयोग करने की आवश्यकता होगी, और एक बार जब आपको डिवाइस मिल जाए, तो इसकी कार्यक्षमता पूछें, और फिर WebClient (TCP) का उपयोग कर इंटरनेट गेटवे डिवाइस के लिए भेजे गए और प्राप्त पैकेट की संख्या से पूछें।

 
Code for a UPnP library: 

using System; 
using System.Collections.Generic; 
using System.Text; 
using System.Net.Sockets; 
using System.Net; 
using System.Xml; 
using System.IO; 
namespace UPNPLib 
{ 
    public class RouterElement 
    { 
     public RouterElement() 
     { 
     } 
     public override string ToString() 
     { 
      return Name; 
     } 
     public List children = new List(); 
     public RouterElement parent; 
     public string Name; 
     public string Value; 
     public RouterElement this[string name] { 
      get 
      { 
       foreach (RouterElement et in children) 
       { 
        if (et.Name.ToLower().Contains(name.ToLower())) 
        { 
         return et; 
        } 
       } 
       foreach (RouterElement et in children) 
       { 
        Console.WriteLine(et.Name); 
       } 
       throw new KeyNotFoundException("Unable to find the specified entry"); 
      } 
    } 
     public RouterElement(XmlNode node, RouterElement _parent) 
     { 

      Name = node.Name; 
      if (node.ChildNodes.Count 
     /// Gets the root URL of the device 
     /// 
     /// 
     public static string GetRootUrl() 
     { 
      StringBuilder mbuilder = new StringBuilder(); 
      mbuilder.Append("M-SEARCH * HTTP/1.1\r\n"); 
      mbuilder.Append("HOST: 239.255.255.250:1900\r\n"); 
      mbuilder.Append("ST:upnp:rootdevice\r\n"); 
      mbuilder.Append("MAN:\"ssdp:discover\"\r\n"); 
      mbuilder.Append("MX:3\r\n\r\n"); 
      UdpClient mclient = new UdpClient(); 
      byte[] dgram = Encoding.ASCII.GetBytes(mbuilder.ToString()); 
      mclient.Send(dgram,dgram.Length,new IPEndPoint(IPAddress.Broadcast,1900)); 
      IPEndPoint mpoint = new IPEndPoint(IPAddress.Any, 0); 
      rootsearch: 

      dgram = mclient.Receive(ref mpoint); 
      string mret = Encoding.ASCII.GetString(dgram); 
      string orig = mret; 
      mret = mret.ToLower(); 
      string url = orig.Substring(mret.IndexOf("location:") + "location:".Length, mret.IndexOf("\r", mret.IndexOf("location:")) - (mret.IndexOf("location:") + "location:".Length)); 
      WebClient wclient = new WebClient(); 
      try 
      { 
       Console.WriteLine("POLL:" + url); 
       string reply = wclient.DownloadString(url); 

       if (!reply.ToLower().Contains("router")) 
       { 
        goto rootsearch; 
       } 
      } 
      catch (Exception) 
      { 
       goto rootsearch; 
      } 
      return url; 
     } 
     public static RouterElement enumRouterFunctions(string url) 
     { 

      XmlReader mreader = XmlReader.Create(url); 
      XmlDocument md = new XmlDocument(); 
      md.Load(mreader); 
      XmlNodeList rootnodes = md.GetElementsByTagName("serviceList"); 
      RouterElement elem = new RouterElement(); 
      foreach (XmlNode et in rootnodes) 
      { 
       RouterElement el = new RouterElement(et, null); 
       elem.children.Add(el); 
      } 

      return elem; 
     } 
     public static RouterElement getRouterInformation(string url) 
     { 
      XmlReader mreader = XmlReader.Create(url); 
      XmlDocument md = new XmlDocument(); 
      md.Load(mreader); 
      XmlNodeList rootnodes = md.GetElementsByTagName("device"); 
      return new RouterElement(rootnodes[0], null); 
     } 

    } 
    public class RouterMethod 
    { 
     string url; 
     public string MethodName; 
     string parentname; 
     string MakeRequest(string URL, byte[] data, string[] headers) 
     { 
      Uri mri = new Uri(URL); 
      TcpClient mclient = new TcpClient(); 
      mclient.Connect(mri.Host, mri.Port); 
      Stream mstream = mclient.GetStream(); 
      StreamWriter textwriter = new StreamWriter(mstream); 
      textwriter.Write("POST "+mri.PathAndQuery+" HTTP/1.1\r\n"); 

      textwriter.Write("Connection: Close\r\n"); 

      textwriter.Write("Content-Type: text/xml; charset=\"utf-8\"\r\n"); 

      foreach (string et in headers) 
      { 
       textwriter.Write(et + "\r\n"); 
      } 
      textwriter.Write("Content-Length: " + (data.Length).ToString()+"\r\n"); 
      textwriter.Write("Host: " + mri.Host+":"+mri.Port+"\r\n"); 


      textwriter.Write("\r\n"); 
      textwriter.Flush(); 



      Stream reqstream = mstream; 
      reqstream.Write(data, 0, data.Length); 
      reqstream.Flush(); 
      StreamReader reader = new StreamReader(mstream); 
      while (reader.ReadLine().Length > 2) 
      { 

      } 
      return reader.ReadToEnd(); 
     } 
     public RouterElement Invoke(string[] args) 
     { 

      MemoryStream mstream = new MemoryStream(); 
      StreamWriter mwriter = new StreamWriter(mstream); 
      //TODO: Implement argument list 
      string arglist = ""; 

      mwriter.Write("" + "" + ""); 


      mwriter.Write("");//" + arglist + ""); 
      mwriter.Write(""); 
      mwriter.Flush(); 

      List headers = new List(); 

      headers.Add("SOAPAction: \"" + parentschema + "#" + MethodName + "\""); 

      mstream.Position = 0; 
      byte[] dgram = new byte[mstream.Length]; 

      mstream.Read(dgram, 0, dgram.Length); 

      XmlDocument mdoc = new XmlDocument(); 
      string txt = MakeRequest(url, dgram, headers.ToArray()); 
      mdoc.LoadXml(txt); 
      try 
      { 
       RouterElement elem = new RouterElement(mdoc.ChildNodes[0], null); 

       return elem["Body"].children[0]; 
      } 
      catch (Exception er) 
      { 
       RouterElement elem = new RouterElement(mdoc.ChildNodes[1], null); 
       return elem["Body"].children[0]; 
      } 

     } 
     public List parameters = new List(); 
     string baseurl; 
     string parentschema; 
     public RouterMethod(string svcurl, RouterElement element,string pname, string baseURL, string svcpdsc) 
     { 
      parentschema = svcpdsc; 
      baseurl = baseURL; 
      parentname = pname; 
      url = svcurl; 
      MethodName = element["name"].Value; 
      try 
      { 
       foreach (RouterElement et in element["argumentList"].children) 
       { 
        parameters.Add(et.children[0].Value); 
       } 
      } 
      catch (KeyNotFoundException) 
      { 
      } 
     } 
    } 
    public class RouterService 
    { 
     string url; 
     public string ServiceName; 
     public List methods = new List(); 
     public RouterMethod GetMethodByNonCaseSensitiveName(string name) 
     { 
      foreach (RouterMethod et in methods) 
      { 
       if (et.MethodName.ToLower() == name.ToLower()) 
       { 
        return et; 
       } 
      } 
      throw new KeyNotFoundException(); 
     } 
     public RouterService(RouterElement element, string baseurl) 
     { 

      ServiceName = element["serviceId"].Value; 
      url = element["controlURL"].Value; 

      WebClient mclient = new WebClient(); 
      string turtle = element["SCPDURL"].Value; 
      if (!turtle.ToLower().Contains("http")) 
      { 
       turtle = baseurl + turtle; 
      } 
      Console.WriteLine("service URL " + turtle); 
      string axml = mclient.DownloadString(turtle); 
      XmlDocument mdoc = new XmlDocument(); 
      if (!url.ToLower().Contains("http")) 
      { 
       url = baseurl + url; 
      } 
      mdoc.LoadXml(axml); 
      XmlNode mainnode = mdoc.GetElementsByTagName("actionList")[0]; 
      RouterElement actions = new RouterElement(mainnode, null); 
      foreach (RouterElement et in actions.children) 
      { 
       RouterMethod method = new RouterMethod(url, et,ServiceName,baseurl,element["serviceType"].Value); 
       methods.Add(method); 
      } 

     } 
    } 
} 

 
 

Code for a bandwidth meter: 
using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Data; 
using System.Drawing; 
using System.Text; 
using System.Windows.Forms; 
using UPNPLib; 
using System.IO; 

namespace bandwidthmeter 
{ 
    public partial class Form1 : Form 
    { 
     public Form1() 
     { 
      InitializeComponent(); 
      BinaryReader mreader = new BinaryReader(File.Open("bandwidthlog.txt", FileMode.OpenOrCreate)); 
      if (mreader.BaseStream.Length > 0) 
      { 
       prevsent = mreader.ReadInt64(); 
       prevrecv = mreader.ReadInt64(); 
      } 
      mreader.Close(); 
      List services = new List(); 
      string fullurl = UPNP.GetRootUrl(); 
      RouterElement router = UPNP.enumRouterFunctions(fullurl); 
      Console.WriteLine("Router feature enumeration complete"); 
      foreach (RouterElement et in router.children) 
      { 

       services.Add(new RouterService(et.children[0], fullurl.Substring(0, fullurl.IndexOf("/", "http://".Length+1)))); 
      } 
      getReceiveDelegate = services[1].GetMethodByNonCaseSensitiveName("GetTotalBytesReceived"); 
      getSentDelegate = services[1].GetMethodByNonCaseSensitiveName("GetTotalBytesSent"); 
      Console.WriteLine("Invoking " + getReceiveDelegate.MethodName); 
      //Console.WriteLine(services[1].GetMethodByNonCaseSensitiveName("GetTotalPacketsSent").Invoke(null)); 

      Timer mymer = new Timer(); 
      mymer.Tick += new EventHandler(mymer_Tick); 
      mymer.Interval = 1000; 
      mymer.Start(); 
      FormClosed += new FormClosedEventHandler(Form1_FormClosed); 
     } 
     long prevsent = 0; 
     long prevrecv = 0; 
     void Form1_FormClosed(object sender, FormClosedEventArgs e) 
     { 
      BinaryWriter mwriter = new BinaryWriter(File.Open("bandwidthlog.txt", FileMode.OpenOrCreate)); 
      mwriter.Write(getsent()); 
      mwriter.Write(getreceived()); 
      mwriter.Flush(); 
      mwriter.Close(); 

     } 
     long getsent() 
     { 
      long retval = Convert.ToInt64(getSentDelegate.Invoke(null).children[0].Value); 
      if (prevsent > retval) 
      { 
       retval = prevsent + retval; 
      } 
      return retval; 
     } 
     long getreceived() 
     { 
      long retval = Convert.ToInt64(getReceiveDelegate.Invoke(null).children[0].Value); 
      if (prevrecv > retval) 
      { 
       retval = prevrecv + retval; 
      } 
      return retval; 
     } 
     void mymer_Tick(object sender, EventArgs e) 
     { 
      label1.Text = "Sent: "+(getsent()/1024/1024).ToString()+"MB\nReceived: "+(getreceived()/1024/1024).ToString()+"MB"; 

     } 
     RouterMethod getSentDelegate; 
     RouterMethod getReceiveDelegate; 

    } 
} 
 
+0

प्रतिक्रिया के लिए धन्यवाद। क्या यह दृष्टिकोण सभी समर्थित विन ओएस और अधिकतर राउटर के साथ काम करेगा? एक बार मुझे पैकेट भेजा और प्राप्त हो जाने के बाद, उपयोग को निर्धारित करने के बारे में मुझे कैसे करना है (जैसे कि मेरे उदाहरण में> 50% व्यस्त मानते हैं) –

+0

हां, यह दृष्टिकोण अधिकांश उपभोक्ता राउटर के साथ काम करेगा, लेकिन अधिकांश व्यवसाय वाले नहीं हैं (यूपीएनपी कॉर्पोरेट रूटर पर डिफ़ॉल्ट रूप से अक्षम)। – IDWMaster

+0

कृपया इस आलेख को पढ़ें - http://www.codeproject.com/Articles/27992/NAT-Traversal-with-UPnP-in-C UPNP के परिचय के लिए। यह नमूना बंदरगाह अग्रेषण के लिए है, लेकिन आप उन यूआरएल का उपयोग कर सकते हैं जो राउटर अपने अन्य कार्यों को देखने के लिए प्रदान करता है (बैंडविड्थ फ़ंक्शन आमतौर पर अधिकांश राउटर में समान होते हैं)। – IDWMaster

4

आप Background Intelligent Transfer Service (BITS) का उपयोग कर माना जाता है।यह पहले से ही यह काम कर हेतु बनाया गया है:

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

और,

अन्य नेटवर्क आवेदनों की जवाबदेही को बचाना।

मुझे यकीन नहीं है कि इसमें एक प्रबंधित इंटरफ़ेस है (मैं पावरहेल सीएमडीलेट्स के संदर्भ देख सकता हूं), इसलिए आपको इसका उपयोग करने के लिए COM इंटरऑप का उपयोग करना पड़ सकता है।

+0

हां, लेकिन दुर्भाग्यवश यह कई कारणों से हमारी आवश्यकता को पूरा नहीं करता है: बीआईटीएस सेवा अक्षम की जा सकती है, इसके लिए समूह नीति परिवर्तन और सर्वर अंत बिंदु (माना जाता आईआईएस) की आवश्यकता है और कॉन्फ़िगर करने की आवश्यकता है - हमारे मामले में सर्वर नहीं है 'यह है। सुझाव के लिए +1। –

1

यह मानते हुए कि आप विंडोज पीसी को लक्षित कर रहे हैं (जैसा कि आपने कहा था कि आप सी # में विकास कर रहे थे), क्या आपने BITS, पृष्ठभूमि इंटेलिजेंट ट्रांसफर सर्विस देखा है?

एमएसडीएन और अन्य जगहों पर सी # का उपयोग करके इसमें कैसे शामिल होना है इसके उदाहरण हैं। http://msdn.microsoft.com/en-us/magazine/cc188766.aspx

+0

प्रतिक्रिया के लिए धन्यवाद। हां मेरे पास है, कृपया डेमियन के जवाब पर मेरी प्रतिक्रिया देखें जो एक ही चीज़ पर छू गया। –