[SOLVED] Reflect func (Value) SetString | reflect.flag.mustBeAssignable

Hi everyone,

Given the situation below, I got the following panic output:
panic: reflect: reflect.flag.mustBeAssignable using unaddressable value

Call to val.CanSet() also returns false

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

package main

import (
	"fmt"
	"reflect"
)

type Foo struct {
        Id, Bar string
}

func create(data interface{}) {
        val := reflect.ValueOf(data).FieldByName("Id")
        fmt.Println(val.CanSet())

        id := "someString"
        val.SetString(id)
}

func main() {
	create(Foo{
		Bar: "foo",
	})
}

I want this function to automatically assign a value to the Id field.
Unfortunately I don’t quiet understand reflect.flag.mustBeAssignable.

I search through the forum, the go doc on reflect package but nothing appears to give me more advice on the value assignment topic with this particular case.

Can someone point me to the right direction ?

Waiting to here from you.
Have a nice day.
Thomas

2 Likes

For the one having the same issue, I found the solution by digging on reflect package doc. The most useful part is here :

CanAddr reports whether the value’s address can be obtained with Addr. Such values are called addressable. A value is addressable if it is an element of a slice, an element of an addressable array, a field of an addressable struct, or the result of dereferencing a pointer. If CanAddr returns false, calling Addr will panic.

Then, below outputs true :slight_smile:

package main

import (
	"fmt"
	"reflect"
)

type Foo struct {
	Id, Bar string
}

func create(data interface{}) {
	val := reflect.ValueOf(data).Elem()
	fmt.Println(val.CanSet())

	id := "someString"
	val.FieldByName("Id").SetString(id)
}

func main() {
	create(&Foo{
		Bar: "Foo",
	})
}

I must say godoc is amazing ! Cheers.

2 Likes

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