arches_extensions.management.commands.maplayer

  1import json
  2from django.db import transaction
  3from django.core.management.base import BaseCommand
  4from django.db.utils import IntegrityError
  5
  6from arches.app.models.models import MapSource, MapLayer
  7
  8class Command(BaseCommand):
  9    """
 10    Manage Arches map layers with this command.
 11
 12    .. warning::
 13        This command is a work-in-progress
 14
 15    Usage:
 16
 17        python manage.py maplayer [operation] [-s/--source] [-n/--name]
 18    
 19    Operations:
 20
 21        - `add`
 22        - `remove`
 23        - `list`
 24
 25    """
 26
 27    def __init__(self, *args, **kwargs):
 28        self.help = self.__doc__
 29
 30    def add_arguments(self, parser):
 31
 32        parser.add_argument(
 33            "operation",
 34            choices=["add", "remove", "list"]
 35        )
 36
 37        parser.add_argument(
 38            "-s", "--source",
 39            help="Map Layer JSON file to be loaded",
 40        )
 41
 42        parser.add_argument(
 43            "-n", "--name",
 44            help="The name of the Map Layer to remove"
 45        )
 46
 47    def handle(self, *args, **options):
 48
 49        if options["operation"] == "add":
 50            self.add_layer(
 51                options["layer_name"],
 52                options["mapbox_json_path"],
 53                options["layer_icon"],
 54                options["is_basemap"],
 55            )
 56
 57        if options["operation"] == "remove":
 58            self.remove_layer(
 59                options["name"]
 60            )
 61
 62        if options["operation"] == "list":
 63            self.list()
 64
 65
 66    def add_layer(self, layer_name=False, mapbox_json_path=False, layer_icon="fa fa-globe", is_basemap=False,
 67    ):
 68        """not yet implemented"""
 69        if layer_name is not False and mapbox_json_path is not False:
 70            with open(mapbox_json_path) as data_file:
 71                data = json.load(data_file)
 72                with transaction.atomic():
 73                    for layer in data["layers"]:
 74                        if "source" in layer:
 75                            layer["source"] = layer["source"] + "-" + layer_name
 76                    for source_name, source_dict in data["sources"].items():
 77                        map_source = MapSource.objects.get_or_create(name=source_name + "-" + layer_name, source=source_dict)
 78                    map_layer = MapLayer(
 79                        name=layer_name, layerdefinitions=data["layers"], isoverlay=(not is_basemap), icon=layer_icon
 80                    )
 81                    try:
 82                        map_layer.save()
 83                    except IntegrityError:
 84                        print("Cannot save layer: {0} already exists".format(layer_name))
 85
 86    def remove_layer(self, layer_name):
 87        try:
 88            layer = MapLayer.objects.get(name=layer_name)
 89        except MapLayer.DoesNotExist:
 90            print(f'error: Map Layer "{layer_name}" does not exist.')
 91            return
 92        sources = set([i.get("source") for i in layer.layerdefinitions])
 93        with transaction.atomic():
 94            # list through and delete sources that aren't None
 95            for source in [i for i in sources if i]:
 96                print(f'removing Map Source "{source}"')
 97                try:
 98                    MapSource.objects.get(name=source).delete()
 99                except MapSource.DoesNotExist:
100                    pass
101            print(f'removing Map Layer "{layer_name}"')
102            layer.delete()
103
104    def list(self):
105        """
106        Lists all registered map layers and the sources they use.
107        """
108
109        layers = MapLayer.objects.all()
110        print(f"-- {layers.count()} Map Layers --")
111        
112        for layer in layers:
113            print(f"{layer.name}")
114            sources = set([i.get("source") for i in layer.layerdefinitions])
115            print(f"  source(s): {', '.join([i for i in sources if i is not None])}")
class Command(django.core.management.base.BaseCommand):
  9class Command(BaseCommand):
 10    """
 11    Manage Arches map layers with this command.
 12
 13    .. warning::
 14        This command is a work-in-progress
 15
 16    Usage:
 17
 18        python manage.py maplayer [operation] [-s/--source] [-n/--name]
 19    
 20    Operations:
 21
 22        - `add`
 23        - `remove`
 24        - `list`
 25
 26    """
 27
 28    def __init__(self, *args, **kwargs):
 29        self.help = self.__doc__
 30
 31    def add_arguments(self, parser):
 32
 33        parser.add_argument(
 34            "operation",
 35            choices=["add", "remove", "list"]
 36        )
 37
 38        parser.add_argument(
 39            "-s", "--source",
 40            help="Map Layer JSON file to be loaded",
 41        )
 42
 43        parser.add_argument(
 44            "-n", "--name",
 45            help="The name of the Map Layer to remove"
 46        )
 47
 48    def handle(self, *args, **options):
 49
 50        if options["operation"] == "add":
 51            self.add_layer(
 52                options["layer_name"],
 53                options["mapbox_json_path"],
 54                options["layer_icon"],
 55                options["is_basemap"],
 56            )
 57
 58        if options["operation"] == "remove":
 59            self.remove_layer(
 60                options["name"]
 61            )
 62
 63        if options["operation"] == "list":
 64            self.list()
 65
 66
 67    def add_layer(self, layer_name=False, mapbox_json_path=False, layer_icon="fa fa-globe", is_basemap=False,
 68    ):
 69        """not yet implemented"""
 70        if layer_name is not False and mapbox_json_path is not False:
 71            with open(mapbox_json_path) as data_file:
 72                data = json.load(data_file)
 73                with transaction.atomic():
 74                    for layer in data["layers"]:
 75                        if "source" in layer:
 76                            layer["source"] = layer["source"] + "-" + layer_name
 77                    for source_name, source_dict in data["sources"].items():
 78                        map_source = MapSource.objects.get_or_create(name=source_name + "-" + layer_name, source=source_dict)
 79                    map_layer = MapLayer(
 80                        name=layer_name, layerdefinitions=data["layers"], isoverlay=(not is_basemap), icon=layer_icon
 81                    )
 82                    try:
 83                        map_layer.save()
 84                    except IntegrityError:
 85                        print("Cannot save layer: {0} already exists".format(layer_name))
 86
 87    def remove_layer(self, layer_name):
 88        try:
 89            layer = MapLayer.objects.get(name=layer_name)
 90        except MapLayer.DoesNotExist:
 91            print(f'error: Map Layer "{layer_name}" does not exist.')
 92            return
 93        sources = set([i.get("source") for i in layer.layerdefinitions])
 94        with transaction.atomic():
 95            # list through and delete sources that aren't None
 96            for source in [i for i in sources if i]:
 97                print(f'removing Map Source "{source}"')
 98                try:
 99                    MapSource.objects.get(name=source).delete()
100                except MapSource.DoesNotExist:
101                    pass
102            print(f'removing Map Layer "{layer_name}"')
103            layer.delete()
104
105    def list(self):
106        """
107        Lists all registered map layers and the sources they use.
108        """
109
110        layers = MapLayer.objects.all()
111        print(f"-- {layers.count()} Map Layers --")
112        
113        for layer in layers:
114            print(f"{layer.name}")
115            sources = set([i.get("source") for i in layer.layerdefinitions])
116            print(f"  source(s): {', '.join([i for i in sources if i is not None])}")

Manage Arches map layers with this command.

This command is a work-in-progress

Usage:

python manage.py maplayer [operation] [-s/--source] [-n/--name]

Operations:

- `add`
- `remove`
- `list`
Command(*args, **kwargs)
28    def __init__(self, *args, **kwargs):
29        self.help = self.__doc__
help = ''
def add_arguments(self, parser):
31    def add_arguments(self, parser):
32
33        parser.add_argument(
34            "operation",
35            choices=["add", "remove", "list"]
36        )
37
38        parser.add_argument(
39            "-s", "--source",
40            help="Map Layer JSON file to be loaded",
41        )
42
43        parser.add_argument(
44            "-n", "--name",
45            help="The name of the Map Layer to remove"
46        )

Entry point for subclassed commands to add custom arguments.

def handle(self, *args, **options):
48    def handle(self, *args, **options):
49
50        if options["operation"] == "add":
51            self.add_layer(
52                options["layer_name"],
53                options["mapbox_json_path"],
54                options["layer_icon"],
55                options["is_basemap"],
56            )
57
58        if options["operation"] == "remove":
59            self.remove_layer(
60                options["name"]
61            )
62
63        if options["operation"] == "list":
64            self.list()

The actual logic of the command. Subclasses must implement this method.

def add_layer( self, layer_name=False, mapbox_json_path=False, layer_icon='fa fa-globe', is_basemap=False):
67    def add_layer(self, layer_name=False, mapbox_json_path=False, layer_icon="fa fa-globe", is_basemap=False,
68    ):
69        """not yet implemented"""
70        if layer_name is not False and mapbox_json_path is not False:
71            with open(mapbox_json_path) as data_file:
72                data = json.load(data_file)
73                with transaction.atomic():
74                    for layer in data["layers"]:
75                        if "source" in layer:
76                            layer["source"] = layer["source"] + "-" + layer_name
77                    for source_name, source_dict in data["sources"].items():
78                        map_source = MapSource.objects.get_or_create(name=source_name + "-" + layer_name, source=source_dict)
79                    map_layer = MapLayer(
80                        name=layer_name, layerdefinitions=data["layers"], isoverlay=(not is_basemap), icon=layer_icon
81                    )
82                    try:
83                        map_layer.save()
84                    except IntegrityError:
85                        print("Cannot save layer: {0} already exists".format(layer_name))

not yet implemented

def remove_layer(self, layer_name):
 87    def remove_layer(self, layer_name):
 88        try:
 89            layer = MapLayer.objects.get(name=layer_name)
 90        except MapLayer.DoesNotExist:
 91            print(f'error: Map Layer "{layer_name}" does not exist.')
 92            return
 93        sources = set([i.get("source") for i in layer.layerdefinitions])
 94        with transaction.atomic():
 95            # list through and delete sources that aren't None
 96            for source in [i for i in sources if i]:
 97                print(f'removing Map Source "{source}"')
 98                try:
 99                    MapSource.objects.get(name=source).delete()
100                except MapSource.DoesNotExist:
101                    pass
102            print(f'removing Map Layer "{layer_name}"')
103            layer.delete()
def list(self):
105    def list(self):
106        """
107        Lists all registered map layers and the sources they use.
108        """
109
110        layers = MapLayer.objects.all()
111        print(f"-- {layers.count()} Map Layers --")
112        
113        for layer in layers:
114            print(f"{layer.name}")
115            sources = set([i.get("source") for i in layer.layerdefinitions])
116            print(f"  source(s): {', '.join([i for i in sources if i is not None])}")

Lists all registered map layers and the sources they use.