9x
005597
22. August 2024

Webanfragen (API) Geo-Zonen-Tool: Automatisierung mittels Python

Wie kann ich Webanfragen (API) an das Geo-Zonen-Tool mittels Python automatisieren?


Antwort:

Ja, dies ist sehr unkompliziert möglich. Im Folgenden wird dies an einem Beispiel gezeigt.

Vorbereitung

Um mittels Python Webanfragen an das Geo-Zonen-Tool durchzuführen benötigen Sie:

  1. Editor bzw. IDE (Integrierte Entwicklungsumgebung) zum Schreiben des Skripts
  2. Python - python.org
  3. Python-Bibliothek Requests
  4. Python-Bibliothek Pandas (optional)

Um eine Webanfrage des Geo-Zonen-Tools durchzuführen, werden die Informationen für das Geo-Zonen-Tool benötigt. Am Beispiel des Aufbaus der Abfrage-URL is dies in folgendem Artikel erläutert:
Webservice (API) ansteuern

Für dieses Beispiel werden beispielhaft folgende Angaben verwendet, welche sie im Skript mit ihren ersetzen müssen:

  1. Sprache: de (deutsch)
  2. Login: [email protected]
  3. Hash: 123456ABCD
  4. Karte: wind-DIN-EN-1991-1-4 (Windlast nach deutschem Anhang EC1)
  5. Ort: Dlubal, Tiefenbach (Firmensitz Dlubal GmbH)
  6. Position: 49.4353975, 12.5894907 (Breitengrad, Längengrad)

Webanfrage ausführen und Daten auslesen

Folgendes Skript führt die Abfrage an den Webservice des Geo-Zonen-Tools durch und dokumentiert die benötigten Zeiten und den Inhalt.


...
#%% Imports
# Bibliothek um Zeitstempel auszulesen (Standardbibliothek, optional) 
import datetime as dt
# Bibliothek um Webanfrage durchführen
import requests

#%% Parameter festlegen
# URl Webservice Geo-Zonen-Tool 
urlgz = 'https://external-crm.dlubal.com/loadzones/data.aspx'

# Parameter für Abfrage (mit eigenen Werten ersetzen)
pargz = {
        'language': 'de',
        'login': '[email protected]',
        'hash': '123456ABCD',
        'map': 'wind-DIN-EN-1991-1-4',
        'place': 'Dlubal, Tiefenbach',
        'position': '49.4353975,12.5894907'
        }
# Zeit für Abrruch der Anfrage festlegen
reto=10 # s

#%% Abfrage durchführen
# Zeitstempel vor Abruf
cdt1 = dt.datetime.now()
# Webabfrage mittels Requests
rgz = requests.get(urlgz, params=pargz, timeout=reto)
# Zeitstempel nach Abruf
cdt2 = dt.datetime.now()
# Dauer der Abfrage in Sekunden
dur=(cdt2-cdt1).total_seconds()
# HTTP-Status-Code der Abfrage
sgz=rgz.status_code
# Inhaltsbeschreibung der Abfrage
hgz=rgz.headers['content-type']
# Inhalt der Webanfrage als text
tgz = rgz.text

#%% Konsolenausgaben der Webanfrage
txt=[]
txt.append(f"Timestamp: {cdt1}") # Zeitpunkt YYYY-MM-DD HH:MM:SS.SSSSSS
txt.append(f"Duration: {dur} s") # Dauer der Abfrage
txt.append(f"Status code: {rgz.status_code}") # HTTP-Statuscode (normal: 200)
txt.append(f"Header: {hgz}") # Beschreibung des Inhalts (normal: text/html; charset=utf-8)
txt.append(f"Text output of request:\n{tgz}") # Ausgaben des Geozonen-Tools
print('\n'.join(txt))
...

Dies führt Beispielsweise zu folgenden Ausgaben:


Timestamp: 2024-08-22 13:24:32.727006
Duration: 2.214527
Status code: 200
Header: text/html; charset=utf-8
Text output of request: 
Result 1,Result 2,Zone,Latitude,Longitude,Elevation,Street,ZIP,City,Standard,Annex,Note(s),Legal notice
22.5 m/s,0.32 kN/m2,1,49.4353975,12.5894907,520.69384765625,Am Zellweg 2,93464,Tiefenbach,EN 1991-1-4,DIN EN 1991-1-4,,Alle Angaben ohne Gewähr

Zusatz: Inhalt der Webanfrage aufbereiten

Folgendes Skript wandelt den vom Geo-Zonen-Tool Webservice erhaltenen Text in eine tabellarische Form um. Des Weiteren werden hier die Ergebniswerte von ihren Einheiten getrennt und schlussendlich als csv- und Excel-Datei gespeichert.


...
#%% Imports
# String-Funktionen der Standardbibliothek für import und export
from io import StringIO
# Bibliothek zur Datenverarbeitung
import pandas as pd

#%% Funktionen
def rsep_val_unit(indf, cnstart='Result',):
    """
    Seperates Dlubal Geo-Zone-Tool request Dataframe columns with results by value and unit.

    Parameters
    ----------
    indf : pandas.DataFrame
        Input data.
    cnstart: string, optional
        Identifier at start of column name containing results.

    Returns
    -------
    outdf : pandas.DataFrame
        Output data.

    """
    tmp2 = indf.loc(axis=1)[indf.columns.str.startswith(cnstart)]
    tmp3 = pd.DataFrame()
    for i in tmp2.columns:
        tmp3[[(i, 'value'), (i, 'unit')]] = tmp2[i].str.split(
            ' ', n=1, expand=True)
    outdf = pd.concat(
        [tmp3, indf.loc(axis=1)[~indf.columns.str.startswith(cnstart)]], axis=1)
    return outdf

#%% Konvertierung durchführen
# Ausgabe des Geo-Zonen-Tools in "tabellarische" Dataframe umwandeln
dfgz=pd.read_csv(StringIO(rgz.text))
# DataFrame mit getrenntem Ergebnissen nach Wert und Einheit
dfgz_rs=rsep_val_unit(dfgz)

#%% Speicherung
# als CSV-Datei
dfgz_rs.to_csv("Dlubal_GZT_request.csv")
# als Excel-Datei
dfgz_rs.to_excel("Dlubal_GZT_request.xlsx")

#%% Konsolenausgaben der Konvertierung
print(f"Original Dataframe:\n{dfgz.to_string()}")
print(f"Manipulated Dataframe:\n{dfgz_rs.to_string()}")
print("Exemplary Output:\n"
      + f"   The first result has the value {dfgz_rs.iloc[0,0]}."
      + f" (in {dfgz_rs.iloc[0,1]})")
...

Dies führt beispielsweise zu folgenden Ausgaben:


Original Dataframe:
   Result 1               Result 2  Zone   Latitude  Longitude   Elevation        Street    ZIP        City     Standard            Annex  Note(s)              Legal notice
0  22.5 m/s  0.32 kN/m2     1  49.435398  12.589491  520.693848  Am Zellweg 2  93464  Tiefenbach  EN 1991-1-4  DIN EN 1991-1-4      NaN  Alle Angaben ohne Gewähr
Manipulated Dataframe:
  (Result 1, value) (Result 1, unit) (Result 2, value)  (Result 2, unit)  Zone   Latitude  Longitude   Elevation        Street    ZIP        City     Standard            Annex  Note(s)              Legal notice
0              22.5              m/s              0.32  kN/m2     1  49.435398  12.589491  520.693848  Am Zellweg 2  93464  Tiefenbach  EN 1991-1-4  DIN EN 1991-1-4      NaN  Alle Angaben ohne Gewähr
Exemplary Output:
   The first result has the value 22.5. (in m/s)

Autor

Herr Gebhardt kümmert sich im Kundensupport um die Anliegen unserer Anwender.

Links