1/*2Maddy Mail Server - Composable all-in-one email server.3Copyright © 2019-2020 Max Mazurov <fox.cpp@disroot.org>, Maddy Mail Server contributors45This program is free software: you can redistribute it and/or modify6it under the terms of the GNU General Public License as published by7the Free Software Foundation, either version 3 of the License, or8(at your option) any later version.910This program is distributed in the hope that it will be useful,11but WITHOUT ANY WARRANTY; without even the implied warranty of12MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the13GNU General Public License for more details.1415You should have received a copy of the GNU General Public License16along with this program. If not, see <https://www.gnu.org/licenses/>.17*/1819package exterrors2021type fieldsErr interface {22 Fields() map[string]interface{}23}2425type unwrapper interface {26 Unwrap() error27}2829type fieldsWrap struct {30 err error31 fields map[string]interface{}32}3334func (fw fieldsWrap) Error() string {35 return fw.err.Error()36}3738func (fw fieldsWrap) Unwrap() error {39 return fw.err40}4142func (fw fieldsWrap) Fields() map[string]interface{} {43 return fw.fields44}4546func Fields(err error) map[string]interface{} {47 fields := make(map[string]interface{}, 5)4849 for err != nil {50 errFields, ok := err.(fieldsErr)51 if ok {52 for k, v := range errFields.Fields() {53 // Outer errors override fields of the inner ones.54 // Not the reverse.55 if fields[k] != nil {56 continue57 }58 fields[k] = v59 }60 }6162 unwrap, ok := err.(unwrapper)63 if !ok {64 break65 }66 err = unwrap.Unwrap()67 }6869 return fields70}7172func WithFields(err error, fields map[string]interface{}) error {73 return fieldsWrap{err: err, fields: fields}74}