Monday, September 17th, 2007

Sprinkle In Your JavaScript

Category: JavaScript, Library

Jon Davis had a message for us:

I’ll make this brief.

  1. <script src="sprinkle.js"></script>
  2.  
  3. <div src="info.html"></div>

http://www.sprinklejs.com

This is the latest in the client-side includes explosion that started with the colour purple.

Take a peak at the sprinkle.js that makes it happen.

Posted by Dion Almaer at 12:11 am
29 Comments

++---
2.3 rating from 47 votes

29 Comments »

Comments feed TrackBack URI

You may use “class” or “id” attribute for div, because “src” is not a valid W3C attribute for DIV tag.

Comment by Vikas — September 17, 2007

Port 880? That’s odd.

Comment by Robert — September 17, 2007

No Working Link
No Working Site

how can i see its a working idea ?

Comment by tkdmatze — September 17, 2007

That code is scary. Here’s an example:


var attribs = el.attributes;
var i;
var j, d;
for (i=0; i<attribs.length; i++) {
if (attribs[i].name == "src") {
d = false;
for (j=0; j<attribs.length; j++) {
if (attribs[j].name == "csiLoadStatus" && (
attribs[j].value == "loading" ||
attribs[j].value == "loaded")) {
d = true;
break; // from nested loop
}
}
if (!d) {
csiLoad(el, attribs[i].value);
}
}
}

Isn't that about the same as this?

var src = el.getAttribute('src');
if( src ) {
var status = el.getAttribute('status');
if( status != 'loading' && status != 'loaded' )
csiLoad( el, src );
}

Comment by Michael Geary — September 17, 2007

It’s not too useful… Why sprinkle? There are many, many frameworks with more possibilities. And this is not XHTML valid page.

Comment by amon — September 17, 2007

“If you are unable to see content above, maybe you should turn Javascript on, or get a halfway decent web browser.”

Opera 9.x is as decent as they come. ;) Sprinkle didn’t support it, though.

Comment by HÃ¥vard Pedersen — September 17, 2007

In jQuery:

$(“textarea[src], div[src], span[src]”).each(function() {
$(this).load(this.src);
});

for all but inputs. If you want to support inputs too:

$(“textarea[src], input[src], span[src], div[src]”).each(function() {
var self = this;
$.get(this.src, function(data) {
if(self.tagName == “INPUT”) $(self).val(data);
else $(self).html(data);
});
});

Comment by Yehuda Katz — September 17, 2007

i hope this was posted as a joke

Comment by Jamie — September 17, 2007

Awesome, a piece of Javascript that’s invalid AND inaccessible at the same time. Good to see we’re making inroads with the whole “unobtrusive scripting” idea.

Not only that, but the code itself is pretty bad.

Comment by Brad Wright — September 17, 2007

Hey gents,
give him a break… the idea behind it is valid… I´ll have a closer look at the code.

Comment by Frank Thuerigen — September 17, 2007

Sry just saw Yehudas jQ solution… nothing to add.

Comment by Frank Thuerigen — September 17, 2007

I’ll actually rate this, based on Yehuda’s three line jQuery alternative alone.

Comment by Dan Atkinson — September 17, 2007

In Prototype:
//create element method ‘loadSrc’
Element.addMethods({
loadSrc: function(element, options){
element = $(element);
new Ajax.Updater(element, element.src||”, options);
return element;
}
});

//execute ‘loadSrc’ on queried elements
$$(‘textarea[src],div[src],span[src]’).invoke(‘loadSrc’, options);

Comment by jdalton — September 17, 2007

//add support for input elements
if(element.tagName == ‘INPUT’){
new Ajax.Request(element.src||”, {
method:’get’,
onSuccess:function(transport){
element.value = transport.responseText;
}
});
}

Comment by jdalton — September 17, 2007

Can we make this an ongoing Ajaxian game – take long, bloated, scary javascript code from other projects and see how few lines we can re-create it with using jQuery/ProtoType/etc?

note: 100% serious, I’ve found it rather amusing, interesting (and increasing my desire to sit down and learn one of these frameworks) when I see X project/source posted, followed by the 3-line jQuery alternative in the comments :)

Comment by kaniz — September 17, 2007

Great idea kaniz.

Tx jdalton!

Comment by Marty — September 17, 2007

Prototype 3 lines:
$$(’textarea[src],div[src],span[src]’).each(function(el){
new Ajax.Updater(el, el.src||”);
});

Comment by mike — September 17, 2007

The core issue I see with this is that without javascript, it’s broken. A link to the HTML content (ie., the no-JS case) which is otherwise removed and replaced with the content of that link via JS would be more useful.

Comment by Scott Schiller — September 17, 2007

Hands up, who else remembers ?

Comment by Chris Heilmann — September 17, 2007

In all fairness, the Sprinkle code does a lot more than the three-line jQuery or Prototype versions. But it seems to be doing more than it needs to – some of the options aren’t really necessary.

Here’s some more of the source code:


function csiGetInnerHtmlOfTag(str, tagName) {

if (str.toLowerCase().indexOf("<" + tagName) > -1 &&
str.toLowerCase().indexOf("</" + tagName + ">",
str.toLowerCase().indexOf("<" + tagName)) > -1) {

var startTagStart = str.toLowerCase().indexOf("<" + tagName);
var startTagEnd = str.indexOf(">", startTagStart);
var endTagStart = str.toLowerCase().indexOf("</" + tagName, startTagEnd);

var ret = str.substring(startTagEnd + 1, endTagStart - 1);
return ret;

} else return str;
}

That one function calls str.toLowerCase() five times. It calls str.toLowerCase().indexOf("<" + tagName) three times. It calls str.toLowerCase().indexOf("</" + tagName + ">", str.toLowerCase().indexOf("<" + tagName)) twice!

Clearly some refactoring would be in order here. Or you could do the whole thing with one regular expression:


function getInnerHtmlOfTag(str, tagName) {
var match = str.match(
new RegExp( '<' + tagName + '[^>]*>(.*)</' + tagName + '>', 'i' ) );
return match ? match[1] : str;
}

Comment by Michael Geary — September 17, 2007

I hate this comment system. No preview, no editing, a tiny narrow fixed width theme, and it screws up any source code I try to post!

Ajaxians, fix this thing. Kill it and get something that works. You should expect that people will want to post code in the comments, right?

Check my blog for an example of how you can have comments with good readable code formatting – in fact the same formatting as the posts themselves. Take this discussion for example:

http://mg.to/2006/01/25/json-for-jquery

If I can do it, you can do it. :-)

(Sorry, you wouldn’t be able to use my code “as is” because the site uses Drupal – but you’re welcome to use the code formatting part if you want to adapt it to WordPress – it’s based on the GeSHi code formatter with some tweaks of my own for the zebra striping and such.)

Comment by Michael Geary — September 17, 2007

Hey guys,

Thx for the feedback on my Sprinkle. I totally agree that the code should be cleaned up. I just my idea was a cool one, even if it isn’t the most beautiful implementation around. :) I’ll likely do a lot of refactoring.

Jon

Comment by Jon Davis — September 17, 2007

Thanks for not taking offense at our comments, Jon. You are a true gentleman. If I called your code “scary”, believe me, I used to write code that was much scarier!

I’m just kind of an inveterate code simplifier. Here’s one more for the road… :-)


if (antiCacheMethod == "querystring") {
var dt = new Date();
var dts = ""
+ dt.getFullYear()
+ dt.getMonth()
+ dt.getDate()
+ dt.getHours()
+ dt.getMinutes()
+ dt.getSeconds();
if (src.indexOf("?") == -1) src += "?nocachetimestamp=" + dts;
else src += "&nocachetimestamp=" + dts;
}

could be:


if (antiCacheMethod == "querystring") {
src +=
( src.match(/\?/) ? '&' : '?' ) +
'nocachetimestamp=' + (new Date).getTime();
}

Note that this also gives you a timestamp with “millisecond” resolution (actually around 15 milliseconds on many platforms), instead of the one second resolution in the original code.

I look forward to seeing your new streamlined revision… :-)

Comment by Michael Geary — September 17, 2007

“The core issue I see with this is that without javascript, it’s broken. A link to the HTML content (ie., the no-JS case) which is otherwise removed and replaced with the content of that link via JS would be more useful. ”

Scott, how is this broken? That should work just fine. It just doesn’t work on the actual sprinklejs.com web site itself since the site doubles as a browser test. You can obviously populate the contents of your tag with HTML while adding src=”..” to the tag itself, so that its contents have HTML defaults and Javascripted replacements. I just chose not to do that on the actual web site.

Comment by Jon Davis — September 18, 2007

Jon, that gets to the heart of some of the objections that a few commenters raised: The sprinklejs.com website doesn’t offer a good use case for the technology. In fact, the site is a better illustration of a case where you *shouldn’t* use this. Does the dynamic loading on this particular site give you anything that you couldn’t do with a straight-up HTML page? Especially considering that an HTML page would have several advantages:

* Indexable by search engines
* Works in any browser
* Works if JavaScript is disabled
* Faster loading
* Fewer hits on your server

I’m not saying there aren’t use cases where this approach has some benefit, just that the current sprinklejs.com page isn’t one of them. Put together a demo case where the dynamic loading actually offers some value, in fact enough extra value to overcome its inherent disadvantages, and then it will be easier to convince people of its merits.

Comment by Michael Geary — September 18, 2007

Michael, I agree that while there are some cases where this would be ideal (literally it was for a quick sidebar navigation / advertisement component that we added to one of our magazine web sites), and several more places where it wouldn’t be ideal. The site does demonstrate where it wouldn’t be ideal.

Comment by Jon Davis — September 18, 2007

.. *cough* and yes I should clean up sprinklejs.com to make it “more ideal”. The point is, that’s not the point. :)

Comment by Jon Davis — September 18, 2007

I wrote a similar script using JQuery a while back. The JQuery implementation is about three lines of code. I just blogged about the script and included implementations for Prototype and several other JavaScript frameworks. The link is:

http://www.forgeniuses.com/?p=3

Comment by Levi Senft — September 22, 2007

While this is an old thread, I still want to make it clear what my intentions were with sprinklejs.com. I am not trying to convince anyone to use this; rather, I had a need for this functionality, I didn’t want a big, bulk jQuery or Prototype support lib (3 lines of jQuery code, sure, with 48kb of support code!!), and so I sat down and produced it myself. I registered a domain name and put it out there to *share* it, not to sell myself or get rich and famous or compete with anyone.

So if you have the same need, great, enjoy! If you don’t, I don’t care!

Comment by Jon Davis — November 4, 2007

Leave a comment

You must be logged in to post a comment.