update on development: all (hopefully) messages from system are implemented - session expired shown. Still not handling "Revert" (button) and "resolve" (server) actions. Created repository at https://code.launchpad.net/~stekoje/web2py/ajaxeditor
On Mon, Feb 23, 2009 at 9:28 PM, Boris Manojlovic < boris.manojlo...@gmail.com> wrote: > Changed files: > web2py/applications/admin/controllers/default.py > web2py/applications/admin/static/ajax_editor.js > web2py/applications/admin/views/default/edit.html > web2py/applications/admin/views/layout.html > web2py/applications/admin/views/web2py_ajax.html > > this time patch is more intrusive than from last time, because i had to > change html layout to make "flash" field available. > Still missing part is relogin but this time this is just response to your > request :) > > I don't know why it does not work from konqueror as jquery should be > portable that much? > Anyway for now this is MozillaFirefox only untill I found out what is not > working in my JavaScript code :-\ > > > On Mon, Feb 23, 2009 at 7:52 PM, Boris Manojlovic < > boris.manojlo...@gmail.com> wrote: > >> will try to do it asap :) >> only missing will be "relogin" as i still didn't look into session issue. >> You would have to open new window(tab) and login there untill i find some >> nice solution for session timeout. >> >> >> On Mon, Feb 23, 2009 at 7:16 PM, mdipierro <mdipie...@cs.depaul.edu>wrote: >> >>> >>> ok but can you send me a patch that does 1,2,3? >>> >>> On Feb 23, 9:59 am, Boris Manojlovic <boris.manojlo...@gmail.com> >>> wrote: >>> > hello, >>> > 1) what exactly you need is very simple to achive as putting with JS >>> value >>> > into some <div> (or I'm missing your point, which i think is case here) >>> > 2) this is done already trough javascript (ajax_editor.js) as that was >>> > needed for successful "save" functionality (or resolve redirect is >>> received >>> > if it is not sent) >>> > 3) that is still to be done on client side - server side is same (and >>> > implemented) code as it was before for /edit/ control,JSON should >>> contain >>> > standard errors you receive by HTML as you can see in patch >>> > >>> > >>> > >>> > On Mon, Feb 23, 2009 at 4:41 AM, mdipierro <mdipie...@cs.depaul.edu> >>> wrote: >>> > >>> > > Boris. I really like this but we need >>> > >>> > > 1) make hash value visible and readonly >>> > > 2) return the same when it was saved as well >>> > > 3) some kind of notification (possibly in the form of flash) that >>> > > informs the user if the file was saved or not. >>> > >>> > > Massimo >>> > >>> > > On Feb 22, 12:43 pm, Boris Manojlovic <boris.manojlo...@gmail.com> >>> > > wrote: >>> > > > Please try this patch last one was non working... >>> > >>> > > > On Sun, Feb 22, 2009 at 7:16 PM, Boris Manojlovic < >>> > >>> > > > boris.manojlo...@gmail.com> wrote: >>> > > > > Hello to All, >>> > >>> > > > > i have started to work on something called "ajax" code editor. >>> > > > > What exactly does it mean? >>> > >>> > > > > 1. No need for reloads on editor page (just think about undo >>> redo in >>> > > > > editor window) >>> > > > > 2. No "terrible loss of code" if you are logged out >>> (application >>> > > > > timeout... with that "great" redirect to login page...) >>> > > > > 3. speed gain >>> > >>> > > > > Current implementation has "save" functionality only and it works >>> just >>> > > from >>> > > > > firefox (konqueror ignores my jquery code and same for opera...). >>> > > > > Most coding as it would be expected should (and is) done on >>> client side >>> > > and >>> > > > > will degrade depending if user use javascript at all - no script >>> no >>> > > ajax >>> > > > > anyway. >>> > > > > All messages in current stage are json passed to client. >>> > > > > Patch against latest SVN from google code >>> > >>> > > > > P.S. Comments welcome and needed (to continue on this idea or >>> not) >>> > > > > -- >>> > > > > "Only two things are infinite, the universe and human stupidity, >>> and >>> > > I'm >>> > > > > not sure about the former."-Albert Einstein >>> > >>> > > > -- >>> > > > "Only two things are infinite, the universe and human stupidity, >>> and I'm >>> > > not >>> > > > sure about the former."-Albert Einstein >>> > >>> > > > ajax_editor.patch >>> > > > 7KViewDownload >>> > >>> > -- >>> > "Only two things are infinite, the universe and human stupidity, and >>> I'm not >>> > sure about the former."-Albert Einstein >>> >>> >>> >> >> >> -- >> "Only two things are infinite, the universe and human stupidity, and I'm >> not sure about the former."-Albert Einstein >> > > > > -- > "Only two things are infinite, the universe and human stupidity, and I'm > not sure about the former."-Albert Einstein > -- "Only two things are infinite, the universe and human stupidity, and I'm not sure about the former."-Albert Einstein --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "web2py Web Framework" group. To post to this group, send email to web2py@googlegroups.com To unsubscribe from this group, send email to web2py+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/web2py?hl=en -~----------~----~----~----~------~----~------~--~---
=== modified file 'applications/admin/controllers/default.py' --- applications/admin/controllers/default.py 2009-02-17 05:27:43 +0000 +++ applications/admin/controllers/default.py 2009-02-25 23:36:50 +0000 @@ -42,6 +42,9 @@ socket.gethostbyname(http_host)) remote_addr = request.env.remote_addr +# Load json only if it is ajax edited... +if request.vars.has_key('from_ajax'): + import gluon.contrib.simplejson as json if request.env.http_x_forwarded_for or request.env.wsgi_url_scheme\ in ['https', 'HTTPS']: @@ -121,7 +124,10 @@ query_string = '' url = request.env.path_info + query_string - redirect(URL(r=request, f='index', vars=dict(send=url))) + if not request.vars.has_key('from_ajax'): + redirect(URL(r=request, f='index', vars=dict(send=url))) + else: + raise HTTP(200, json.dumps({'error': 'EXPIRED','text': 'Session has expired please relogin'})) def index(): @@ -425,7 +431,6 @@ def edit(): """ File edit handler """ - filename = '/'.join(request.args) # Try to discover the file type @@ -450,7 +455,10 @@ data1 = open(path, 'r').read() except IOError: session.flash = 'Invalid action' - redirect(URL(r=request, f='site')) + if request.vars.has_key('from_ajax'): + return json.dumps({'error': 'INVALID_ACTION','text':'Invalid action'}) + else: + redirect(URL(r=request, f='site')) file_hash = md5_hash(data) open(path, 'w').write(data) @@ -461,7 +469,10 @@ data = open(path, 'r').read() except IOError: session.flash = 'Invalid action' - redirect(URL(r=request, f='site')) + if request.vars.has_key('from_ajax'): + return json.dumps({'error': 'INVALID_ACTION','text':'Invalid action'}) + else: + redirect(URL(r=request, f='site')) file_hash = md5_hash(data) @@ -469,7 +480,11 @@ session.flash = T('file changed on disk') data = request.vars.data.replace('\r\n', '\n').strip() + '\n' open(path + '.1', 'w').write(data) - redirect(URL(r=request, f='resolve', args=request.args)) + if request.vars.has_key('from_ajax'): + #return json.dumps({'error': session.flash, 'resolve': 'true'}) + return json.dumps({'error': 'FILE_CHANGED', 'resolve': 'true','text': 'file changed on disk'}) + else: + redirect(URL(r=request, f='resolve', args=request.args)) elif request.vars.data: open(path + '.bak', 'w').write(data) data = request.vars.data.replace('\r\n', '\n').strip() + '\n' @@ -504,15 +519,18 @@ else: (controller, functions) = (None, None) - return dict(app=request.args[0], - filename=filename, - filetype=filetype, - data=data, - edit_controller=edit_controller, - file_hash=file_hash, - controller=controller, - functions=functions) - + if request.vars.has_key('from_ajax'): + return json.dumps({'file_hash': file_hash,'error' :'FILE_SAVED','text': 'File Successfully saved','time_saved': time.ctime()}) + #return response.json(file_hash) # maybe? + else: + return dict(app=request.args[0], + filename=filename, + filetype=filetype, + data=data, + edit_controller=edit_controller, + file_hash=file_hash, + controller=controller, + functions=functions) def resolve(): """ """ === added file 'applications/admin/static/ajax_editor.js' --- applications/admin/static/ajax_editor.js 1970-01-01 00:00:00 +0000 +++ applications/admin/static/ajax_editor.js 2009-02-25 23:43:15 +0000 @@ -0,0 +1,60 @@ +function prepareDataForSave(name,data) { + var obj = new Object(); + obj.Name = name; + obj.Data = data; + return obj; +} + +function prepareMultiPartPOST(data) { + var boundary = 'sPlItME' + Math.floor(Math.random()*10000); + var reqdata = '--' + boundary; + //console.log(data.length); + for (var i=0;i < data.length;i++) + { + reqdata += "\r\n" ; + reqdata += 'content-disposition: form-data; name="' + data[i].Name + '"'; + reqdata += "\r\n" ; + reqdata += data[i].Data; + reqdata += "\r\n" ; + reqdata += '--' + boundary; + } + return new Array(reqdata,boundary); +} + +function doClickSave() { + var dataForPost = prepareMultiPartPOST( + new Array( + prepareDataForSave('data', area.textarea.value), + prepareDataForSave('file_hash', $("input[name='file_hash']").val()), + prepareDataForSave('from_ajax','true') + ) + ) + //console.info(area.textarea.value); + $.ajax({ + type: "POST", + contentType: 'multipart/form-data;boundary="' + dataForPost[1] + '"', + url: self.location.href, + dataType: "json", + data: dataForPost[0], + success: function(json){ + //console.info( json.file_hash ); + if (json.error == 'FILE_SAVED') { + $("input[name='file_hash']").val(json.file_hash); + //console.info($("input[name='file_hash']").val()); + //$('.flash').text(json.text + ' at ' + json.time_saved + " hash=" + json.file_hash); + $('.flash').text(json.text + ' at ' + json.time_saved + ' (Server time)'); + $('.flash').removeClass('error'); // remove error class if we had it in previous call... + } else if (json.error == 'INVALID_ACTION') { + $('.flash').addClass('error'); + $('.flash').text(json.error); + } else if (json.error == 'FILE_CHANGED') { + $('.flash').addClass('error'); + $('.flash').text(json.text); + } else if (json.error == 'EXPIRED') { + $('.flash').addClass('error'); + $('.flash').text(json.text); + } + $('.flash').slideDown('slow'); + } + }); +} === modified file 'applications/admin/views/default/edit.html' --- applications/admin/views/default/edit.html 2009-02-12 05:27:08 +0000 +++ applications/admin/views/default/edit.html 2009-02-24 19:58:40 +0000 @@ -2,7 +2,12 @@ <script language="Javascript" type="text/javascript" src="{{=URL(r=request,c='static',f='edit_area/edit_area_full.js')}}"></script><script language="Javascript" type="text/javascript"> editAreaLoader.init({id: "body",start_highlight: true,allow_resize: "both",allow_toggle: true,language: "en",syntax: "{{=filetype}}",replace_tab_by_spaces: 4}); </script> +<script language="Javascript" type="text/javascript" src="/{{=request.application}}/static/ajax_editor.js"></script><script language="Javascript" type="text/javascript"> +$(document).ready(function(){ + $("form").bind("submit", function() { doClickSave();return false; }); +}); +</script> <h1>Editing file "{{=filename}}"</h1> {{if functions:}} === modified file 'applications/admin/views/layout.html' --- applications/admin/views/layout.html 2009-02-19 12:51:07 +0000 +++ applications/admin/views/layout.html 2009-02-24 19:58:41 +0000 @@ -31,9 +31,11 @@ <div id="main_inner" class="fixed"> <div id="primaryContent_columnless"> <div id="columnA_columnless"> + <div class="flash"> {{if response.flash:}} - <div class="flash">{{=response.flash}}</div> + {{=response.flash}} {{pass}} + </div> {{include}} </div> </div> === modified file 'applications/admin/views/web2py_ajax.html' --- applications/admin/views/web2py_ajax.html 2008-12-09 21:44:36 +0000 +++ applications/admin/views/web2py_ajax.html 2009-02-24 19:58:41 +0000 @@ -22,8 +22,11 @@ $(document).ready(function() { $('.hidden').hide(); $('.error').hide().slideDown('slow'); -$('.flash').hide().slideDown('slow') -$('.flash').click(function() { $(this).fadeOut('slow'); return false; }); +if ($('.flash').text() == '') + $('.flash').hide().slideDown('slow'); +else + $('.flash').hide(); +$('.flash').click(function() { $(this).slideUp('slow'); return false; }); //changed from default fadeout as it is too much intrusive :) $('input.string').attr('size',50); $('textarea.text').attr('cols',50).attr('rows',10); $('input.integer').keyup(function(){this.value=this.value.reverse().replace(/[^0-9\-]|\-(?=.)/g,'').reverse();});