From: Philipp Spitzer Date: Tue, 19 Oct 2021 20:32:07 +0000 (+0200) Subject: Copy converting JSON to wikitext from wradmin. X-Git-Url: https://git.toastfreeware.priv.at/philipp/winterrodeln/wrpylib.git/commitdiff_plain/8d685d8882aa11010e502a821e3b174852e9c1ec Copy converting JSON to wikitext from wradmin. --- diff --git a/setup.py b/setup.py index 3d2c12a..46cdfb1 100644 --- a/setup.py +++ b/setup.py @@ -24,4 +24,6 @@ setup(name='wrpylib', 'scripts/updatewrreportcache.py', 'scripts/updatewrsledruncache.py', ], + package_data={'wrpylib': ['templates/*']}, + zip_safe=False, ) diff --git a/tests/test_wrmwmarkup.py b/tests/test_wrmwmarkup.py index b9ef0fb..f5248fd 100644 --- a/tests/test_wrmwmarkup.py +++ b/tests/test_wrmwmarkup.py @@ -6,7 +6,7 @@ import wrpylib.wrvalidators import wrpylib.wrmwmarkup from wrpylib.wrvalidators import LonLat from wrpylib.wrmwmarkup import sledrun_from_rodelbahnbox, sledrun_to_rodelbahnbox, \ - inn_from_gasthausbox, inn_to_gasthausbox, lonlat_ele_from_template, latlon_ele_to_template + inn_from_gasthausbox, inn_to_gasthausbox, lonlat_ele_from_template, latlon_ele_to_template, create_sledrun_wiki class TestSledrun(unittest.TestCase): @@ -454,3 +454,9 @@ class TestWrMap(unittest.TestCase): ''')) + + +class TestWikiJson(unittest.TestCase): + def test_empty_json(self): + wiki_text = create_sledrun_wiki({}, None) + self.assertIsInstance(wiki_text, str) diff --git a/wrpylib/templates/sledrun_wiki.txt b/wrpylib/templates/sledrun_wiki.txt new file mode 100644 index 0000000..341e09f --- /dev/null +++ b/wrpylib/templates/sledrun_wiki.txt @@ -0,0 +1,86 @@ +{% block content %} +== Allgemeines == +{{ rodelbahnbox }} +{{ description }} +{% raw %} +* {{Position oben}} +* {{Position unten}} +* {{Höhenunterschied}} +* {{Bahnlänge}} +* {{Gehzeit}} +{% endraw -%} +* '''Beleuchtung''': {{ night_light }} +* '''Rodelverleih''': {{ sled_rental_description }} +* '''Schneelage - Auskunft''':{% for info in sledrun_json.get('info_phone', []) %} +** {{ info['phone'] }} ({{ info['name'] }}){% endfor %}{% for info in sledrun_json.get('info_web', []) %} +** {% if 'text' in info %}[{{ info['url'] }} {{ info['text'] }}]{% else %}{{ info['url'] }}{% endif %}{% endfor %} +* '''Betreiber''': {{ operator }} +* '''Hütten''':{% for info in sledrun_json.get('gastronomy', []) %} +** {% if 'wr_page' in info -%} + {% if 'name' in info %}[[{{ info['wr_page']['title'] }}|{{ info['name'] }}]] + {%- else %}{{ info['wr_page'] }}{% endif -%} + {% endif -%} + {% endfor %} +* '''Andere Rodelbahnen''': +** [[Untermarkter Alm]] +* '''Siehe auch''':{% for info in sledrun_json.get('see_also', []) %} +** {% if 'text' in info %}[{{ info['url'] }} {{ info['text'] }}]{% else %}{{ info['url'] }}{% endif %}{% endfor %} + + +{% raw %}{{Buttonleiste{% endraw -%} +|Bericht={% if sledrun_json.get('allow_reports', True) %}Ja{% else %}Nein{% endif -%} +{% if 'forum_id' in sledrun_json %}|ForumId={{ sledrun_json['forum_id'] }}{% endif -%} +{% if 'position' in sledrun_json %}|Wetter=Ja{% endif -%} +|Korrektur=Seite{% if 'correction_email' in sledrun_json %}|Korrektur_To={{ sledrun_json['correction_email'] }}{% endif -%} +{% if 'freizeitticket_tyrol' in sledrun_json %}|Freizeitticket=Ja{% endif -%} +{% if 'regio_card_tyrol' in sledrun_json %}|Regiocard=Ja{% endif -%}}} +{% raw %}{{Clear}}{% endraw %} + + +== Landkarte == +{% if map_json is none -%} +''leider ist derzeit keine [[Winterrodeln:Landkarte|Landkarte]] zu dieser Rodelbahn vorhanden'' +{%- else -%} +{{ h.create_wrmap(map_json) }} +{% raw %}{{Landkarte Legende}}
{{GoogleMaps Hinweis}}{% endraw %} +{% endif %} + +== Anreise mit öffentlichen Verkehrsmitteln == +{% if 'public_transport_description' in sledrun_json %}{{ sledrun_json['public_transport_description'] }} +{%- else %}''Hier wird die Anreise mit öffentlichen Verkehrsmitteln beschrieben.''{% endif %} + +{% for pt_stop in sledrun_json.get('public_transport_stops', []) -%} +* {{ h.list_template('Haltestelle', [pt_stop.get('name', ''), '', h.json_pos_ele_position(pt_stop.get('position', '')), h.json_pos_ele_elevation(pt_stop.get('position', ''))]) }} +{% for template_name in ['monitor_template', 'route_arrival_template', 'route_departure_template'] -%} +{% if template_name in pt_stop -%} +** {{ h.json_template(pt_stop[template_name]) }} +{% endif %} +{%- endfor %} +{%- endfor -%} +{% for pt_line in sledrun_json.get('public_transport_lines', []) -%} +{% if loop.first -%} +* '''Fahrplan''': +{% endif -%} +** {% if pt_line.timetable_template is defined %}{{ h.json_template(pt_line.timetable_template) }} + {%- else %}{{ pt_line.name }}{% endif %} +{% endfor %} + + +== Anreise mit dem Auto == +{% if 'car_description' in sledrun_json %}{{ sledrun_json.car_description }} +{%- else %}''Hier wird die Anreise mit dem Auto beschrieben.''{% endif %} + +{% for parking in sledrun_json.car_parking -%} +* '''Parkplatz''': {{ h.list_template('Parkplatz', [h.json_pos_ele_position(parking.position), h.json_pos_ele_elevation(parking.position)]) }} +{% endfor -%} +{% for distance_info in sledrun_json.car_distances -%} +{% if loop.first -%} +* '''Entfernung''': +{% endif -%} +** {{ distance_info.route }}: {{ distance_info.km }} km +{% endfor %} + +{% raw %}{{Rodelbahnzustand|Forumlink={% endraw %}{{ sledrun_json.forum_id }}}} + +[[Kategorie:Rodelbahn]] +{% endblock %} diff --git a/wrpylib/wrmwmarkup.py b/wrpylib/wrmwmarkup.py index b346c55..def51f1 100644 --- a/wrpylib/wrmwmarkup.py +++ b/wrpylib/wrmwmarkup.py @@ -1,10 +1,12 @@ """This module contains winterrodeln specific functions that are processing the MediaWiki markup. """ import re +import subprocess import xml.etree.ElementTree import collections from typing import Tuple, Optional, List, OrderedDict, Union, Dict +import jinja2 from mwparserfromhell.nodes import Template import wrpylib.wrvalidators @@ -12,7 +14,9 @@ import wrpylib.mwmarkup import wrpylib.wrmwdb from wrpylib.wrvalidators import LonLat, opt_lonlat_from_str, opt_lonlat_to_str, opt_uint_from_str, opt_uint_to_str, \ opt_str_opt_comment_enum_to_str, lift_german_to_str, webauskunft_to_str, cachet_german_to_str, \ - opt_phone_comment_enum_to_str, lift_german_from_str, GASTHAUSBOX_DICT + opt_phone_comment_enum_to_str, lift_german_from_str, GASTHAUSBOX_DICT, opt_difficulty_german_from_str, \ + opt_avalanches_german_from_str, nightlightdays_from_str, opt_public_transport_german_from_str, \ + opt_tristate_german_comment_from_str, rodelbahnbox_to_str, lonlat_to_str def split_lon_lat(value: Optional[LonLat]) -> Union[LonLat, Tuple[None, None]]: @@ -328,3 +332,142 @@ def create_wrmap(geojson: Dict) -> str: if last_json_feature is not None: last_json_feature.tail = '\n\n' return xml.etree.ElementTree.tostring(wrmap_xml, encoding='utf-8').decode('utf-8') + + +class Jinja2Tools: + def create_wrmap(self, geojson: Dict) -> str: + return create_wrmap(geojson) + + def json_position(self, value: dict) -> str: + lon_lat = LonLat(value['longitude'], value['latitude']) + return lonlat_to_str(lon_lat) + + def json_pos_ele_position(self, value: dict) -> str: + pos = value.get('position') + if pos is None: + return '' + return self.json_position(pos) + + def json_pos_ele_elevation(self, value: dict) -> str: + return value.get('elevation', '') + + def list_template(self, name: str, value: List[str]) -> str: + return str(wrpylib.mwmarkup.create_template(name, value)) + + def json_template(self, value) -> str: + args = [] + kwargs = {} + for p in value.get('parameter', []): + v = p.get('value', '') + if 'key' in p: + kwargs[p['key']] = v + else: + args.append(v) + return str(wrpylib.mwmarkup.create_template(value['name'], args, kwargs)) + + +def create_sledrun_wiki(sledrun_json: Dict, map_json: Optional[Dict]) -> str: + env = jinja2.Environment( + loader=jinja2.PackageLoader("wrpylib"), + autoescape=jinja2.select_autoescape() + ) + template = env.get_template("sledrun_wiki.txt") + + def markdown_to_mediawiki(markdown: str) -> str: + return subprocess.check_output(['pandoc', '--to', 'mediawiki'], input=markdown, encoding='utf-8') + + def position_to_lon_lat(value: Optional[dict]) -> Optional[LonLat]: + if value is not None: + lon = value.get('longitude') + lat = value.get('latitude') + if lon is not None and lat is not None: + return LonLat(lon, lat) + return None + + def position_ele_to_lon_lat(value: Optional[dict]) -> Optional[LonLat]: + if value is not None: + return position_to_lon_lat(value.get("position")) + return None + + def position_ele_to_ele(value: Optional[dict]) -> Optional[int]: + if value is not None: + ele = value.get('elevation') + if ele is not None: + return int(ele) + return None + + def aufstiegshilfe() -> Optional[List[Tuple[str, Optional[str]]]]: + ws = sledrun_json.get('walkup_supports') + if ws is None: + return None + return [(w['type'], w.get('comment')) for w in ws] + + def rodelverleih() -> Optional[List[Tuple[str, Optional[str]]]]: + sr = sledrun_json.get('sled_rental_direct') + if sr is None: + return None + return [('Ja', None)] if sr else [] + + def webauskunft() -> Tuple[Optional[bool], Optional[str]]: + info_web = sledrun_json.get('info_web') + if info_web is None: + return None, None + if len(info_web) == 0: + return False, None + return True, info_web[0]['url'] + + def telefonauskunft() -> Optional[List[Tuple[str, str]]]: + info_phone = sledrun_json.get('info_phone') + if info_phone is None: + return None + return [(pc['phone'], pc['name']) for pc in info_phone] + + def betreiber() -> str: + has_operator = sledrun_json.get('has_operator') + if has_operator is None: + return sledrun_json.get('operator') + if has_operator: + return sledrun_json.get('operator') + return 'Nein' + + sledrun_rbb_json = collections.OrderedDict([ + ('Position', position_to_lon_lat(sledrun_json.get('position'))), + ('Position oben', position_ele_to_lon_lat(sledrun_json.get('top'))), + ('Höhe oben', position_ele_to_ele(sledrun_json.get('top'))), + ('Position unten', position_ele_to_lon_lat(sledrun_json.get('bottom'))), + ('Höhe unten', position_ele_to_ele(sledrun_json.get('bottom'))), + ('Länge', sledrun_json.get('length')), + ('Schwierigkeit', opt_difficulty_german_from_str(sledrun_json.get('difficulty', ''))), + ('Lawinen', opt_avalanches_german_from_str(sledrun_json.get('avalanches', ''))), + ('Betreiber', betreiber()), + ('Öffentliche Anreise', opt_public_transport_german_from_str(sledrun_json.get('public_transport', ''))), + ('Aufstieg möglich', sledrun_json.get('walkup_possible')), + ('Aufstieg getrennt', opt_tristate_german_comment_from_str(sledrun_json.get('walkup_separate', ''))), + ('Gehzeit', sledrun_json.get('walkup_time')), + ('Aufstiegshilfe', aufstiegshilfe()), + ('Beleuchtungsanlage', opt_tristate_german_comment_from_str(sledrun_json.get('nightlight_possible', ''))), + ('Beleuchtungstage', nightlightdays_from_str(sledrun_json.get('nightlight_weekdays', ''))), + ('Rodelverleih', rodelverleih()), + ('Gütesiegel', None), + ('Webauskunft', webauskunft()), + ('Telefonauskunft', telefonauskunft()), + ('Bild', sledrun_json.get('image')), + ('In Übersichtskarte', sledrun_json.get('show_in_overview')), + ('Forumid', sledrun_json.get('forum_id')) + ]) + + def get_markdown_field(key: str) -> str: + if key in sledrun_json: + return markdown_to_mediawiki(sledrun_json[key]) + return '' + + description = get_markdown_field('description').strip() + night_light = get_markdown_field('night_light').strip() + sled_rental_description = get_markdown_field('sled_rental_description').strip() + + rodelbahnbox = rodelbahnbox_to_str(sledrun_rbb_json) + + return template.render(sledrun_json=sledrun_json, + rodelbahnbox=rodelbahnbox, description=description, night_light=night_light, + sled_rental_description=sled_rental_description, operator=betreiber(), + map_json=map_json, h=Jinja2Tools())