JsonHelper.cs 3.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798
  1. using System.IO;
  2. using System.Text;
  3. using System.Text.Json;
  4. using System.Text.Json.Serialization.Metadata;
  5. namespace Ryujinx.Common.Utilities
  6. {
  7. public class JsonHelper
  8. {
  9. private static readonly JsonNamingPolicy SnakeCasePolicy = new SnakeCaseNamingPolicy();
  10. private const int DefaultFileWriteBufferSize = 4096;
  11. /// <summary>
  12. /// Creates new serializer options with default settings.
  13. /// </summary>
  14. /// <remarks>
  15. /// It is REQUIRED for you to save returned options statically or as a part of static serializer context
  16. /// in order to avoid performance issues. You can safely modify returned options for your case before storing.
  17. /// </remarks>
  18. public static JsonSerializerOptions GetDefaultSerializerOptions(bool indented = true)
  19. {
  20. JsonSerializerOptions options = new()
  21. {
  22. DictionaryKeyPolicy = SnakeCasePolicy,
  23. PropertyNamingPolicy = SnakeCasePolicy,
  24. WriteIndented = indented,
  25. AllowTrailingCommas = true,
  26. ReadCommentHandling = JsonCommentHandling.Skip
  27. };
  28. return options;
  29. }
  30. public static string Serialize<T>(T value, JsonTypeInfo<T> typeInfo)
  31. {
  32. return JsonSerializer.Serialize(value, typeInfo);
  33. }
  34. public static T Deserialize<T>(string value, JsonTypeInfo<T> typeInfo)
  35. {
  36. return JsonSerializer.Deserialize(value, typeInfo);
  37. }
  38. public static void SerializeToFile<T>(string filePath, T value, JsonTypeInfo<T> typeInfo)
  39. {
  40. using FileStream file = File.Create(filePath, DefaultFileWriteBufferSize, FileOptions.WriteThrough);
  41. JsonSerializer.Serialize(file, value, typeInfo);
  42. }
  43. public static T DeserializeFromFile<T>(string filePath, JsonTypeInfo<T> typeInfo)
  44. {
  45. using FileStream file = File.OpenRead(filePath);
  46. return JsonSerializer.Deserialize(file, typeInfo);
  47. }
  48. public static void SerializeToStream<T>(Stream stream, T value, JsonTypeInfo<T> typeInfo)
  49. {
  50. JsonSerializer.Serialize(stream, value, typeInfo);
  51. }
  52. private class SnakeCaseNamingPolicy : JsonNamingPolicy
  53. {
  54. public override string ConvertName(string name)
  55. {
  56. if (string.IsNullOrEmpty(name))
  57. {
  58. return name;
  59. }
  60. StringBuilder builder = new();
  61. for (int i = 0; i < name.Length; i++)
  62. {
  63. char c = name[i];
  64. if (char.IsUpper(c))
  65. {
  66. if (i == 0 || char.IsUpper(name[i - 1]))
  67. {
  68. builder.Append(char.ToLowerInvariant(c));
  69. }
  70. else
  71. {
  72. builder.Append('_');
  73. builder.Append(char.ToLowerInvariant(c));
  74. }
  75. }
  76. else
  77. {
  78. builder.Append(c);
  79. }
  80. }
  81. return builder.ToString();
  82. }
  83. }
  84. }
  85. }