Ajaxによるコンテンツの切替え–対策方法

コンテンツ(contentX.htmlと仮定)に直接アクセス
された場合、様々な対策法があるとは思うが、私は
次のようにすることにした。

  1. 直接アクセスされたかどうかを検知する。
  2. 直接アクセスされた場合、sessionStorageにcontentX.htmlを出力
  3. index.html(Ajaxを設定したページ)へリダイレクト
  4. sessionStorageを参照して、contentX.htmlをロード

1. の検知方法は、title 要素の存在有無で
判定している。ちょっと怪しい処理だが、自分には
問題がないので、これで良しとする。

この検知処理は全コンテンツに追加する必要がある。
外部ファイルとするので
<script src=”/my/directory/xxx.js></script>
のような1行をHTMLの末尾に追加するだけだが、量が多いので
中々大変な作業量になってしまう。
と言うことで、以前書いた
「ディレクトリにある全ソースの末尾に1行追加」
につながる訳で、これで一件落着。目出度し目出度し。

各コンテンツに追加したスクリプトは以下の通り。

// 直接このコンテンツをアクセスしたかのチェック
var x = document.getElementsByTagName("title");
if(x.length == 0){  // 直接アクセスした?
  // 直接アクセスした場合の処理
  var url = document.URL;      // このドキュメントのURL
  var arry = url.split("/");  // スラッシュで分割
  // リダイレクトするURLの生成
  var html = "/"+arry[arry.length - 3]+"/"+arry[arry.length - 2]+"/"+"index.html";
  if(sessionStorage){
    sessionStorage.setItem("AccessURL",arry[arry.length - 1]);
  }else{
    alert("セッションストレージが使用できません");
  }
  // index.htmlへリダイレクト
  location.href=html;
}

index.htmlのスクリプト。

$(document).ready(function(){

    init();
    
    // 左サイドメニューをクリック
    $("#leftcolumn a").click(function(){
      srcSet(this);
    });
    // a タグの"href"を読んで、取得した内容を #main に設定する
    $("#leftcolumn a").pjax("#main");

});

function init(){
  if(sessionStorage){
    // sessionStorageが設定されていれば、それを入力
    var html = sessionStorage["AccessURL"];
    if(!html){
      // 設定されていなければdefault.htmlを入力
      html = "default.html";
    }
  }else{
    alert("セッションストレージが使用できません");
  }
  $("#main").load(html);
  // アンカータグのデフォルト動作を抑止
  $("#leftcolumn a").click(function(event){
    event.preventDefault();
  });
  // 本文中のリンクをクリック(tryitbtnを除く)
  $("#main").on('click','a:not(.tryitbtn)',function(event){
    event.preventDefault();  // リンクの動作を抑止
    srcSet(this);
    var vhref = $(this).attr("href");
      // tile に設定する値を、左サイドメニューから取得
      var title = $("#leftcolumn a[href='"+vhref+"']").text();
      if(title != ""){
        $("title").text(title);
      }
    //}
  });
}
function srcSet(obj){
  document.title = $(obj).text();      // title を設定
  $("a[style]").removeAttr("style");  // Bold 設定を一旦削除
  var geturl = $(obj).attr("href");    // クリックされたメニューの href 属性値
  // クリックされたメニューを Bold に
  $("#leftcolumn a[href='"+geturl+"']").css("font-weight","bold");
  // HTML 本文のロード
  $.pjax({
    "url": geturl,
    "container": "#main"
  });
  $("html").scrollTop(0);  // 画面を先頭に戻す

}

Ajaxによるコンテンツの切替え

この方式は、副作用が多々あるようである。

先ずは、Pjaxのところで書いたように
URLの変更がないため履歴が変更されず
ブラウザの「戻る」や「進む」ボタンが
使えない。
そのため、Pjaxを使用するなどの対策が
必要になるのであった。

ところが、このPjaxを使用したことによる
問題もあることが判明。

ブラウザの「更新」(再読み込み)
ボタンを押すと、コンテンツのみが
ロードされてしまうのだ。

一般的には、それ程使用するボタンでは
ないと思われるが、ページの開発過程
では頻繁に使用するボタンである。
このボタン押すたびに、フォームが崩れ
毎回、Ajaxを設定しているHTML
(index.html)から、読み直すのは結構
なストレスがかかる。

もう一つの問題は、Google検索である。
申請して、漸く使えるようになったの
だが、もしコンテンツ部分がクロール
され、それが結果に表示された場合
あられもない、スッピンのHTMLが表示
されてしまうのだ。

ページを公開するには、何らかの対策
が必要なのだが、長くなったので、こ
の対策は後日書く。

ディレクトリにある全ソースの末尾に1行追加

いろいろHTMLを見直していたら
多数のソースの末尾に1行追加
する必要が生じた。

Javascriptは、ファイルのロードは出来ても
出力ができ無ない。
そこで、こんなものを作ってみた。

● HTML

<!DOCTYPE html>
<html>
<head>
<title>ソースの末尾にコードを追加するツール</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta name="Description" content="ソースの末尾にコードを追加するツール" />
<script type="text/javascript" src="/files/jquery.js"></script>
<script type="text/javascript">
//******************************************************
//  ソースの末尾にコードを追加するツール
//******************************************************
$(document).ready(function(){
  $("button").click(function(){
    indir = $("#indir").val();
    otdir = $("#otdir").val();
    // テンプレートデータ入力
    $.ajax({
      type: "GET",
      url: "lineAdd.php",			// データ入力
      data: {
             "indir" : indir,
             "otdir" : otdir
            },
      dataType: "text",
      success: dataProc,
      error: function(req,msg,err){
      alert("input error " + msg);
    }
  });
});

  function dataProc(data){
    $("#output").html(data);
  }
})
</script>

</head>
<body>
<h1>ソースの末尾にコードを追加するツール</h1>
<div>
入力ソースのディレクトリ名: <br />
<input type="text" size="20" id="indir" name="indir" value="/w3c/sql/in/" />
</div>
<br/>
<div>
出力ソースのディレクトリ名: <br />
<input type="text" size="20" id="otdir" name="otdir" value="/w3c/sql/out/" />
</div>
<br/>
<button>処理実行</button><br /><br />
<div id="output"></div>
</body>
</html>

● php

<?php
	
	/***********************************************************************
	   指定ディレクトリ(/web/xxx/in/)配下のファイル名を配列で返します
	***********************************************************************/
	function getProg($dirname){
		// ディレクトリのオープン
		$dir = dir($dirname);
		//var_dump($dir);
		// g:/w3c 配下のディレクトリを入力
		$cnt = 0;
		while (($file = $dir->read()) !== false){
			if(is_file($dirname . $file)){					// ファイル以外は無視
			  if($file != ".." && $file != "."){		// 「.」、「..」は無視
			  	//echo $file . "<br/>";
					$info = pathinfo($file);						// path情報取得
					if($info['extension'] == "html"){		// 拡張子の判定取得
						$pArry[$cnt] = $file;							// ファイル名を設定
						$cnt++;
					}
			 	}
			}
		}
		//echo (count($pArry) . "<br/>");
		return $pArry;
	}

	/***********************************************************************
	   Main
	***********************************************************************/
	// 入力ソースのディレクトリ名(/web/dom/in/)
	if(isset($_GET['indir'])) {
		$indir = $_GET['indir'];
	} else {
		die ("引数に indir の指定がありません !");
	}
	//echo "dir名=" . $indir . "<br/>";	// <-- Debug
	
	// 出力ソースのディレクトリ名(/web/dom/out/)
	if(isset($_GET['otdir'])) {
		$otdir = $_GET['otdir'];
	} else {
		die ("引数に otdir の指定がありません !");
	}
	//echo "otdir名=" . $otdir . "<br/>";	// <-- Debug
	
	//**********************************************************************
	// w3schoolのソースを抽出
	$pArry = getProg($indir);
	$num = count($pArry);
	$wtbl = '<table id="res">';
	for($i = 0; $i < $num; $i++){
		$file = file_get_contents($indir.$pArry[$i]);
		$src  = mb_convert_encoding($file,"utf-8", "auto");
		// ソースの末尾に1行追加する
		$src .= '<script src="/w3c/common/procSeqCheck.js"></script>';
		// ファイル出力
	 	$otfile = $otdir . $pArry[$i];
	 	$flen  = file_put_contents($otfile,$src);
		$wtbl .= '<tr><td class="sou">' . $pArry[$i] . '</td><td class="byt">' . $flen . ' bytes</td></tr>';
	}
	echo $wtbl .= "</table>";
?>

これが、どうしても必要な訳は後日に。