1. 程式人生 > >《應用拆分與平臺搭建最佳實踐》- 跨應用平臺資源

《應用拆分與平臺搭建最佳實踐》- 跨應用平臺資源

《應用拆分與平臺搭建最佳實踐》- 跨應用平臺靜態資源

什麼是跨應用平臺靜態資源

靜態資源可以橫跨多個應用正常使用

為什麼需要做成靜態資源

1.任何使用的此資源的平臺風格保證一致性。 2.不需要後段做太多渲染處理,降低接入平臺成本。

效果圖




怎麼做

可以看出,top頭部,和左側的導航,基本樣式保持一致。其中,top顏色不同,是提供給每個應用個喜歡定製需要的配置顏色的方式。導航沒有改顏色,當然也是可以改的。 我們如何做成這個效果呢? 兩套方案: 方案一  將靜態資源打包成war包,需要的應用依賴來使用,缺點很明顯,應用需要往頁面注入值,需要對接一系列介面,複雜。 方案二  引入一段js,所有的事情都是js去完成。業務方不關心其他細節。 兩種方案筆者都有做過,筆者這裡只講第二種方案,因為更加合理。 首先,我們引入一個空的js檔案
<#-- 公用靜態資源 -->
<script type="text/javascript" src="http://login.xiaotian.shi/js/plat/plat.js" id="plat-resources" env="${env}" nav="true" userinfo="true" ></script>

使用的應用始終只調用線上的js檔案,然後注入env,決定當前環境,找對應jsonp介面拿資料。(現在說複雜了點,慢慢來。) 我們引入了這段js,如下給出原始碼
// 此檔案最好修改成純js,在jquery之前體驗更好,筆者js功底不行,不敢獻醜
$(function (){

    // 獲取當前環境
var env = $("#plat-resources").attr("env"); // 是否需要導航 var needNav = $("#plat-resources").attr("nav"); // 是否顯示個人資訊 var needUserInfo = $("#plat-resources").attr("userinfo"); // 獲取靜態服務地址 var logginServerUrl = getSpileUrl(env); // 最前面插入標籤 // 載入公共資源頁面 // var publicDoc = "<style>" + "*{padding:0;margin:0;font-family:'微軟雅黑';}"
+ "body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,th,td,p,pre,form,input,textarea,fieldset,blockquote{padding: 0;margin: 0;}" + ".body-top {width: 100%;height: 100px;color: white;background: black;}" + ".body-top-left {height: 100%;width: 270px; float: left;}" + ".body-top-left-top {height: 70px;width: 270px;font-size: 50px;padding-left: 10px;line-height: 70px;}" + ".body-top-left-bottom {height: 30px;width: 270px;font-size: 15px;line-height: 30px;text-align: right;}" + ".body-top-mid {float: left;}" + ".body-top-right {float: right;margin-right: 40px; width: 400px;margin-top: 10px;}" + ".body-top-right-count {text-align: right;margin: 5px;font-size: 20px;}" + ".hidden {display: none}" + "div{cursor:default}" + "</style>" + "<div class='body-top'>" + "<div class='body-top-left'>" + "<div class='body-top-left-top'>xiaotian.shi</div>" + "<div class='body-top-left-bottom'>歡迎來到石嘯天的個人網站</div>" + "</div>" + "<div class='body-top-mid'></div>" + "<div class='body-top-right'>" + "<div class='body-top-right-count'></div>" + "<div class='body-top-right-user hidden'>登陸</div>" + "<div class='body-top-right-userinfo hidden'>" + "<div class='body-top-right-userinfo-username'></div>" + "<div class='body-top-right-userinfo-logout'>退出</div>" + "</div>" + "</div>" + "</div>" + "<style>" + ".body-nav {top: 100px;left: 0px;width: 200px;bottom:0; height:100%;position: absolute;color: white;background: #2e68aa;padding-top: 20px;}" + ".body-nav-item {height: 20px;font-size: 20px;padding-left: 40px;padding-top: 10px;padding-bottom: 10px;}" + ".body-nav-item:hover{background: #1e508a}" + ".current {background:#5387c3}" + "</style>" + "<div class='body-nav hidden'>" + "</div>" ; $("body").prepend(publicDoc); // 請求top頭右邊個人資訊,和左邊導航資訊,進行渲染 $.ajax({ type : "get", async:false, url : logginServerUrl + "/cloudInfo", dataType : "jsonp",//資料型別為jsonp jsonp: "callback",//服務端用於接收callback呼叫的function名的引數 success : function(data){ var indexAccessCount = data.data.indexAccessCount; $(".body-top-right-count").html("訪問量:" + indexAccessCount); if(data.code === 200 && "true" === needUserInfo) { $(".body-top-right-userinfo-username").html(data.data.username + " |"); $(".body-top-right-userinfo").removeClass("hidden"); $(".body-top-right-user").addClass("hidden"); $(".body-top-right-user").click(function() { location.href = loginHost; }); } if(data.code === 200 && "true" === needNav) { var navlist = data.data.nav; if(navlist.length > 0) { var navStr = ""; for(var i = 0 ; i < navlist.length ; i++) { var url =navlist[i].url; var nowUrl = window.location.href; var current = ""; if(nowUrl.indexOf(url) > -1) { current = "current"; } navStr = navStr + "<div class='body-nav-item "+ current +"' url='" + url + "'>" + navlist[i].name + "</div>"; } $(".body-nav").html(navStr); $(".body-nav").removeClass("hidden"); $(".body-nav-item").click(function(){ var url = $(this).attr("url"); location=url; }) } } mRealy(data); }, error:function(){ alert('fail'); } }); $(".body-top-right-userinfo-logout").click(function() { $.ajax({ type : "get", async:false, url : logginServerUrl + "/logout", dataType : "jsonp",//資料型別為jsonp jsonp: "callback",//服務端用於接收callback呼叫的function名的引數 success : function(data){ location.href = "/"; }, error:function(){ alert('fail'); } }); }); // 繫結高度 $(".body-nav").height(document.documentElement.clientHeight); }); // 預設http // 如何組裝,需要根據自己應用的域名來決定 function getSpileUrl(env) { var p = "http"; var s = ":8081"; if(typeof(env) == "undefined" || env === "product") { env=""; // 暫時沒有https環境 // p = "https"; s = ""; } return p + "://login.xiaotian" + env + ".shi" + s; }

js檔案有點長,但是不復雜 1.獲取了標籤的一些配置 2.寫了一些html樣式 3.根據環境引數,組裝了介面資料請求地址 4.讀取了jsonp 個人會話的資料 其中html筆者有嘗試寫在另一個靜態檔案中,然後跨域調取。但是面臨幾個問題: 1.延遲高 2.跨域方式不友好 這些內容不長,所以寫成字串的形式,一次渲染進去,高效快捷。 其中,綠色的login系統右上角的樣式,有特殊定製,可以通過複寫的方式,將樣式修改掉。 例如top頭部的顏色修改
.body-top {
    width: 100%;
height: 100px;
/*border-bottom: 4px white solid;*/
color: white;
background: black;
}

或者使用plat.js渲染完成後的回掉函式進行設定。
function mRealy(publicData) {

};

其中publicData是非同步請求的個人資訊資料,結構可以自行設定。 這樣基本完成了資源靜態化的工作,但是這裡有一些小細節。 比如如何提速,plat最好使用cdn加速節點,並且,jquery也需要cdn加速。版本需要手動控制,不可以經常更新。 例如plat.js?v1.0.0 這樣可以提升使用者體驗,不過最好的方式是使用純原生的js方式去實現,筆者js功底不好,為了趕稿子就不獻醜了。 這裡可以跨域訪問的前提是,您完成了應用跨域訪問的配置,詳情請看筆者單點登入相關的帖子,裡面有詳細描述,跨子域名會話共享的實現。 或者您可以下載系列原始碼,run demo來體驗 專案地址  https://github.com/shixiaotian/xiaotian.shi-plat.git
demo http://www.miledao.top/
賬戶密碼
admin admin
user1 user1
user2 user2
user3 user3