Go Down

Topic: Wetter Server mit Api oder Aps vor Server Name funktioniert nicht (Read 3384 times) previous topic - next topic

-Micky

Dec 20, 2013, 02:26 am Last Edit: Dec 20, 2013, 02:35 am by -Micky Reason: 1
Folgendes Script funktioniert:

Code: [Select]
#include <SPI.h>
#include <Ethernet.h>

#include <TextFinder.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
LiquidCrystal_I2C lcd(0x27,16,2);

// Enter a MAC address for your controller below.
// Newer Ethernet shields have a MAC address printed on a sticker on the shield
byte mac[] = {  0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED };
// Änderung 1
char serverName[] = "Openweathermap.org";

// Initialize the Ethernet client library
// with the IP address and port of the server
// that you want to connect to (port 80 is default for HTTP):
EthernetClient client;
char buf[8];  // Puffer deklarieren

TextFinder  finder( client );  

void setup() {

 lcd.init(); // initialize the lcd
 lcd.backlight();
 // Open serial communications and wait for port to open:
 Serial.begin(9600);
  while (!Serial) {
   ; // wait for serial port to connect. Needed for Leonardo only
 }


 // start the Ethernet connection:
 if (Ethernet.begin(mac) == 0) {
   Serial.println("Failed to configure Ethernet using DHCP");
   // no point in carrying on, so do nothing forevermore:
   while(true);
 }
 // give the Ethernet shield a second to initialize:
 delay(1000);
 Serial.println("connecting...");

 // if you get a connection, report back via serial:

 if (client.connect(serverName, 80)) {
   Serial.println("connected");
   // Make a HTTP request:
   // Änderung 2
   client.println("GET /data/2.5/weather?q=Nienburg&mode=xml&units=metric&APPID=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx");
   client.print("Host: ");client.println(serverName);  
   client.println();
 }
 else {
   // kf you didn't get a connection to the server:
   Serial.println("connection failed");
 }
}

void loop()
{
 // if there are incoming bytes available
 // from the server, read them and print them:
 if (client.available()) {
   char c = client.read();
   Serial.print(c);
memset(buf,0,sizeof(buf)); // Puffer löschen
   }
   finder.find("<temperature");
   int temperature = finder.getValue();
   //lcd.clear();
   lcd.setCursor(0,0);
   //lcd.print("T=");
   lcd.print(temperature);
   lcd.setCursor(3,0);
   lcd.print((char)223);
   lcd.print("C ");
   delay(3000);
   
   finder.find("humidity");
   int Lf = finder.getValue();
   //lcd.clear();
   lcd.setCursor(6,0);
   //lcd.print("F:");
   lcd.print(Lf);
   lcd.setCursor(8,0);
   lcd.print("%");
   delay(3000);
   
   finder.find("pressure");
   int pressure = finder.getValue();
   lcd.setCursor(0,1);
   //lcd.print("D:");
   lcd.print(pressure);
   lcd.setCursor(5,1);
   lcd.print("hPa");
   delay(3000);
   
   finder.find("speed");
   int speed = finder.getValue();
   lcd.setCursor(11,1);
   lcd.print("G:");
   lcd.print(speed);
   delay(3000);
   
   int count=finder.getString("code=","n", buf, sizeof(buf));
   if (count>0)
   lcd.setCursor(11,0);
   lcd.print(buf);
   
   // if the server's disconnected, stop the client:
   if (!client.connected()) {
   Serial.println();
   Serial.println("disconnecting.");
   client.stop();

   // do nothing forevermore:
   while(true);
 }
}


Sobald ich aber einen Server nehme der ein Api oder Aps vor dem Server Namen hat, zum Beispiel api.wunderground.com, entsprechende Zeilen natürlich angepaßt, kommt zwar noch ein Kontakt zum Server zustande, nur erfolgt keine Ausgabe mehr.

Was muß ich ändern damit das dann geht?


Micky

sschultewolter

Kann es sein, dass es auch ohne "api." nicht funktioniert? Woher weiß finder.find("..."), wo er suchen soll?
Orginal Atmel AVRISP mkII zu verkaufen. Anfrage per PN ;)

-Micky

Und warum kommt der dann mit normalen Servernamen klar?


Mickx

sschultewolter

Versuche mal
Code: [Select]

char serverName[] = "http://api.wunderground.com";
Orginal Atmel AVRISP mkII zu verkaufen. Anfrage per PN ;)

rudirabbit

Hi,
"api.wunderground.com" passt schon.
Der Url muss sich pingen lassen, über das Problem bin ich auch schon gestolpert.


Wenn ich dein Beispiel api.wunderground.com  ansehe:
http://www.wunderground.com/weather/api/d/docs?d=data/index

Dann sollte Textfinder z.b nach "temperature_string" suchen  und nicht wie bei Openweathermap.org nach "<temperature".
Hast du dies auch angepaßt ?
Arduino UNO,MEGA,DUE 
Dunkel die andere Seite ist. - Klappe, Yoda, und iss deinen Toast :-)

mkl0815


Versuche mal
Code: [Select]

char serverName[] = "http://api.wunderground.com";


Das kann so aber nicht funktionieren. Das "http://" hat vor dem Servernamen beim Connect nix zu suchen. Das ist lediglich die Angabe des Protokolls, die z.B. ein Browser verwendet um zum Einen den richtigen Port (80, oder 443 bei https) und zum Anderen das richtige Protokoll (HTTP) zu nutzen. Das "http://" gehört aber NICHT zum Servernamen.
Korrekt müßte also sein:
Code: [Select]

char serverName[] = "api.wunderground.com";

[/quote]
Wird denn von Deinem Arduino der Name überhaupt korrekt aufgelöst? Sprich wird aus dem "api.wunderground.com" denn auch die IP "2.19.56.120"?
Mario


-Micky

#7
Dec 20, 2013, 11:58 am Last Edit: Dec 20, 2013, 12:02 pm by -Micky Reason: 1
Man kann die Server auch über die IP abfragen, mit einem anderen Script, nur funktionieren dann wiederum auch nicht alle. Zum Beispiel geht dann Worldweatheronline.com nicht. Man findet einfach keine gültige IP.  Anfrage bei Worldweatheronline.com hat ergeben:

We cannot provide any static IP as our api is run across CDN.

Da sind noch etliche andere bei denen das auch so ist.

http://de.wikipedia.org/wiki/Content_Delivery_Network


Micky

mkl0815

OK, das ist aber nicht weiter von Bedeutung. Es ist halt nur so, das der Name keiner eindeutigen IP zugeordnet wird, sondern verschiedenen. Wichtig ist aber, das überhaupt eine IP rauskommt.

Ich würde an Deiner Stelle erstmal schrittweise vorgehen. Bau ein einfaches Script, das erstmal nichts anderes macht als sich mit dem Server zu verbinden. Einen HTTP GET Request losschickt, das macht Dein Script ja schon und dann nur noch die Rückantwort des Servers auf die serielle Schnittstelle schreibt, ohne weitere Verarbeitung.
Am einfachsten passt Du Dir dafür das "WebClient" Example aus der Ethernet-Library an.
Den gleichen Aufruf solltest Du parallel auch im Browser testen und dann schauen was rauskommt.
Erst wenn das klappt, fängst Du an die Daten auseinander zu nehmen.
Unabhängig davon könntest Du auch anfangen die statischen Strings in den Flash-Speicher auszulagern, um SRAM zu sparen, alleine der GET Request sind ja schon eine Menge Bytes.
Mario.


-Micky

#9
Dec 20, 2013, 04:43 pm Last Edit: Dec 20, 2013, 04:46 pm by -Micky Reason: 1
Was ich rausbekommen habe ist das diese ganzen api.xxxx.com Sachen auf irgendwelche Server laufen wo es dann nicht weitergeht. Kann man gut verfolgen wenn man selbige Anschrift im Browser aufruft.

Bei api.wetter.com kommt 62.138.109.40 bei raus.

Welcome to nginx!

If you see this page, the nginx web server is successfully installed and working. Further configuration is required.

For online documentation and support please refer to nginx.org.
Commercial support is available at nginx.com.

Thank you for using nginx.


Wetter.com hat aber die IP 62.138.109.37

Und nun?


Micky

mkl0815

Das Du irgendeinen "default" Text bekommst, wenn Du nur die IP per HTTP aufrufst, ist normal. Das Ganze nennt sich "virtual namend host". (siehe Wikipedia) Damit ist es möglich, das ein Webserver mit nur einer IP auf Anfragen für mehrere Domains sinnvoll antworten kann. Dafür ist der Parameter "Host: www.irgendwas..." zuständig, den Du beim Client-Aufruf mit angeben mußt. Dein Browser machte das automatisch, wenn Du statt der "62.138.109.40" den Domainnamen "api.wetter.com" verwendest.

Wie bereits geschrieben, bau erstmal ein einfaches Script, das nur die Seite Zeichen für Zeichen ausliest. Wenn Du das hast, kannst Du das hier posten, dann können wir schauen ob irgendwo noch ein Fehler drin steckt.
Mario.

Go Up