I defined a "role" type which is a uint64
and use its high 24-bit value to store user roles, and the lower 40-bit are reserved for user-id. My problem now is the custom json marshaler will cause stack overflow. Full code below:
type Role uint64
const (
RoleAdmin Role = (1 << 40) << iota
RoleProjectManager
RoleOperator
RoleDeveloper
)
var roleNames map[Role]string
func (r Role) Is(a Role) bool {
return r&a != 0
}
func (r Role) Values() []map[string]any {
rv := []map[string]any{}
for m, n := range roleNames {
if r.Is(m) {
rv = append(rv, map[string]any{"id": m, "name": n})
}
}
return rv
}
func (r Role) MarshalJSON() ([]byte, error) {
return json.Marshal(r.Values())
}
func init() {
roleNames = map[Role]string{
RoleAdmin: "administrator",
RoleProjectManager: "project manager",
RoleOperator: "operator",
RoleDeveloper: "developer",
}
}
If I change the marshaler to a pointer receiver, like this:
func (r *Role) MarshalJSON() ([]byte, error) {
return json.Marshal(r.Values())
}
It will work fine. As far as I understand, unlike UnmarshalJSON()
, there is no need to use pointer receiver for MarshalJSON()
.