main.cc 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135
  1. #include <unistd.h>
  2. #include <iostream>
  3. #include <silicon/backends/mhd.hh>
  4. #include <silicon/api.hh>
  5. #include <silicon/middlewares/mysql_connection.hh>
  6. #include <silicon/middlewares/mysql_orm.hh>
  7. #include "symbols.hh"
  8. using namespace s;
  9. using namespace sl;
  10. typedef decltype(D(_id(_auto_increment, _primary_key) = int(),
  11. _randomNumber = int())) random_number;
  12. typedef decltype(D(_id(_auto_increment, _primary_key) = int(),
  13. _message = std::string())) fortune;
  14. typedef mysql_orm_factory<random_number> rn_orm_factory;
  15. typedef mysql_orm<random_number> rn_orm;
  16. typedef mysql_orm_factory<fortune> fortune_orm_factory;
  17. typedef mysql_orm<fortune> fortune_orm;
  18. std::string escape_html_entities(const std::string& data)
  19. {
  20. std::string buffer;
  21. buffer.reserve(data.size());
  22. for(size_t pos = 0; pos != data.size(); ++pos) {
  23. switch(data[pos]) {
  24. case '&': buffer.append("&amp;"); break;
  25. case '\"': buffer.append("&quot;"); break;
  26. case '\'': buffer.append("&apos;"); break;
  27. case '<': buffer.append("&lt;"); break;
  28. case '>': buffer.append("&gt;"); break;
  29. default: buffer.append(&data[pos], 1); break;
  30. }
  31. }
  32. return std::move(buffer);
  33. }
  34. int main(int argc, char* argv[])
  35. {
  36. if (argc != 4)
  37. {
  38. std::cerr << "Usage: " << argv[0] << " mysql_host port pid_file" << std::endl;
  39. return 1;
  40. }
  41. auto hello_api = make_api(
  42. _plaintext = [] () { return "Hello, World!"; },
  43. _json = [] () { return D(_message = "Hello, World!"); },
  44. _db = [] (rn_orm& orm) {
  45. random_number r;
  46. orm.find_by_id(1245, r);
  47. return r;
  48. },
  49. _queries = [] (rn_orm& orm, get_parameters& get_params) {
  50. int N = atoi(get_params["queries"].c_str());
  51. N = std::max(1, std::min(N, 500));
  52. std::vector<random_number> qs(N);
  53. for (int i = 0; i < N; i++)
  54. orm.find_by_id(1 + rand() % 9999, qs[i]);
  55. return std::move(qs);
  56. },
  57. _updates = [] (rn_orm& orm, get_parameters& get_params) {
  58. int N = atoi(get_params["queries"].c_str());
  59. N = std::max(1, std::min(N, 500));
  60. std::vector<random_number> qs(N);
  61. for (int i = 0; i < N; i++)
  62. {
  63. orm.find_by_id(1 + rand() % 9999, qs[i]);
  64. qs[i].randomNumber = 1 + rand() % 9999;
  65. orm.update(qs[i]);
  66. }
  67. return std::move(qs);
  68. },
  69. _fortunes = [] (fortune_orm& orm) {
  70. std::vector<fortune> table;
  71. orm.forall([&] (fortune& f) { table.push_back(f); });
  72. table.push_back(fortune(0, "Additional fortune added at request time."));
  73. std::sort(table.begin(), table.end(),
  74. [] (const fortune& a, const fortune& b) { return a.message < b.message; });
  75. std::stringstream ss;
  76. ss << "<!DOCTYPE html><html><head><title>Fortunes</title></head><body><table><tr><th>id</th><th>message</th></tr>";
  77. for(auto& f : table)
  78. ss << "<tr><td>" << f.id << "</td><td>" << escape_html_entities(f.message) << "</td></tr>";
  79. ss << "</table></body></html>";
  80. return ss.str();
  81. }
  82. ).bind_factories(
  83. mysql_connection_factory(argv[1], "benchmarkdbuser", "benchmarkdbpass", "hello_world"),
  84. fortune_orm_factory("Fortune"),
  85. rn_orm_factory("World")
  86. );
  87. try
  88. {
  89. // Demonize the process.
  90. if (daemon(0,0))
  91. {
  92. std::cerr << "Cannot start the daemon." << std::endl;
  93. exit(1);
  94. }
  95. // Write the pid.
  96. std::ofstream pidfile(argv[3]);
  97. pidfile << getpid() << std::endl;
  98. pidfile.close();
  99. // Start the server.
  100. sl::mhd_json_serve(hello_api, atoi(argv[2]));
  101. }
  102. catch (std::exception& e)
  103. {
  104. std::cerr << e.what() << std::endl;
  105. }
  106. catch (sl::error::error& e)
  107. {
  108. std::cerr << e.what() << std::endl;
  109. }
  110. }