Best way to execute js only on specific page

I was wondering what would be the best way to execute a java-script code only on specific pages.

Let's imagine we have a template-based web-site, rewrite rule for the content ist set, jquery available and it basically looks like this:

  <!DOCTYPE html>
  <html>
   <head>
    <script src="script.js"></script>
   </head>
   <body>
    ...
    include $content;
    ..
   </body>
</html>

content 'info' contains a button, we want something to happen on click, content 'alert' should give us a message when you hover a text field.

What is the best way to trigger these actions, without running into an error, because the object is not found?

Option one: using window.location.pathname

 $(document).ready(function() {
      if (window.location.pathname == '/info.php') {
          $("#button1").click(function(){
            //do something
          })
      }else if(window.location.pathname == '/alert.php'){
           $("#mytextfield").hover(){
             alert('message');
           }
    }

Option two: checking if elements exist

$(document).ready(function() {
  if ($("#button1").length > 0) {
      $("#button1").click(function(){
        //do something
      })
  }else if ($("#mytextfield").length > 0){
       $("#mytextfield").hover(){
         alert('message');
       }
}

Option three: include the script in the loaded template

//stands for itself

Is there a better solution? Or do I have to get along with one of these solutions?

Your experience, usage, or any links related to this topic are appreciated.

//EDIT:

I might have choosen a bad example, the actual code would be somethin like:

    mCanvas = $("#jsonCanvas");
    mMyPicture = new myPicture (mCanvas);

where the myPicture constructor get's the context of the canvas element, and throws an error, if mCanvas is undefined.


Solution 1:

Set a class attribute to your body tag.

<body class="PageType">

And then in your script..

$(function(){
  if($('body').is('.PageType')){
    //add dynamic script tag  using createElement()
    OR
    //call specific functions
  }
});

Solution 2:

I would use the switch statement and a variable. (I'm using jQuery!)

var windowLoc = $(location).attr('pathname'); //jquery format to get window.location.pathname

switch(windowLoc){      
  case "/info.php":
    //code here
    break;
  case "/alert.php":
    //code here
    break;
}

//use windowLoc as necessary elsewhere

This will allow you to change what "button" does based on the page that you're on. If I understood your question correctly; this is what I would do. Also, if I had were serving large amounts of javascript, I would simply add a new JS file completely.

var windowLoc = $(location).attr('pathname'); //jquery format to get window.location.pathname

switch(windowLoc){      
  case "/info.php":
    var infoJS = document.createElement('script');
    infoJS.type = 'text/javascript';
    infoJS.src = 'location/to/my/info_file.js';
    $('body').append(infoJs);
    break;
  case "/alert.php":
    var alertJS = document.createElement('script');
    alertJS.type = 'text/javascript';
    alertJS.src = 'location/to/my/alert_file.js';
    $('body').append(alertJs);
    break;
}

Hope this helps -

Cheers.

Solution 3:

A little different approach than checking the URL path : You can group page specific event handlers in a single function and then in each include, have a domready which will call these functions.

Eg: in script.js you have two functions (outside domready) viz. onPage1Load() and onPage2Load().

While in your page1.php you have a $(document).ready(onPage1Load) and so on for other pages. This will make sure that unintended event handlers are not registered.

Solution 4:

You can also use vanilla javascript to do the same

console.log(window.location.href);
const host = "http://127.0.0.1:5500/";
// JAVASCRIPT FOR INDEX PAGE 
if (window.location.href == host + 'index.html') {
    console.log("this is index page");
}

// JAVASCRIPT FOR ORDER PAGE 
if (window.location.href == host + 'order.html') {
    console.log("this is order page");
}