Pictures!
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

admin.js 4.1KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171
  1. var querystring = require("querystring");
  2. var fs = require("fs");
  3. var pathlib = require("path");
  4. var formidable = require("formidable");
  5. var basepath = "/admin/api/";
  6. // Used in every method handler to make sure the correct arguments are provided
  7. function hasargs(query, respond, expected) {
  8. var missing = [];
  9. for (var e of expected) {
  10. if (query[e] === undefined)
  11. missing.push(e);
  12. }
  13. if (missing.length > 0) {
  14. respond("Missing arguments: "+missing.join(", "));
  15. return false;
  16. } else {
  17. return true;
  18. }
  19. }
  20. // Method handlers are defined here
  21. var methods = {
  22. // List all slides in the slides directory
  23. list_slides: function(query, conf, req, respond) {
  24. fs.readdir(conf.slides, (err, files) => {
  25. if (err)
  26. return respond(err);
  27. respond(null, files);
  28. });
  29. },
  30. // Get metadata about a slide
  31. slide_meta: function(query, conf, req, respond) {
  32. if (!hasargs(query, respond, [ "slide" ])) return;
  33. var path = pathlib.join(conf.slides, query.slide);
  34. fs.stat(path, (err, stat) => {
  35. if (err || !stat.isDirectory())
  36. return respond(path+" is not a slide.");
  37. fs.readFile(pathlib.join(path, "meta.json"), (err, res) => {
  38. if (err && err.code === "ENOENT")
  39. return respond(null, {});
  40. else if (err)
  41. return respond(err);
  42. try {
  43. respond(null, JSON.parse(res));
  44. } catch (err) {
  45. respond(err);
  46. }
  47. });
  48. });
  49. },
  50. // Get a list of files of a slide
  51. slide_file_list: function(query, conf, req, respond) {
  52. if (!hasargs(query, respond, [ "slide" ])) return;
  53. var dir = pathlib.join(conf.slides, query.slide);
  54. fs.readdir(dir, (err, files) => {
  55. if (err)
  56. return respond(err);
  57. respond(null, { files: files });
  58. });
  59. },
  60. // Get a slide's HTML
  61. slide_content: function(query, conf, req, respond) {
  62. if (!hasargs(query, respond, [ "slide" ])) return;
  63. var path = pathlib.join(conf.slides, query.slide, "index.md");
  64. fs.readFile(path, "utf-8", (err, text) => {
  65. if (err && err.code === "ENOENT")
  66. return respond(null, { text: "" });
  67. else if (err)
  68. return respond(err);
  69. respond(null, { text: text });
  70. });
  71. },
  72. // Update a slide's HTML
  73. slide_content_update: function(query, conf, req, respond) {
  74. if (!hasargs(query, respond, [ "slide", "text" ])) return;
  75. var path = pathlib.join(conf.slides, query.slide, "index.md");
  76. fs.writeFile(path, query.text, err => {
  77. respond(err);
  78. });
  79. },
  80. // Rename a file
  81. slide_file_rename: function(query, conf, req, respond) {
  82. if (!hasargs(query, respond, [ "slide", "from", "to" ])) return;
  83. var op = pathlib.join(conf.slides, query.slide, query.from);
  84. var np = pathlib.join(conf.slides, query.slide, query.to);
  85. fs.rename(op, np, err => respond(err));
  86. },
  87. // Delete a file
  88. slide_file_delete: function(query, conf, req, respond) {
  89. if (!hasargs(query, respond, [ "slide", "file" ])) return;
  90. var path = pathlib.join(conf.slides, query.slide, query.file);
  91. fs.unlink(path, err => respond(err));
  92. },
  93. // Upload a file to a slide
  94. slide_file_upload: function(query, conf, req, respond) {
  95. if (!hasargs(query, respond, [ "slide" ])) return;
  96. var form = new formidable.IncomingForm();
  97. form.uploadDir = pathlib.join(conf.slides, query.slide);
  98. form.keepExtensions = true;
  99. form.on("fileBegin", (name, file) => {
  100. file.path = pathlib.join(form.uploadDir, file.name);
  101. });
  102. form.parse(req, (err, fields, files) => {
  103. respond();
  104. });
  105. }
  106. }
  107. exports.canServe = function(parts) {
  108. // Temporary, while working on stuff
  109. return false;
  110. return methods[parts.pathname.replace(basepath, "")] !== undefined;
  111. }
  112. exports.serve = function(parts, conf, req, res) {
  113. var fn = methods[parts.pathname.replace(basepath, "")];
  114. if (!fn) {
  115. res.writeHead(404);
  116. res.end();
  117. return;
  118. }
  119. var query = querystring.parse(parts.query);
  120. for (var i in query) {
  121. query[i] = decodeURIComponent(query[i]);
  122. }
  123. // Better than manually doing res.end(JSON.stringify(obj)) everywhere
  124. function respond(err, obj) {
  125. var result = {
  126. obj: obj,
  127. err: err ? err.toString() : null
  128. };
  129. if (err)
  130. res.writeHead(400);
  131. else
  132. res.writeHead(200);
  133. res.end(JSON.stringify(result));
  134. }
  135. // Finally, call method handler
  136. fn(query, conf, req, respond);
  137. }