From 77ccaef87d14ba6d908b13a8a768442b2a59749c Mon Sep 17 00:00:00 2001 From: alban Date: Sun, 24 May 2020 23:02:56 +0200 Subject: [PATCH] [enh] There should be a patch method. Also, DOM events should work... --- index.js | 6 +- public/js/app.js | 169 +++++++++++++++++++++++++++++++++-------------- routes/index.js | 33 ++++++++- 3 files changed, 154 insertions(+), 54 deletions(-) diff --git a/index.js b/index.js index a63b304..99e08c9 100644 --- a/index.js +++ b/index.js @@ -38,6 +38,7 @@ app.use(express.static('public')); const bodyParser = require('body-parser'); app.use(bodyParser.json()); app.use(bodyParser.raw()); +app.use(bodyParser.urlencoded({ extended: true })); app.use(bodyParser.text({ type : "text/*" })); app.disable('x-powered-by'); @@ -62,12 +63,13 @@ function requireAuthentication( req, res, next ){ app.all('*', requireAuthentication); const routes = require( "./routes"); +app.get('/get/:id', routes.get); app.get('/log/:id', routes.log); app.get('/health', routes.health); app.get('/search', routes.search); -app.post('/*', routes.add); app.get('/*', routes.main); -app.patch('/*', routes.main); +app.post('/*', routes.add); +app.patch('/patch/:id', routes.patch); app.put('/*', routes.main); app.delete('/delete/:id', routes.delete); diff --git a/public/js/app.js b/public/js/app.js index 7838bd4..f1eec74 100644 --- a/public/js/app.js +++ b/public/js/app.js @@ -1,7 +1,100 @@ /* global initData, authorizationToken */ $(function(){ - + + const actionToggle = function(e){ + var el=e.target; + $(el).parent().siblings('.actions').show(); + $(el).hide(); + }; + + const deleteButton = function(e){ + const el = $(e.target); + const url = el.attr('href'); + $.ajax(url,{ + method: "DELETE", + beforeSend: function(request) { + request.setRequestHeader("authorizationToken", authorizationToken); + } + }) + .done(function(data) { + $(el).parents('.log').remove(); + }) + .fail(function() { + alert( "error" ); + }); + return false; + }; + + const editButton = function(e){ + const el = $(e.target); + const id = el.attr("rel"); + const pre = el.parents(".log").find("pre"); + $.ajax(`/get/${id}`,{ + beforeSend: function(request) { + request.setRequestHeader("authorizationToken", authorizationToken); + } + }) + .done(function(data) { + pre + .text(data._source.content) + .attr('rel',id) + .css("background","#ccc") + .attr("contenteditable",true) + .focus(); + $('body pre[contenteditable]').on('focusout', contentEdited ); + + }) + .fail(function(data,err) { + console.log(data,err); + alert( "error" ); + }); + + return false; + }; + + const contentEdited = function(e) { + const el = $(e.target); + const id = el.attr('rel'); + const content = el.text(); + $.ajax(`/patch/${id}`,{ + method: "PATCH", + data: {content:content}, + beforeSend: function(request) { + request.setRequestHeader("authorizationToken", authorizationToken); + } + }) + .done(function(data) { + el + .css("background","") + .html( formatContent(content) ); + }) + .fail(function(data,err) { + console.log(data,err); + alert( "error" ); + }); + }; + + const search = function(e){ + const el = $(e.target); + const val = el.val(); + if( val.length < 3 ){ return; } + $.ajax("/search",{ + beforeSend: function(request) { + request.setRequestHeader("authorizationToken", authorizationToken); + }, + data: { + q:val + } + }) + .done(function(data) { + updatePage(data); + }) + .fail(function() { + alert( "error" ); + }); + }; + // List of HTML entities for escaping. var htmlEscapes = { '&': '&', @@ -16,31 +109,37 @@ $(function(){ var htmlEscaper = /[&<>"'\/]/g; // Escape a string for HTML interpolation. - escape = function(string) { + const escape = function(string) { return ('' + string).replace(htmlEscaper, function(match) { return htmlEscapes[match]; }); }; - var urlRegex = /(\S+): (https?://[^\s]+)/g; - url = function(string){ + const urlRegex = /(\S+): (https?://[^\s]+)/g; + const url = function(string){ return ''+string.replace(urlRegex, '$1'); }; var titleRegex = /^(.*\n)/; - title = function(string){ + const title = function(string){ return ''+string.replace(titleRegex, '$1'); }; var cmdRegex = /```([^`]*?)```/g; - cmd = function(string) { + const cmd = function(string) { return ''+string.replace(cmdRegex, '$1'); }; - date = function(string){ + const date = function(string){ var D = new Date(string); return D.toLocaleDateString()+" "+D.toLocaleTimeString(); }; - mailRegexp = /(.*) <(.+@.+)>/; - mail = function( string ){ + const mailRegexp = /(.*) <(.+@.+)>/; + const mail = function( string ){ return ''+string.replace(mailRegexp, `$1`); }; + + const formatContent = function(string){ + return cmd(title(url(escape(string)))); + }; + + function updatePage(data){ var content = ""; @@ -68,61 +167,29 @@ $(function(){ Actions

- Remove - Edit + Remove + Edit
-
-
 ${cmd(title(url(escape(item.content))))}
+
+
 ${formatContent(item.content)}
`; }); $("#content").html(content); + + // attache events + $(".actions-toggle").on("click",actionToggle ); + $('.delete').on('click', deleteButton); + $('.edit').on('click', editButton ); } - $("input").on("keyup",function(e){ - const el = $(e.target); - const val = el.val(); - if( val.length < 3 ){ return; } - $.ajax("/search",{ - beforeSend: function(request) { - request.setRequestHeader("authorizationToken", authorizationToken); - }, - data: { - q:val, - } - }) - .done(function(data) { - updatePage(data); - }) - .fail(function() { - alert( "error" ); - }); - }); + $("input").on("keyup",search ); updatePage( initData ); - $(".actions-toggle").on("click",(e) => { var el=e.target; $(el).parent().siblings('.actions').show(); $(el).hide(); } ) - - $('.delete').on('click', (e) => { - const el = $(e.target); - const url = el.attr('href'); - $.ajax(url,{ - method: "DELETE", - beforeSend: function(request) { - request.setRequestHeader("authorizationToken", authorizationToken); - } - }) - .done(function(data) { - $(el).parents('.log').remove(); - }) - .fail(function() { - alert( "error" ); - }); - return false; - }); }); diff --git a/routes/index.js b/routes/index.js index 6ac1b64..f30b382 100644 --- a/routes/index.js +++ b/routes/index.js @@ -116,12 +116,43 @@ const routes = { res.end("error"); }); } , + get: (req, res) => { + + const id= req.params.id; + var log = client.get({ + index: 'changelog', + id: id + }).then( (results, err) => { + res.json(results); + }, (e) => { + res.status(400); + res.json({msg:"Failed to get record"}); + }); + }, + patch: (req,res) => { + const id= req.params.id; + const content= req.body.content; + var log = client.update({ + + index: 'changelog', + id: id, + body:{ + doc:{ + content:content + } + } + }).then( (results, err) => { + res.json(results); + }, (e) => { + res.status(400); + res.json({msg:"Failed to get record"}); + }); }, log: (req, res) => { const id= req.params.id; var log = client.get({ index: 'changelog', - id: id + id: id }).then( (results, err) => { res.render('index', { title: 'changelog',