JavaScript - Variablen aus JSON-Datei laden

OP (Firma: wiki.flowerhouse.at) #4231341
Lesenswert?

Hallo Community,
ich möchte Variablen aus einer JSON-Datei sekündlich laden.
Dazu hab ich ein kleines Script geschrieben:
JSON-Datei:
1
{
2
"temp_1": 10,
3
"pumpe_1": 1
4
}
JavaScript-Datei:
1
/** URL zur Variablendefinierung - JSON-Format */
2
var urlVariables = "./variables/variables.html";
3
function nameVariables(jd){
4
/** Variablen deklarieren */
5
temp_1 = (jd.temp_1);
6
pumpe_1 = (jd.pumpe_1);
7
}
8
function updateVariables(){
9
$.getJSON(urlVariables, nameVariables);
10
}
11
/** Alle 1000ms werden die Variablen aktualisiert */
12
updateVariables();
13
setInterval(updateVariables, 1000);
Die Variablen sollen dann Global verfügbar sein, weil Anzeigen, 
Graphen,... davon abhängig sind und dynamisch aktualisiert werden.

Das Script funktioniert, wenn ich nur eine Variable verwende wie z.B. 
temp_1.
Aber eine 2te oder mehr Variablen funktionier nicht.
Ich suche jetzt schon ein paar Stunden an dem Fehler, aber ich komme 
nicht darauf.

Kann mir da vll. jemand einen Tipp geben/helfen?
Danke und Mfg,
Tropaion
OP (Firma: wiki.flowerhouse.at) #4231399
Lesenswert?

Ich habe ein 2te Script wo ich die Variable so verwende, was aber nicht 
funktioniert. Kann es daran liegen das die Variable nicht übergeben 
wird?
Weil wenn ich sie im selben Script vor der Funktion defniere 
funktioniert es.
1
function funcMode()
2
{
3
  if(kreiselpumpe_1_mode){
4
    document.getElementById("modeOpen").innerHTML = "Automatisch";
5
  }
6
  else{
7
    document.getElementById("modeOpen").innerHTML = "Manuell";
8
  }
9
}
10
funcMode();
11
setInterval(funcMode, 1000);
#4231413
Lesenswert?

Aus deinem 1. Posting:
1
/** Variablen deklarieren */
2
temp_1 = (jd.temp_1);
3
pumpe_1 = (jd.pumpe_1);

Fabian P. schrieb:
> Ich habe ein 2te Script wo ich die Variable so verwende, was aber nicht
> funktioniert.

Und in deinem 2. Script kommt weder "temp_1" noch "pumpe_1" vor. Kann 
sein, dass es sich hier um ein Verständnisproblem meinerseits handelt. 
Aber das könnte man ganz einfach umgehen indem du einfach deinen 
gesamten Code posten würdest und auch erwähnen würdest, wie du den 
ausführst. JScript, Firefox, NodeJS, Rhino,...?
#4231470
Lesenswert?

du hat da nen type, an manchen stellen nutzt du pump_1 an anderen 
pumpe_1.
in der Heizkreis2.html klappt das dann. in der heizkessel1.html nicht, 
da fehlt glaub ich der Aufruf zur functions.js.

Du solltest dein json file auch .json nennen, je nach einstellung mag 
dein browser es nicht wenn json mit falschem content-type ausgeliefert 
wird.
OP (Firma: wiki.flowerhouse.at) #4231557
Lesenswert?

Bin die Variablen jetzt noch mal in Ruhe durchgegangen und ich bin der 
Meinung es sollte passen. .json hab ich jetzt auch reingetan.

Die Temperaturanzeige funktioniert auch (dynamisch).
Habe das script functions ganz unten eingebunden, weil es ja erst laden 
soll wenn das DOM-Model vollständig ist sonst kann es ja nicht 
funktionieren.

Nach rumprobiern bin ich der Meinung das die Variable das script nicht 
"erreicht". Denn beide funktionen selbst funktionieren ja.

Im Anhang geänderte Dateien.

Ich muss mich entschuldigen wenn der Code nicht besonders schön ist, ich 
arbeite erst seit ein paar Tagen intensiv mit JS.
Angehängte Dateien:
OP (Firma: wiki.flowerhouse.at) #4231585
Lesenswert?

Also erstens mal bin ich berufsuntätig, ich bin Schüler an einer 
technischen Schule.
Dieses Projekt mache ich in meiner Freizeit um mein Wissen und Können zu 
erweitern. Es wird wahrscheinlich nie verwendet werden geschweige denn 
verkauft. Höchstens auf meiner Webseite als OpenSource-Projekt 
veröffentlicht. (OpenSource-Befürworter ;) )

Wenn es Geld verdienen wäre wäre es nicht verkaufbar da stimme ich dir 
zu.
Aber was erwartet man von jemanden der seit 4 Tagen mit JavaScript 
arbeitet ;)

Von "onload" hab ich schon gehört, aber ich versuche es am Anfang 
einfacher zu halten und immer mehr zu erweitern.

Ich denke nicht das "onload" der Grund ist das es nicht funktioniert 
oder liege ich da falsch?

Mfg,
Tropaion
#4231611
Lesenswert?

Fabian P. schrieb:
> Ich denke nicht das "onload" der Grund ist das es nicht funktioniert

Der Grund ist, dass JS hochgradig asynchron arbeitet. Wenn du JS sagst, 
es soll dir deine "variables.json" holen, dann macht es das. Irgendwann.
Währenddessen läuft das Programm weiter ab, denn so ein Datenabruf kann 
im Internet ja einige Zeit dauern. Wäre ja blöd, wenn währenddessen 
alles blockiert wäre. Es läuft also weiter in deine functions.js, will 
die "pumpe_1_mode" lesen und peng - nicht gefunden, weil die kommt erst 
irgendwann in der Zukunft asynchron daher. Also dort einen check 
einbauen, ob es die schon gibt, ansonsten "return". Beim Durchlauf eine 
Sekunde später ist sie dann schon da.
Gast #4231638
Lesenswert?

In
$.getJSON(urlVariables, nameVariables);
ist nameVariables ein "Funktionsobjekt", d.h. ein Objekt, das den 
()-Operator kennt, mit dem man das im Objekt versteckte Script ausführen 
kann. $.getJSON ruft dieses dann irgendwann später auf, um die 
empfangenen Daten zurückzuliegen.

PS.: seh's als Kompliment, daß ich den Schüler nicht gleich entdeckt 
hab. Ich bin dir eben 35 Jahre voraus. Damals haben wir am TG noch 
deutlich einfachere Dinge gemacht ;-)
OP (Firma: wiki.flowerhouse.at) #4231662
Lesenswert?

Danke Basterl ;)

Das es ein Obejekt ist, ist mir glar was was meinst du mit aufrufen?


@Dirk
Global initialisiert sind sie doch eh oder?
Laut definition in W3C ist eine Variable ohne "var" in einem 
Unterprogramm automatisch global

@Jan Hansen
Auch wenn das so ist, die Funktion wird ja jede Sekunde ausgeführt, das 
heißt es müsste spätestens eine Sekunde nach dem Laden gehen oder nicht?

EDIT:
Ok, um ehrlich zu sein, ich bin jetzt etwas verwirrt. Hab denn Tipp von 
Hansen mal ausprobiert und er funktioniert, jedoch warum ist mir 
unerklärlich.
1
/** URL zur Variablendefinierung - JSON-Format */
2
var urlVariables = "./variables/variables.json";
3
var pumpe_1_mode;
4
  
5
function nameVariables(jd){
6
/** Variablen deklarieren */
7
  temp_1 = (jd.temp_1);
8
  pumpe_1_mode = (jd.pumpe_1_mode);
9
}
10
  
11
function updateVariables(){
12
  $.getJSON(urlVariables, nameVariables);
13
}
14
/** Alle 1000ms werden die Variablen aktualisiert */
15
updateVariables();
16
setInterval(updateVariables, 1000);

Die Variable "temp_1" kann ich ja auch mit einer anderen Funktion 
(Global) aufrufen, laut W3C (http://www.w3schools.com/js/js_scope.asp) 
definiert man eine Variable ja auch so innerhalb einer Funktion als 
Global. Warum muss ich dann pumpe_1_mode noch mal außerhalb der Funktion 
deklarieren
1
 var pumpe_1_mode;
 damit sie global ist?
#4231743
Lesenswert?

Fabian P. schrieb:
> @Jan Hansen
> Auch wenn das so ist, die Funktion wird ja jede Sekunde ausgeführt, das
> heißt es müsste spätestens eine Sekunde nach dem Laden gehen oder nicht?

Habe den Code nicht mehr vor mir, aber wenn ich mich richtig erinnere 
rufst du die Funktion initial einmal auf (Skriptfehler => Abbruch), erst 
danach setzt du das Intervall (wird in diesem Fall nicht gemacht, weil 
vorher der Fehler war).
Also prinzipiell hast du recht: hättest du das Intervall vor dem Fehler 
gesetzt, dann hätte der nächste Durchlauf geklappt. So gibt es aber 
keine weiteren Durchläufe.
#4231750
Lesenswert?

Fabian P. schrieb:
> @Dirk
> Global initialisiert sind sie doch eh oder?
> Laut definition in W3C ist eine Variable ohne "var" in einem
> Unterprogramm automatisch global

Ja, aber das machst du erst später asynchron. So versucht er die globale 
Variable zu lesen, die es nicht gibt. Wenn du zu Beginn "pumpe_1_mode = 
null;" schreibst, dann gibt es sie und alles ist paletti.

> var pumpe_1_mode;
> damit sie global ist?

Musst du eh nicht, ohne "var" passt damit sie global ist.
OP (Firma: wiki.flowerhouse.at) #4231761
Lesenswert?

Habe jetzt window.onload eingebaut in das Script:
1
function funcMode(varHeizkreis)
2
{
3
  if(eval("pumpe_" + varHeizkreis + "_mode")){
4
    document.getElementById("modeOpen").innerHTML = "Automatisch";
5
  }
6
  else{
7
    document.getElementById("modeOpen").innerHTML = "Manuell";
8
  }
9
}
10
window.onload = function() {
11
  funcMode(1);
12
  setInterval(function(){funcMode(1);}, 1000);
13
}
Jetzt funktioniert es auch ohne das die Variablen extra definiert 
werden.

Kann ich das Script varUpdate.js so priorisieren, das es das erste 
Script ist welches ausgeführt werden soll?
#4231885
Lesenswert?

Um da mal weniger an den symptomen rumzudoktern und das alles ein 
bisschen grade zu rücken:
warum rufst du nicht aus deinem update-interval (ggf. wenn du 
festgestellt hast das sich etwas geändert hat) ein update des dom auf? 
dann hast du das Problem gar nicht das die Daten noch nicht da sind wenn 
du den dom updaten willst, und du hast deine Daten im schnitt 500ms 
schneller auf dem schirm :)
OP (Firma: wiki.flowerhouse.at) #4231953
Lesenswert?

Sehr interessanter Ansatz, mir kam das auch schon mal in den Sinn, aber 
ich wusste nicht das das geht.
Wie heißt der Befehl mit dem das geht, bzw. nach was muss ich suchen?
Unter "Javascript dom update" finde ich nichts dazu.
Und wie kommst du darauf das es im Schnitt 500ms sind?

Danke und Mfg,
Tropaion
#4232196
Lesenswert?

Na momentan hast du ja 2 Intervale die alle 1000ms dinge tun, der eine 
läd Daten irgendwo her und speichert sie zwischen, der andere nimmt 
diese Daten und zeigt sie an (in dem es den dom updated).
Die Zeit die vergeht zwischen dem Updaten der zwischengespeicherten 
Daten und dem Anzeigen dieser ist liegt zwischen 0 und 1000ms. Wo genau 
kannst du nur im Einzelfall bestimmen, und es gibt da einen Drift.
Der Mittelwert ist also ( 100 - 0 ) / 2.
Was du jetzt tun kannst: du kannst in dem interval der die Daten 
einsammelt sie auch rausschreiben, am besten mit einer Prüfung ob sich 
diese überhaupt geändert haben.
Grüße, Dirk
OP (Firma: wiki.flowerhouse.at) #4232247
Lesenswert?

Achso, sozusagen ein Intervall mit einer anonymen Funktion wo alle 
Funktionen zum Updaten einfach ausgeführt wird so unser Art:
Intervall {
varUpdate;
valueUpdate1;
valueUpdate2;
.....
}

Von der Rechnung her meinst du wahr. (1000 - 0)/2 = 500ms oder?

Danke und Mfg,
Tropaion
OP (Firma: wiki.flowerhouse.at) #4232806
Lesenswert?

Jetzt weiß ich auch was du meinst.
Wir haben mal so was ähnliches in der Schule gemacht.
Prozessor -> zyklisches Abarbeiten von Befehlen.

Meine Lösung ist jetzt:
1
<script>
2
<!--
3
/** Alle 1000ms werden die Werte aktualisiert */
4
window.onload = function() {
5
  setInterval(function() {
6
/** Die zu aktualisierenden Funktionen hier eintragen */
7
    updateVariables();
8
    funcMode(pumpe_1_mode);
9
    g1.refresh(temp_1);
10
    g2.refresh(pumpe_1_temp);
11
    g3.refresh(pumpe_1);
12
    funcOverheated(pumpe_1_temp, pumpe_1_max_temp);
13
  }
14
/** Aktualisierungszyklus in ms  */  
15
  ,1000);
16
};
17
//-->
18
</script>

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren