0

The idea is, if a user is accessing our site from China, we've got to block certain assets to improve our site speed. (For example, Facebook resources. I need to block them from even trying to load, because they'll always come back as blocked)

The caveat is that I have to do it in JavaScript (update: see edit at bottom), because it must be done client-side due to our caching with Akamai.

Consider this HTML with some JSTL:

<div class="num1">
  //some stuff like text and images
    <div class="num2">
        //a nested div with other stuff
      <c:if test="${varIsAlwaysTrue eq false}">
        <div class="num3">
        </div>
      </c:if>
    </div>
</div>

How do I put something like an IF statement around that, which uses a JavaScript variable? (The variable is called XY.isChina)

All I can really think of is what would be the scriptlet approach: (instead of the <% tags and Java code, obviously)

<script>
if (XY.isChina === false) {
</script>

<div class="num1">
  //some stuff like text and images
    <div class="num2">
        //a nested div with other stuff
      <c:if test="${varIsAlwaysTrue eq false}">
        <div class="num3">
        </div>
      </c:if>
    </div>
</div>


<script>
}
</script>

I'm almost positive that won't work.

The object of the game here is that none of that stuff within the IF statement loads. Making holes on the page is acceptable, but if it's possible for responsive elements to treat it like it's not even there (for alignment purposes) then that's even better.

Any thoughts?

Thanks in advance.

EDIT: I should have said that I need to do it client-side instead of specifying JavaScript in particular. The variable is already set in JavaScript, but if there are other client-side methods to doing this, that's fine. I cannot, however, use libraries like jQuery.

12
  • Can you try the other way round: load them later via JS if its not China, else let it be? Commented Dec 12, 2015 at 19:05
  • actually js would be a bad idea if the user has js turned off Commented Dec 12, 2015 at 19:06
  • I agree that JS is a lesser idea, but our company had a discussion about this and we (rather defeatedly) decided to go with JS was we have so much other stuff going on, we can't rely on server-side processing for this. Commented Dec 12, 2015 at 19:07
  • Have you looked at maybe using the framework angular js. Make a template with all of your blocked resources and only load the template if they are not in China Commented Dec 12, 2015 at 19:08
  • 1
    developer.mozilla.org/en-US/docs/Web/API/Document it's part of the browser supported web api so it doesn't require external libraries and I don't know of anything that doesn't support it Commented Dec 12, 2015 at 19:18

2 Answers 2

2

Look at it the other way. Why don't you hide those sections if XY.isChina == true rather than not loading them if this condition is true since your JSP has already rendered the HTML before even Javascript is executed.

<script>
if (XY.isChina === false) {
   document.getElementById( "numxyz" ).style.display = 'none';
}
</script>
Sign up to request clarification or add additional context in comments.

8 Comments

I came across this as an option earlier in my research. Just wondering: do I have to name every single element, or if I hide the first div, do the nested ones go away too?
@Joodoo Yes, unless they have a common class, which could easily be in your control. Then you can hide/remove by class stackoverflow.com/questions/4777077/…
This would prevent them from showing but not from loading.
Well, to start with this is fine. I can just hide the Facebook stuff, and if they can't click on it, great. Some of our embedded stuff, like Google Maps, probably needs a different approach.
Wondering if adding that common class would screw up our CSS? If I just add "flibbityflobbityfloo" as an additional class, that's not mentioned anywhere in our CSS obviously. Would the CSS rules that have always worked continue to work? Would they still match? (I'm leaning towards "there's gonna be a problem with that"
|
1

I need to block them from even trying to load

sounds like trying to square the circle, since also

it must be done client-side due to our caching

So as a first (partial) conclusion it seems that you must accept the involved parts to be loaded.

Then the remaining problem is to avoid displaying what will be hidden just right (takes time, and bad for the user experience).

So the solution could be to originally hide these parts, then show them only if they must show. In your given example, looks like this:

HTML:

<div class="num1 block-for-china"> <!-- note the dedicated class here -->
  //some stuff like text and images
    <div class="num2">
        //a nested div with other stuff
      <c:if test="${varIsAlwaysTrue eq false}">
        <div class="num3">
        </div>
      </c:if>
    </div>
</div>

CSS:

.block-for-china {
  display: none;
}

JS:

document.onload(function() {
  if (!XY.isChina) { // <-- up to you how to test this condition...
    var blockForChina = document.getElementsByClassName('block-for-china');
    for (var index in blockForChina) {
       blockForChina[index].style.display = 'inherit';
    }
  }
});

4 Comments

I'm trying this in a JS Fiddle right now, but my initial impressions: THANK YOU SO MUCH. I'll let you know if this is the key to my problems!
Query: the CSS seems to just display none no matter what. Is the JS supposed to toggle that?
As English is not my mother language I'm not absolutely sure to understand "no matter what"! But a priori yes: the trick is 1) none is displayed just after loading; 2) the JS part toggles that if you recognized the XY.China condition is false (I proposed inherit in order to keep agnostic vs any involved component).
Sorry, instead of "no matter what" it could say "always." Thanks for the answer :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.