json.go 1.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. package option
  2. import (
  3. "bytes"
  4. "github.com/sagernet/sing-box/common/badjson"
  5. "github.com/sagernet/sing-box/common/json"
  6. "github.com/sagernet/sing/common"
  7. E "github.com/sagernet/sing/common/exceptions"
  8. )
  9. func ToMap(v any) (*badjson.JSONObject, error) {
  10. inputContent, err := json.Marshal(v)
  11. if err != nil {
  12. return nil, err
  13. }
  14. var content badjson.JSONObject
  15. err = content.UnmarshalJSON(inputContent)
  16. if err != nil {
  17. return nil, err
  18. }
  19. return &content, nil
  20. }
  21. func MergeObjects(objects ...any) (*badjson.JSONObject, error) {
  22. var content badjson.JSONObject
  23. for _, object := range objects {
  24. objectMap, err := ToMap(object)
  25. if err != nil {
  26. return nil, err
  27. }
  28. content.PutAll(objectMap)
  29. }
  30. return &content, nil
  31. }
  32. func MarshallObjects(objects ...any) ([]byte, error) {
  33. objects = common.FilterNotNil(objects)
  34. if len(objects) == 1 {
  35. return json.Marshal(objects[0])
  36. }
  37. content, err := MergeObjects(objects...)
  38. if err != nil {
  39. return nil, err
  40. }
  41. return content.MarshalJSON()
  42. }
  43. func UnmarshallExcluded(inputContent []byte, parentObject any, object any) error {
  44. parentContent, err := ToMap(parentObject)
  45. if err != nil {
  46. return err
  47. }
  48. var content badjson.JSONObject
  49. err = content.UnmarshalJSON(inputContent)
  50. if err != nil {
  51. return err
  52. }
  53. for _, key := range parentContent.Keys() {
  54. content.Remove(key)
  55. }
  56. if object == nil {
  57. if content.IsEmpty() {
  58. return nil
  59. }
  60. return E.New("unexpected key: ", content.Keys()[0])
  61. }
  62. inputContent, err = content.MarshalJSON()
  63. if err != nil {
  64. return err
  65. }
  66. decoder := json.NewDecoder(bytes.NewReader(inputContent))
  67. decoder.DisallowUnknownFields()
  68. return decoder.Decode(object)
  69. }