changeset 4936:21a48e2d2260 fairway-marks-import

Create group layers in GeoServer via REST calls.
author Sascha L. Teichmann <sascha.teichmann@intevation.de>
date Mon, 17 Feb 2020 00:45:21 +0100
parents c64dba002726
children 40da1b8aba01
files pkg/geoserver/boot.go
diffstat 1 files changed, 118 insertions(+), 15 deletions(-) [+]
line wrap: on
line diff
--- a/pkg/geoserver/boot.go	Sun Feb 16 15:16:22 2020 +0100
+++ b/pkg/geoserver/boot.go	Mon Feb 17 00:45:21 2020 +0100
@@ -245,6 +245,14 @@
 }
 
 func ensureFeatures() error {
+	tables := models.InternalServices.Filter(models.IntWFS)
+	if len(tables) == 0 {
+		log.Println("info: no tables to publish")
+		return nil
+	}
+
+	log.Printf("info: number of tables to publish %d\n", len(tables))
+
 	var (
 		geoURL   = config.GeoServerURL()
 		user     = config.GeoServerUser()
@@ -255,14 +263,6 @@
 	datastoreURL := geoURL + "/rest/workspaces/" + workspaceName +
 		"/datastores/" + datastoreName
 
-	tables := models.InternalServices.Filter(models.IntWFS)
-	if len(tables) == 0 {
-		log.Println("info: no tables to publish")
-		return nil
-	}
-
-	log.Printf("info: number of tables to publish %d\n", len(tables))
-
 	var features struct {
 		FeatureTypes struct {
 			FeatureType []struct {
@@ -394,16 +394,119 @@
 	}
 
 	log.Printf("info: number of layer groups to publish %d\n", len(groups))
-	// TODO: Implement me!
+
+	var (
+		geoURL   = config.GeoServerURL()
+		user     = config.GeoServerUser()
+		password = config.GeoServerPassword()
+		auth     = basicAuth(user, password)
+	)
 
-	/*
-		for i := range groups {
-			log.Printf("info: layer group #%d: %s\n", i+1, groups[i].Name)
-			for _, layer := range groups[i].Layers {
-				log.Printf("info: layer: %s\n", layer)
+	type layerGroups struct {
+		LayerGroups struct {
+			LayerGroup []struct {
+				Name string `json:"name"`
+			} `json:"layerGroup"`
+		} `json:"layerGroups"`
+	}
+
+	var lg layerGroups
+
+	hasLayerGroup := func(name string) bool {
+		for i := range lg.LayerGroups.LayerGroup {
+			if lg.LayerGroups.LayerGroup[i].Name == name {
+				return true
 			}
 		}
-	*/
+		return false
+	}
+
+	layerGroupsURL := geoURL + "/rest/workspaces/" + workspaceName +
+		"/layergroups"
+
+	// Fetch all layer groups.
+	req, err := http.NewRequest(
+		http.MethodGet,
+		layerGroupsURL+".json",
+		nil)
+	if err != nil {
+		return err
+	}
+	auth(req)
+	resp, err := http.DefaultClient.Do(req)
+	if err != nil {
+		return err
+	}
+
+	err = json.NewDecoder(resp.Body).Decode(&lg)
+	resp.Body.Close()
+	if err != nil {
+		// XXX: ignore this error.
+	}
+
+	var already []string
+
+	defer func() {
+		if len(already) > 0 {
+			log.Printf("info: already having layer groups: %s\n",
+				strings.Join(already, ", "))
+		}
+	}()
+
+	for i := range groups {
+		if hasLayerGroup(groups[i].Name) {
+			already = append(already, groups[i].Name)
+			continue
+		}
+
+		type (
+			Layers struct {
+				Layer []string `xml:"layer"`
+			}
+			Styles struct {
+				Style []string `xml:"style"`
+			}
+			LayerGroup struct {
+				XMLName xml.Name `xml:"layerGroup"`
+				Name    string   `xml:"name"`
+				Title   string   `xml:"title"`
+				Layers  Layers   `xml:"layers"`
+				Styles  Styles   `xml:"styles"`
+			}
+		)
+
+		lgr := LayerGroup{
+			Name:  groups[i].Name,
+			Title: groups[i].Name,
+			Layers: Layers{
+				Layer: groups[i].Layers,
+			},
+			Styles: Styles{
+				Style: groups[i].Layers,
+			},
+		}
+
+		req, err = http.NewRequest(
+			http.MethodPost,
+			layerGroupsURL+".xml",
+			toXMLStream(&lgr))
+		if err != nil {
+			return err
+		}
+		asContentType(req, "text/xml")
+		auth(req)
+
+		resp, err := http.DefaultClient.Do(req)
+		if err != nil {
+			return err
+		}
+
+		if resp.StatusCode != http.StatusCreated {
+			return fmt.Errorf("status code '%s' (%d)",
+				http.StatusText(resp.StatusCode),
+				resp.StatusCode)
+		}
+	}
 
 	return nil
 }