JSONString.cpp 2.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103
  1. //
  2. // String.h
  3. //
  4. // Library: Foundation
  5. // Package: Core
  6. // Module: String
  7. //
  8. // Copyright (c) 2004-2006, Applied Informatics Software Engineering GmbH.
  9. // and Contributors.
  10. //
  11. // SPDX-License-Identifier: BSL-1.0
  12. //
  13. #include "Poco/JSONString.h"
  14. #include "Poco/UTF8String.h"
  15. #include <ostream>
  16. namespace {
  17. template<typename T, typename S>
  18. struct WriteFunc
  19. {
  20. typedef T& (T::*Type)(const char* s, S n);
  21. };
  22. template<typename T, typename S>
  23. void writeString(const std::string &value, T& obj, typename WriteFunc<T, S>::Type write, int options)
  24. {
  25. bool wrap = ((options & Poco::JSON_WRAP_STRINGS) != 0);
  26. bool escapeAllUnicode = ((options & Poco::JSON_ESCAPE_UNICODE) != 0);
  27. if (value.size() == 0)
  28. {
  29. if(wrap) (obj.*write)("\"\"", 2);
  30. return;
  31. }
  32. if(wrap) (obj.*write)("\"", 1);
  33. if(escapeAllUnicode)
  34. {
  35. std::string str = Poco::UTF8::escape(value.begin(), value.end());
  36. (obj.*write)(str.c_str(), str.size());
  37. }
  38. else
  39. {
  40. for(std::string::const_iterator it = value.begin(), end = value.end(); it != end; ++it)
  41. {
  42. // Forward slash isn't strictly required by JSON spec, but some parsers expect it
  43. if((*it >= 0 && *it <= 31) || (*it == '"') || (*it == '\\') || (*it == '/'))
  44. {
  45. std::string str = Poco::UTF8::escape(it, it + 1);
  46. (obj.*write)(str.c_str(), str.size());
  47. }else (obj.*write)(&(*it), 1);
  48. }
  49. }
  50. if(wrap) (obj.*write)("\"", 1);
  51. };
  52. }
  53. namespace Poco {
  54. void toJSON(const std::string& value, std::ostream& out, bool wrap)
  55. {
  56. int options = (wrap ? Poco::JSON_WRAP_STRINGS : 0);
  57. writeString<std::ostream,
  58. std::streamsize>(value, out, &std::ostream::write, options);
  59. }
  60. std::string toJSON(const std::string& value, bool wrap)
  61. {
  62. int options = (wrap ? Poco::JSON_WRAP_STRINGS : 0);
  63. std::string ret;
  64. writeString<std::string,
  65. std::string::size_type>(value, ret, &std::string::append, options);
  66. return ret;
  67. }
  68. void toJSON(const std::string& value, std::ostream& out, int options)
  69. {
  70. writeString<std::ostream, std::streamsize>(value, out, &std::ostream::write, options);
  71. }
  72. std::string toJSON(const std::string& value, int options)
  73. {
  74. std::string ret;
  75. writeString<std::string,
  76. std::string::size_type>(value, ret, &std::string::append, options);
  77. return ret;
  78. }
  79. } // namespace Poco