I must say that this approach is bad. We should evaluate on content
type. It is simple to add and i wonder why no one else did it already.
The content-type "text/x-json" is the closest acceptable description
according to the RFCs and should be used by prototype to determine if
evaluation is in order. Just like text/javascript, which is
implemented already.
The whole reason behind this is, that a header line is limited to a
specific size. So if youre JSON data is to huge, the server will
return nothing (or refuse delivery.. i dont know exactly what happens
in the background - browser or server). I expirienced this in a
PHP/Apache enviroment.
We should stick to content types instead of "inventing" new headers
which are limited in size anyways..
This is what i added to make it work:
evalJSONResponse: function() {
try {
return eval('(' + this.transport.responseText + ')');
} catch (e) {}
},
respondToReadyState ...
[...]
if (this.header('Content-type') == 'text/x-json')
json = this.evalJSONResponse();
Opinions?
--
Kjell
-- www.m3nt0r.de
Why "text/x-json" and not "application/json" which is the approved
JSON mime-type?
Peter
--
JavaScript for Rails: http://forkjavascript.org
None of theme are approved, but according to the RFC, the text-tree is
closest one when it comes down to properly describing the content. You
put everything into "application" that is too specific or "does not
fit into any of the other categories"
Kjell
--
Kjell
-- www.m3nt0r.de
".4. The Application Content-Type
The "application" Content-Type is to be used for data which do not fit
in any of the other categories, and particularly for data to be
processed by mail-based uses of application programs. This is
information which must be processed by an application before it is
viewable or usable to a user. "
http://www.faqs.org/rfcs/rfc1521.html
Thats why i chose "text/x-json" over "application/x-json". It is
readable text, after all
Kjell
--
Kjell
-- www.m3nt0r.de
[Re official JSON mime-types]
> None of theme are approved,
From Douglas Crockford himself
<URL: http://tech.groups.yahoo.com/group/json/message/337>
But i dont work for IANA, so be it..
(back to topic)
Since this is a official mime, there is more need to leave the
"X-JSON" path and move towards application/json.. content-type should
be enough to negotiate eval.
On 1/20/07, Peter Michaux <peterm...@gmail.com> wrote:
>
--
Kjell
-- www.m3nt0r.de
David
P.S.: http://www.ietf.org/rfc/rfc4627.txt?number=4627
Secondly, there is no point for X-JSON to be a status message carrier
or "just for simple stuff". Drop it entirely. It's is unnecessary.
Most people will have an own error format / object notation which they
transport in the responseText as a replacement for the expected
content and act on it. (eg include a "status" key)
This two-way devlivery is just complicating things.
And lastly, the thing i am pointing at is, that prototype does not
automaticly evaluates responseText if X-JSON header was found, forcing
me to evaluate by hand..
A server should always deliver, regardless if error or data. With that
in mind, i don't need a X-JSON header to tell me that everything is
alright and that i could now go ahead and eval responseText.
Thats why i suggest automatic evaluation of responseText if the
content-type is application/json. Simple.. just like text/xml, just
like text/javascript ..
Regards
--
Kjell
In future, start discussions about core changes in the Core group.
Thanks!
--
Mislav
Rails & Prototype both have a strong bent towards delivering fragments of HTML
rather than data in the response. In this case, If you're sending back
content, I don't see how to easily embed secondary data inside the main
response body, other than stuffing it into a hidden DIV, which loses several
hundred points for elegance. Sure, if you're delivering data anyway, X-JSON
isn't particularly useful.
On Monday 22 January 2007 12:42, Mislav wrote:
> Will be done:
> http://dev.rubyonrails.org/ticket/7295
Just saw this come in on the list - sounds like a good suggestion to me.
Just my $0.02
Dave
--
----------------------
Author
Ajax in Action http://manning.com/crane
Ajax in Practice http://manning.com/crane2
Prototype & Scriptaculous Quickly http://manning.com/crane3
>
> On Saturday 20 January 2007 15:22, Kjell Bublitz wrote:
>> Secondly, there is no point for X-JSON to be a status message carrier
>> or "just for simple stuff". Drop it entirely. It's is unnecessary.
>>
>> Most people will have an own error format / object notation which
>> they
>> transport in the responseText as a replacement for the expected
>> content and act on it. (eg include a "status" key)
>>
> My reading of the X-JSON header was that it's useful in cases where
> you want
> to pass some secondary data back with a response. The practice of
> 'piggy-backing' data in this way isn't to everybody's taste, but it
> can be a
> useful way of avoiding extra traffic.
>
> Rails & Prototype both have a strong bent towards delivering
> fragments of HTML
> rather than data in the response. In this case, If you're sending back
> content, I don't see how to easily embed secondary data inside the
> main
> response body, other than stuffing it into a hidden DIV, which
> loses several
> hundred points for elegance. Sure, if you're delivering data
> anyway, X-JSON
> isn't particularly useful.
Just want to support that opinion. We are using the X-JSON header
exactly for that.
Alex
This change, while I think is a good idea in general, will be somewhat difficult to make use of if the new JSON object replaces the old JSON object.
This is a different thing from an application error or status code e.g. 'the
object you are trying to update is a stale copy'. X-JSON can also be used for
status/update data such as 'you have three outstanding cases, here are their
names and ids', to automatically refresh a list in the background, every time
you request or update anything in your app (in which case the request body is
busy reporting something else).
Mislav - yes, X-JSON is a hack, and an acceptable one IMO, with a good
pedigree. As you point out, multipart MIME type responses are a hack on top
of HTTP - so are CGI parameters, and sessions, if you look at what HTTP was
originally designed to do.
I puzzled over the choice of "application" first but can think of a
couple reasons "application" could be more natural.
JSON is expressed in JavaScript. JavaScript is distributed as text not
is some unreadable compiled binary. If it could be distributed in a
small compiled form it surely would and so "application" would be more
clearly appropriate.
JSON is expressed in JavaScript. JavaScript is a programming language
that describes behavior aspect of a web page. Behavior is in the
application realm.
Is there something to disagree?
Only because there is a hack which allows transport of HTML (or
whatever) along with a pure dataformat, i don't see why that should be
a keeper. I personally create such fragments from JSON data, or modify
the application behaviour. There is no text/html involved in that
action and i belief that this is the whole purpose of JSON. If my
application uses pre-generated HTML aside from JSON -in a row-, i
should ask myself why i use JSON at all. Just for a 'yay or nay'?? I
don't think so..
But.. it's a matter of application design after all. Generally: mixing
mime is bad.
- Kjell
--
Kjell
-- www.m3nt0r.de
While I read through these comments, I decided for the first time in awhile to throw in my own two cents.
JSON stands for: JavaScript Object Notation. If we take the first word in that title: JavaScript, we get our answer. JSON is, through it's basis, JavaScript -- so set the MIME type as so; application.
Just because you can read text and understand what it means and what it does is not a valid method to describe the data as simple text. I can read binary code (albeit slowly), but that does not mean it is text.
--Will
But.. it's a matter of application design after all. Generally: mixing
mime is bad.
Or did I misunderstand--do you see this as a RoR change request, and
were suggesting it go there?
TAG
You are in the group for Prototype/Script.aculo.us and RoR.
So.. this is the right place for your requests.
--
Kjell
-- www.m3nt0r.de
Full group address: http://groups-beta.google.com/group/prototype-core
I missed the announcement as I've not heavily perused the new
prototype site. Most of my interaction with Prototype/S.a.us comes
from this list.
TAG
I personally like the object extension which was suggested earlier.
Maybe something like responseJSON ...
--
Kjell
-- www.m3nt0r.de
The core group is new, so this discussion was initially created here.
As being requested by Mislav, future discussions of such core specific
topics will be taken there.
If you have question regarding RoR/S.a.us go ahead and create a topic
or search online if your question has already been answered in this
group.
PS: Please don't push this topic anymore.
If you have further questions create a new topic.
On 1/23/07, Tom Gregory <to...@byu.net> wrote:
>
--
Kjell
-- www.m3nt0r.de
I don't quite see the reason for the second list. Is there any problem
using this list for discussing changes and future developement?
There is another thing that might speak towards application/json.
There is this fracking Norton Personal Firewall application that acts
as a web proxy and that injects its own javascript code into pages
fetched.
When I return JSON data in the return body, I set the content type to
application/json, as sending the data as text/html might seduce
Norton to mess it up. Although I can't test if it is really necessary
(I have no spare machine to infect with Norton). Did someone test a
similar setup?
Bye,
Martin
- Spinoffs is for assistance with Prototype and script.aculo.us both.
It's mostly a helpdesk.
- Prototype-Core is the list for discussion on the evolution of
Prototype, at all levels: global architecture, individual features, etc.
--
Christophe Porteneuve a.k.a. TDD
"[They] did not know it was impossible, so they did it." --Mark Twain
Email: t...@tddsworld.com
> - Spinoffs is for assistance with Prototype and script.aculo.us both.
> It's mostly a helpdesk.
>
> - Prototype-Core is the list for discussion on the evolution of
> Prototype, at all levels: global architecture, individual features, etc.
These are the topics, but I was wondering why it was felt necessary to
divide the group.
Changes are mostly because of users' needs and uses. When the needs
and uses manifest themselves on the first list, and the discussion
about how and what to change happens on the second list, then I fear
the code created might not address the problems in the best way
because of missing input from divers users. Kind of an artificial
barrier between the two groups.
Time will tell, I wish you best luck.
I just don't feel the necessity to divide the two topics. They
pollinate each other, the message count is not overwhelming and the
different topics are easily manageable in any decent reader.
These are the topics, but I was wondering why it was felt necessary to
divide the group.
One suggestion though: Shouldn't the json text be verified before
evaluted, as described in the application/json RFC
(http://www.ietf.org/rfc/rfc4627.txt):
var my_JSON_object = !(/[^,:{}\[\]0-9.\-+Eaeflnr-u \n\r\t]/.test(
text.replace(/"(\\.|[^"\\])*"/g, ''))) && eval('(' + text
+ ')');
Matti Ryhänen
Think about it, how about a Object.fromJSON(json) function for this?
Best,
Thomas
I'll post a patch tomorrow.
Best,
Tobie
and live tests:
http://sandbox.tobielangel.com/prototype/rev_6028/trunk/test/unit/string.html
http://sandbox.tobielangel.com/prototype/rev_6028/trunk/test/unit/ajax.html
I'm having issues in IE (don't know if its the actual code or the
testing that is causing the problem).
The JSON sanitazing regex is taken from http://www.json.org/json.js
with permission from Douglas Crockford.
Would like to get as much feedback as possible so we can make it really
bulletproof.
Thanks,
Tobie
Thanks,
Colin
Colin Mollenhour wrote:
> Is the sanitize step necessary? What would the performance hit be like
> on a large response, and is the added complexity worth the trouble
> considering all responses come from a controlled environment? You don't
> sanitize HTML or XML responses, I say just use eval inside a try/catch.
I agree. And in case the data can't be trusted then provide an optional
parameter signifying that it needs to be cleaned first.
--
Michael Peters
Developer
Plus Three, LP
If is data created by a user, you better sanitize it.
The performance hit isn't that bad really.
Tobie
On Jan 25, 11:02 am, Colin Mollenhour <eliteii...@mollenhour.com>
wrote:
Regarding your patch: Shouldn't the X-JSON processing also use evalJSON() ?
And WRT to options.sanitizeJSON, how about a AJAX.sanitizeJSON global
option for the default behaviour? Then a developer he want to sanitize
every response can set this to true once and he does not have to
specifiy this option on every call.
string.evalJSON() returns
Object if everything is OK
null if eval failed
undefined if sanitize was requested and failed
Shouldn't the last case also return null?
On the Ajax object, a seed for a discussion on how it should behave:
transport.responseJSON is always initialized with "undefined". Users
can compare with undefined to see if there was JSON data in the
response at all.
If content-type is application/json:
- a possible X-JSON header is disregarded.
- the responseText is eval'd via string.evalJSON()
transport.responseJSON is set to the returned value, thous it is
* an Object, if evalJSON() succeeds
* null, if evalJSON() fails because the eval() failed
* null, if sanitize was requested and the data did not pass
Question: should failing the sanitize process in evalJSON()
trigger onException? I believe yes.
If content-type is not application/json:
(only the X-JSON part)
- the X-JSON header is eval'd via string.evalJSON()
transport.responseJSON is set to the returned value, thous it is
* an Object, if evalJSON() succeeds
* null, if evalJSON() fails because the eval() failed
* null, if sanitize was requested and the data did not pass
Result:
transport.responseJSON always contains the JSON object returned (if
there was any), regardless how it was transported.
Question:
The callbacks get a parameter list of (transport, json). The json
parameter is not needed any more, if transport.responseJSON is used
consistently, but we cannot let it go for compatibility reasons.
If If content-type is not application/json, json gets its value from
the X-JSON header.
If If content-type is application/json, should it gets its value from
from the responseText?
I say yes. It should not matter what way (header / body) was used to
transfer the data.
> If is data created by a user, you better sanitize it.
Sure, but the server script creating the JSON response should create a
valid JSON representation of the user supplied data. If it cannot
assure this, then this is the component to fix first.
Bye,
Martin
> Regarding your patch: Shouldn't the X-JSON processing also use evalJSON() ?
Oops. It does, of cause.
I'm working on a better handling of exceptions. Will post a patch asap.
Regarding x-json, I think we should leave it as it is for consitency
and backwards compatibility. It should also still be available if the
mime-type is set to application/json.
I had thaught about a global AJAX.sanitizeJSON option. It certainly
something we could implement at some point, but there are some
potential issues with that (especially if you rely on some third party
libs also using Prototype). Your best option for such cases is to
create a var holding your hash of options and reference it each time.
Thanks for the extended comment.
Cheers,
Tobie
my 2 cents.
On 1/25/07, tobie <tobie....@gmail.com> wrote:
>
--
Kjell
-- www.m3nt0r.de
Cheers,
Colin
so self-evident ^^
my vote for responseJSON :)
--
Kjell
-- www.m3nt0r.de
> I had thaught about a global AJAX.sanitizeJSON option. It certainly
> something we could implement at some point, but there are some
> potential issues with that (especially if you rely on some third party
> libs also using Prototype).
That would be only a problem, if the third party module depends on
evalJSON() to not only return an object, but to also execute some
commands contained in the data, which makes the data not a JSON
structure in the first place and it is then an error to call evalJSON.
Bye,
Martin
Hi Martin,
You're right. However, the only consistent way to do this in my
opinion, is to have ALL defaults options available as a property of the
Ajax object (Something similar to what script.aculo.us implemented for
Effect), like so:
Ajax.DEFAULT_OPTIONS = {
asynchronous: true,
sanitizeJSON: false,
etc...
}
As this might have further implications, I believe it should dealt as a
separate issue.
But I agree with you, it would be a great feature.
Best,
Tobie
See http://dev.rubyonrails.org/changeset/5986 for an example of using
the built-in HTTP server (WEBrick) test environment for
testing stuff like this.
You can add:
@server.mount_proc("/JSON") do |req, res| ...
Then just spit back stuff, depending on params.
Best,
Thomas
--
Thomas Fuchs
wollzelle
questentier on AIM
madrobby on irc.freenode.net
http://www.fluxiom.com :: online digital asset management
http://script.aculo.us :: Web 2.0 JavaScript
http://mir.aculo.us :: Where no web developer has gone before
Thanks for your patience. I've encountered annoying issues which I
hadn't foreseen, mainly that IE6 doesn't allow modifying or adding
properties to the response object.
I've dealt with that by cloning the transport when needed... and I'd
like as much input as possible on this proposition as I'm a bit
worried about the possible side effects.
You can find the patch here: http://dev.rubyonrails.org/ticket/7295
To summarize, this patch adds:
- automatic evaluation of JSON if the mime-type is set to application/
json.
- evaluation of JSON if the evalJSON option is set to true (regardless
of the mime-type).
- the possibility to sanitize your JSON by setting the sanitizeJSON
option to true (to guard against user-entered data for example).
- the evaluated JSON comes nicely wrapped up as the responseJSON
property of the transport object.
- the x-json header is kept as is (except it also gets sanitized if
the sanitizeJSON option is used).
- there's an added String.prototype.evalJSON method
- automatic Opera testing has been added to rake (would need a bit of
polishing on windows and Linux - if anybody volunteers).
- all the tests you need (they will only run if launched from rake -
you have been warned!)
- full support in Safari, Firefox, Opera 9, IE6 & 7
Thanks for your input and best regards,
Tobie
Thanks,
Colin
This solution has the following advantages:
So a response like:
---------------
X-JSON: ({status: "go"})
Content-type: application/json
({data: ['one','two','ten']})
----------------
Could be used like so:
----------------
Ajax.Responders.register({
onSuccess: function(xhr,json){
if(json.status && json.status != 'go'){
alert('Error!'); }
}
});
new Ajax.Request(page,{
onSuccess: function(xhr,json){
$('count').update($A(json.data).map(function(item){ return
'<li>'+item.camelize()+'</li>'; }).join(''));
}
});
Thoughts? I personally prefer this over my original suggestion which
was to add a new property to the transport, mainly for simplicity.
Colin
http://dev.rubyonrails.org/ticket/7295
drops the ugly cloning in favor of a brand new Ajax.Response object.
Not ready for prime yet... as we still have to discuss how much we
want it to smoothen out browser discrepancies.
Comments welcomed.
NOTE: can only be tested through rake.
I've added Opera and WebKit to the lot.
This should probably not go into core like this as these browsers are
not officially supported.
+ var contentType = this.getHeader('Content-type');
if (state == 'Complete') {
try {
+ if(contentType &&
contentType.strip().startsWith('application/json'))
+ Object.extend(json || {},
transport.responseText.evalJSON(options.sanitizeJSON) || {});
this._complete = true;
Will these three lines not accomplish what this patch is all about,
making automatic JSON evaluation more usable? Keep it simple.
Thanks,
Colin