1. 程式人生 > >關於 頁面多語言支援的純前端(JQuery外掛)實現及 .json 檔案讀取報404的問題

關於 頁面多語言支援的純前端(JQuery外掛)實現及 .json 檔案讀取報404的問題

如著急尋求解決方案請跳過開頭,直接看正文。

*****************  廢話  *****************

    最近公司搞一個專案,被安排做頁面的多語言支援,對 Hystrix Dashboard 介面實現漢化,和中英切換,剛開始真沒把這個當事兒,主要是生氣,作為一個java程式設計師,就是再初級唄,讓我搞頁面翻譯?!做唄,那怎麼辦。最開始沒說要求,說實現就行。我把這個功能的原始碼從jar包裡扒出來,按照解壓出來的目錄結構放在專案路徑下(這樣會優先載入專案下的同名檔案,也就是我修改的,而不是jar裡的原始碼),開始修改,思路很簡單,做兩套靜態頁,頁面參考微信網頁版登陸頁的實現方式,將

?lang=zh_CN  和  ?lang=en_US

    作為引數傳遞到後臺,修改原始碼Controller的結果檢視跳轉,齊活!
    我說著簡單,其實這中間也挺曲折,最初是這樣修改的:

// Decompiled by Jad v1.5.8e2. Copyright 2001 Pavel Kouznetsov.
// Jad home page: http://kpdus.tripod.com/jad.html
// Decompiler options: packimports(3) fieldsfirst ansi space 
// Source File Name:   HystrixDashboardController.java
package org.springframework.cloud.netflix.hystrix.dashboard; import org.springframework.ui.Model; import org.springframework.web.context.request.WebRequest; public class HystrixDashboardController { public HystrixDashboardController() { //原始碼 /*public String home(Model model, WebRequest request) { model.addAttribute("basePath", extractPath(request)); return "hystrix/index"; }*/
//修改了home方法中結果檢視跳轉的邏輯 public String home(Model model, WebRequest request) { model.addAttribute("basePath", extractPath(request)); String language = request.getParameter("lang"); if ("zh_CN".equals(language)){ return "hystrix/indexCN"; }else{ return "hystrix/indexEN"; } } public String monitor(String path, Model model, WebRequest request) { model.addAttribute("basePath", extractPath(request)); model.addAttribute("contextPath", request.getContextPath()); return (new StringBuilder()).append("hystrix/").append(path).toString(); } private String extractPath(WebRequest request) { String path = (new StringBuilder()).append(request.getContextPath()).append(request.getAttribute("org.springframework.web.servlet.HandlerMapping.pathWithinHandlerMapping", 0)).toString(); return path; } }

    改完了報404。SpringBoot我沒有系統學過,只是入個門,我記得它會根據 return 的字串,去自動匹配靜態目錄下同名的頁面進行結果跳轉,但是現在404。然後我開始找配置檔案,因為跟原頁面 index.ftl 在同一目錄下,字尾名也一樣,所以字首和字尾不用再操心,但是這個控制跳轉的配置檔案我死活找不到,jar包裡真的沒有。到這就像進了一個死結。後來想著要不拿註解試試?因為之前自己玩SpringBoot是用全註解開發。就這樣:

// Decompiled by Jad v1.5.8e2. Copyright 2001 Pavel Kouznetsov.
// Jad home page: http://kpdus.tripod.com/jad.html
// Decompiler options: packimports(3) fieldsfirst ansi space 
// Source File Name:   HystrixDashboardController.java

package org.springframework.cloud.netflix.hystrix.dashboard;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.context.request.WebRequest;
/* here */
@Controller
public class HystrixDashboardController
{

    public HystrixDashboardController()
    {
    }
    /* and here */
    @RequestMapping("/hystrix")
    public String home(Model model, WebRequest request)
    {
        model.addAttribute("basePath", extractPath(request));
        String language = request.getParameter("lang");
        if ("en_US".equals(language)){
            return "hystrix/indexEN";
        }else{
            return "hystrix/indexCN";
        }
    }

    public String monitor(String path, Model model, WebRequest request)
    {
        model.addAttribute("basePath", extractPath(request));
        model.addAttribute("contextPath", request.getContextPath());
        return (new StringBuilder()).append("hystrix/").append(path).toString();
    }

    private String extractPath(WebRequest request)
    {
        String path = (new StringBuilder()).append(request.getContextPath()).append(request.getAttribute("org.springframework.web.servlet.HandlerMapping.pathWithinHandlerMapping", 0)).toString();
        return path;
    }
}

    It works!!!從這裡有兩點:註解優於配置生效了;二是我還是不確定jar包中的配置檔案在哪?希望看到此處的高人能指點一二,感激不盡!
提交方案,被否定,說這種侵入式修改不行,不容易維護或者根本不能維護,說優先利用前端技術實現!我就TM×××××了!早管幹啥呢?當初說實現就行,實現了又說不行!可能是我水平低,我是真不明白了,就是開源軟體再怎麼更新,我就加兩個註解,獲取一個引數,改一個結果檢視邏輯就不好維護了???還優先前端技術實現?培養一個拿著可憐工資的後臺程式設計師向全棧發展???還TM得會專業英語翻譯頁面!為此我還麻煩了一個英語專業同學,恰巧她的方向是計算機英語,不然光靠六級水平根本擋不住。真的,為了實現這個破專案的一個外圍都算不上,就是一個邊緣功能,真是盡心盡力了,國慶前一週同事都計劃回家了,我一直在搞這個,30號提前下班沒有走,十一當天還在解決 .json檔案讀不到的問題!我就想證明一件事,既然你們瞧不上我,我就把這些邊緣功能做的漂漂亮亮,不為什麼狗屁公司,就為了證明自己,然後後會無期!網上說90後這那那這的,任性的有,但是代表不了一個群體,對我而言,我覺著有一點很關鍵,認同感。扯遠了。於是,30號全天,開始尋求前端解決方案,下面是正文:

**************************** 正文 ****************************

    剛開始很苦惱,前端的東西確實生疏。我問前端看有沒有什麼解決方案,前端說一種是將中英文內容寫在兩個div中,放在一個頁面上,通過語言選擇控制div的隱藏和顯示,我覺得太low了… 另外一種是通過外掛,我就問具體是啥,他說不上來,沒做過他也不知道,這就很尷尬,那已經是30號下午了,馬上過節放假,交情不深也不好讓人家做太多… 但是JQuery確實是水太深了,真保不準有沒有哪個外掛能實現,我當時也沒太當回事,那時候主要是想通過讀取語言檔案的方式,沒想到後來將兩者結合在一起了。
    怎麼辦,上網找資料唄,還真讓我找見了!
https://github.com/coderifous/jquery-localize/
    我把我的程式碼拿出來,簡單做個說明:

    js引入

<script src="/hystrix/js/jquery.localize.js" type="text/javascript" charset="utf-8"></script>

    這裡要注意路徑和檔案位置,SpringBoot預設的靜態資源訪問路徑,我在網上查了一下,有

classpath:/META-INF/resources/,classpath:/resources/,classpath:/static/,classpath:/public/

可是我這裡
資源目錄

classpath:/static/  和  classpath:/templates/

    都已經是配置好的。這裡要說一下,紅色的js(紅色是因為忽略在svn的修改,並不是錯誤,這裡只是用顏色來區分),在static根目錄下,訪問不到,只有放在js目錄下的 .js 檔案才能夠被訪問,這應該也是在哪配置了,我沒有找到。

    回到

<script src="/hystrix/js/jquery.localize.js" type="text/javascript" charset="utf-8"></script>

    這個上面來,我的src是從 /hystrix 開始寫,而沒有從 /static 開始,就是上面說的預設配置的原因,注意一下。
另外jquery.min.js的引入我就不寫了。
    以上是 .js 引入。

    關於使用:
    首先必須給出我的語言資原始檔名稱,路徑和內容,下面講解要用:
語言檔案
    可以看到,這個檔名叫 language-cn.json ! 命名結構很重要,不然我不會費勁講名字! 整個名字由 - 分割 , language是前半部分 , cn 是後半部分!!!! 內容就是 json標準形式,沒說的,注意key值。

    1 . 關於data-localize,它是外掛定義的標籤,用來對應資原始檔的key。

<h1 data-localize="greeting" > Hello! </h1>

    2 . 這部分來選擇語言,將值傳遞給呼叫外掛的方法,這個值有講究

<div>
        <select id="language" onchange="changeLanguage(this.value);">
            <option value="cn">簡體中文</option>
            <option value="en" selected="selected">English</option>
        </select>
</div>

    3 . 呼叫外掛,最最核心的地方來了:$(“[data-localize]”).localize(),這是外掛呼叫語言資原始檔的固定寫法!

<script>
        function changeLanguage(lang){
            alert(lang);
            var params = { language: lang, pathPrefix: "hystrix/js" };
            $("[data-localize]").localize("language", params );
        }
</script>

    必須要講一下params 裡面的引數:
     先說pathPrefix:語言資原始檔的路徑,請回過頭去看之前的專案資原始檔路徑。
    然後是params 中的 language: lang ,其中lang變數是呼叫方法時傳遞過來的,也就是 language: “cn” ,它控制的是語言資原始檔名的後半部分;
     檔名的前半部分,由 localize(“language”,params ) 中的“language” 字串決定!
     希望不會對你造成歧義,我另舉一個例子,如果你的params 中的 language: “en”,而 localize(“A”,params ),那麼檔名就應該是A-en.json
這裡 .json 的字尾名是固定的,我大致看了外掛 js,是用了Ajax 獲取的 .json檔案,這也引出了標題中的問題。

    這問題真是難死我了………….就是死活讀不出來!!!!就是404!!!最開始懷疑是SpringBoot把這個靜態檔案攔截了,還是那個問題,找配置檔案找不到!後來索性就不管這個了!開始上網找資料,試各種偏門,真的是逼得沒招。
    茫茫網頁中,我找到了這麼一頁!!!!!
http://blog.csdn.net/chenjing9393/article/details/55102920

    首先排除路徑問題,會不會是什麼IIS配置的問題?我不知道,但是真沒辦法了,死馬當活馬醫,按照他說的搞,新的問題又出現了!妹兒的我的Web管理工具裡沒有 IIS服務 這個選項….. 我忽略了一個重要前提win7 旗艦版 ,我的是家庭版…….
然後開始升級系統,參考這篇文章:
http://jingyan.baidu.com/article/08b6a591ed82d314a809228d.html

    升級完成後新增MIME型別,沒報希望的試了一下。

    成了!!!!成了!!!!真的,你們不知道那一刻我是什麼心情!!!!!
希望此文能幫上你們。