How can I unpack a Map value into a {{ range}} pipeline

Hi,

I’m trying to display details in this format on my page after getting values from my database.

Name: Danny
Class: GoBeginnerClass

I have a method GetDetails()map[string]string{} that returns a map.

const(
db_path = “root:pass@/trialdb”
//
retrieve_query = “SELECT name, class FROM people”
)

func GetComments()map[string]string{
dbase, err := sql.Open(“mysql”, db_path)
if err != nil{
log.Println("Error @ getDetails dbase: ", err)
}
defer dbase.Close()

query, err := dbase.Query(retrieve_query)
if err != nil{
    log.Println("Error @ retrieve_query: ", err)
}
var name string
var class string
students := make(map[string]string)
for query.Next(){
    err := query.Scan(&n, &c)
    if err != nil{
        log.Println("Error while scanning name and class:", err)
    }
    students[n] = c // saves name and correspondin class in a map 
}
return students

}

  1. I expect this method to return a map that have names and classes saved in it. I’m also worried the new values will get overwritten as the iteration continues (Not sure tho)

In my main func, I want to serve the details like this.

{{ range $key, $value := .}}


– htag{{ .key}}–htag
–ptag{{ .value}}–ptag

{{ end}}

Note: the --htag and --ptag refers to the html h1 and p tag

So, I save my map in a new variable like this

t, err := template.ParseFiles(“display.html”)
var x map[string]string
x = GetComments()
PageData := &FullValues{x} // FullValues is a struct that has a map field
t.Execute(w, PageData)

There are no compile errors and also no Visile runtime errors. The only thing is that the template is not rendered.

Please if this is not clear enough, kindly ask me.

Thank you Friends… :grin:

Hey there. Just curiously, if the template is not loading at all, can you try this and let me know if there is any change:

Instead of calling:

t.Execute(w, PageData)

Try:

t.ExecuteTemplate(w, "display.html", PageData)

Still did not work. Have I done the Pipeline on the html page well?

Oh, no you didn’t. I just tried with this and it worked fine for me:

{{ range $key, $value := . }}
<h3>{{ $key }}</h3>
<p>{{ $value }}</p>
{{ end }}

You might still need to change the line I mentioned in the above post since you used template.ParseFiles if you still get no output.

t.ExecuteTemplate(w, "display.html", PageData)

Okay, I’ll try that too. Do you think the trick from the GetComments()map[string]string{} will work fine.

I’m not getting any errors tho, and I can’t see it either. I should probably print it in somehow so I know if it’s working.

Thanks radov… for helping :yum:

No problemo. You can use this code as a reference to get your template working if you like. Just wrote it out for you now.

display.html:

{{ range $key, $value := . }}
<h1>{{ $key }}</h1>
<p>{{ $value }}</p>
{{ end }}

main.go

package main

import (
	"html/template"
	"log"
	"os"
)

func main() {
	students := map[string]string{
		"Danny": "GoBeginnersClass",
		"Benji": "GoMediumsClass",
		"Mike":  "GoAdvancedClass",
	}

	t, err := template.ParseFiles("display.html")
	if err != nil {
		log.Fatalln(err)
	}

	err = t.ExecuteTemplate(os.Stdout, "display.html", students)
	if err != nil {
		log.Fatalln(err)
	}
}
1 Like

The methods Template.Execute and Template.ExecuteTemplate both return an error. Checking it may reveal clues.

Oh!!! calmh,

I handled the error and guess what, I got information.
I did it the way “radovskyb” posted, and of course, the page did not go blank anymore, but still I did not get the values I want. Only the default html was rendered.

However, when I handled the error, it was not clear enough, and what I got only says

" executing students.html at <.>template" range can’t iterate over {map[“prints out all the values of the map here”]}

The error is not clear enough, do you have any clues?

Post a runnable example to https://play.golang.org/ and I’m sure we can sort it out. :wink:

Okay, is that also a forum? I clicked the link, that’s where I started off with go, The playground. How do I post it there?

You write or paste the code in the box, try it with “Run” until it demonstrates your problem, then hit “Share” and post the link here.

Okay, but there is really no way to test with an html file.

Just use a template in a string instead?

Yeah, check this out. I hope I did it right. It’s runnable, but has an error.

https://play.golang.org/p/4jnVRbbg5f

You need to parse the template correctly (and printing the error you get clarifies that…):

https://play.golang.org/p/EUXXUIdsPy

Thanks, It worked.

I did something like

{{ range $key $value := .MapVar}}
{{ $key}}
{{ $value}}

The solution is the equal to, I had to change {{ range $key $value := . }} to {{ range $key $value := .MapVar}}

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.