]> gitweb @ CieloNegro.org - Rakka.git/commitdiff
improvements related to page search
authorpho <pho@cielonegro.org>
Tue, 5 Feb 2008 07:25:10 +0000 (16:25 +0900)
committerpho <pho@cielonegro.org>
Tue, 5 Feb 2008 07:25:10 +0000 (16:25 +0900)
darcs-hash:20080205072510-62b54-41b33e3b33ec668e02676c8bece17aab0aefc476.gz

Rakka.cabal
Rakka/Resource/Search.hs
Rakka/Storage/Impl.hs
Rakka/Storage/Types.hs
defaultPages/StyleSheet/Default.xml
js/Makefile
js/base.js
js/login.js
js/search.js
js/uri.js [new file with mode: 0644]

index 7425209f3b9bb800dd7f5ba2abceb30334878fa6..d9f9b0a81ce0dc6971d0a873e1bdd7fbe2979e20 100644 (file)
@@ -38,6 +38,7 @@ Extra-Source-Files:
     js/login.js
     js/screen.js
     js/search.js
+    js/uri.js
 
 Flag build-test-suite
     Description: Build the test suite.
index 8271640847fb3a8df9ee1f8b8cfbd3dba0faedba..a7e7628918732f050a5759aa99e339ef261b001a 100644 (file)
@@ -3,17 +3,28 @@ module Rakka.Resource.Search
     )
     where
 
+import qualified Codec.Binary.UTF8.String as UTF8
 import           Control.Arrow
 import           Control.Arrow.ArrowIO
+import           Control.Arrow.ArrowIf
 import           Control.Arrow.ArrowList
+import           Control.Arrow.ArrowTree
 import           Control.Monad.Trans
 import           Data.Maybe
 import           Network.HTTP.Lucu
+import           Network.URI hiding (query, fragment)
 import           Rakka.Environment
+import           Rakka.Page
 import           Rakka.Resource
 import           Rakka.Storage
+import           Rakka.SystemConfig
+import           Rakka.Utils
+import           Rakka.Wiki.Engine
+import           System.FilePath
 import           Text.HyperEstraier
+import           Text.XML.HXT.Arrow.Namespace
 import           Text.XML.HXT.Arrow.XmlArrow
+import           Text.XML.HXT.Arrow.XmlNodeSet
 import           Text.XML.HXT.DOM.TypeDefs
 
 
@@ -47,7 +58,7 @@ handleSearch :: Environment -> Resource ()
 handleSearch env
     = do params <- getQueryForm
 
-         let query = fromMaybe ""  $ lookup "q" params
+         let query = UTF8.decodeString $ fromMaybe ""  $ lookup "q" params
              from  = read $ fromMaybe "0"  $ lookup "from" params
              to    = read $ fromMaybe "20" $ lookup "to"   params
 
@@ -91,6 +102,7 @@ handleSearch env
       mkSnippetTree :: ArrowXml a => a SnippetFragment XmlTree
       mkSnippetTree = proc fragment
                     -> case fragment of
+                         Boundary          -> eelem "boundary"
                          NormalText      t -> txt t
                          HighlightedWord w -> eelem "hit" += txt w
                          -<< ()
@@ -99,4 +111,130 @@ handleSearch env
 searchResultToXHTML :: (ArrowXml a, ArrowChoice a, ArrowIO a) => Environment -> a XmlTree XmlTree
 searchResultToXHTML env
     = proc tree
-    -> this -< tree
+    -> do SiteName   siteName   <- getSysConfA (envSysConf env) -< ()
+          BaseURI    baseURI    <- getSysConfA (envSysConf env) -< ()
+          StyleSheet styleSheet <- getSysConfA (envSysConf env) -< ()
+          GlobalLock isGLocked  <- getSysConfA (envSysConf env) -< ()
+
+          let cssHref   = [uriToString id (mkObjectURI baseURI styleSheet) ""]
+              scriptSrc = [uriToString id (baseURI { uriPath = uriPath baseURI </> "js" }) ""]
+
+          pageTitle    <- listA (readSubPage env) -< (Nothing, Nothing, "PageTitle")
+          leftSideBar  <- listA (readSubPage env) -< (Nothing, Nothing, "SideBar/Left")
+          rightSideBar <- listA (readSubPage env) -< (Nothing, Nothing, "SideBar/Right")
+
+          ( eelem "/"
+            += ( eelem "html"
+                 += sattr "xmlns" "http://www.w3.org/1999/xhtml"
+                 += ( eelem "head"
+                      += ( eelem "title"
+                           += txt siteName
+                           += txt " - "
+                           += getXPathTreesInDoc "/searchResult/@query/text()"
+                         )
+                      += ( constL cssHref
+                           >>>
+                           eelem "link"
+                           += sattr "rel"  "stylesheet"
+                           += sattr "type" "text/css"
+                           += attr "href" (arr id >>> mkText)
+                         )
+                      += ( constL scriptSrc
+                           >>>
+                           eelem "script"
+                           += sattr "type" "text/javascript"
+                           += attr "src" (arr id >>> mkText)
+                         )
+                      += ( eelem "script"
+                           += sattr "type" "text/javascript"
+                           += txt ("Rakka.baseURI=\"" ++ uriToString id baseURI "" ++ "\";")
+                           += txt ("Rakka.isGlobalLocked=" ++ trueOrFalse isGLocked ++ ";")
+                           += txt  "Rakka.isSpecialPage=true;"
+                         )
+                    )
+                 += ( eelem "body"
+                      += ( eelem "div"
+                           += sattr "class" "header"
+                         )
+                      += ( eelem "div"
+                           += sattr "class" "center"
+                           += ( eelem "div"
+                                += sattr "class" "title"
+                                += constL pageTitle
+                              )
+                           += ( eelem "div"
+                                += sattr "class" "body"
+                                += ( eelem "h1"
+                                     += txt "Search Result"
+                                   )
+                                += ( eelem "div"
+                                     += sattr "class" "searchStat"
+                                     += txt "Search result for "
+                                     += ( eelem "span"
+                                          += sattr "class" "queryString"
+                                          += getXPathTreesInDoc "/searchResult/@query/text()"
+                                        )
+                                     += txt ": found "
+                                     += getXPathTreesInDoc "/searchResult/@total/text()"
+                                     += txt " pages."
+                                   )
+                                += ( getXPathTreesInDoc "/searchResult/page"
+                                     >>>
+                                     eelem "div"
+                                     += sattr "class" "searchResult"
+                                     += ( eelem "a"
+                                          += attr "href" ( getAttrValue "name"
+                                                           >>>
+                                                           arr (\ x -> uriToString id (mkPageURI baseURI x) "")
+                                                           >>>
+                                                           mkText
+                                                         )
+                                          += (getAttrValue "name" >>> mkText)
+                                        )
+                                     += ( eelem "p"
+                                          += ( getChildren
+                                               >>>
+                                               choiceA [ isText             :-> this
+                                                       , hasName "boundary" :-> txt " ... "
+                                                       , hasName "hit"      :-> ( eelem "span"
+                                                                                  += sattr "class" "highlighted"
+                                                                                  += getChildren
+                                                                                )
+                                                       ]
+                                             )
+                                        )
+                                   )
+                              )
+                         )
+                      += ( eelem "div"
+                           += sattr "class" "footer"
+                         )
+                      += ( eelem "div"
+                           += sattr "class" "left sideBar"
+                           += ( eelem "div"
+                                += sattr "class" "content"
+                                += constL leftSideBar
+                              )
+                         )
+                      += ( eelem "div"
+                           += sattr "class" "right sideBar"
+                           += ( eelem "div"
+                                += sattr "class" "content"
+                                += constL rightSideBar
+                              )
+                         )
+                    )
+                 >>>
+                 uniqueNamespacesFromDeclAndQNames
+               ) ) -<< tree
+
+
+readSubPage :: (ArrowXml a, ArrowChoice a, ArrowIO a) =>
+               Environment
+            -> a (Maybe PageName, Maybe XmlTree, PageName) XmlTree
+readSubPage env
+    = proc (mainPageName, mainPage, subPageName) ->
+      do subPage  <- getPageA (envStorage env) >>> arr fromJust >>> xmlizePage -< (subPageName, Nothing)
+         subXHTML <- makeSubXHTML (envStorage env) (envSysConf env) (envInterpTable env)
+                     -< (mainPageName, mainPage, subPage)
+         returnA -< subXHTML
index c763a304f51f187b6625bcebcb6478ae6dfd0032..200423ffc644f94c02860bab754323b7896f64f4 100644 (file)
@@ -17,6 +17,7 @@ import           Data.Maybe
 import           Data.Set (Set)
 import qualified Data.Set as S
 import           Network.HTTP.Lucu
+import           Network.HTTP.Lucu.Utils
 import           Network.URI
 import           Prelude hiding (words)
 import           Rakka.Attachment
@@ -198,7 +199,7 @@ searchIndex index cond
                snippet <- unsafeInterleaveIO $
                           do doc <- getDocument index docId [NoAttributes, NoKeywords]
                              sn  <- makeSnippet doc words 300 80 80
-                             return (map toFragment sn)
+                             return (trim (== Boundary) $ map toFragment sn)
                return SearchResult {
                             srPageName = decodePageName $ uriPath uri
                           , srPageRev  = rev
@@ -206,6 +207,7 @@ searchIndex index cond
                           }
 
       toFragment :: Either String (String, String) -> SnippetFragment
+      toFragment (Left "")      = Boundary
       toFragment (Left t)       = NormalText t
       toFragment (Right (w, _)) = HighlightedWord w
 
index 2944f287038ba81ee45389694bcfc8901ba73b56..c83e53e0cd3bf8663eba2883573eeda9f2775708 100644 (file)
@@ -36,6 +36,7 @@ data SearchResult
 
 
 data SnippetFragment
-    = NormalText      !String
+    = Boundary
+    | NormalText      !String
     | HighlightedWord !String
     deriving (Show, Eq)
\ No newline at end of file
index 7a5a6abd61d96de86b08e938392ce0f144faad4f..74a17db9c9d9e700c784aa0f8c4a7dd4ba6fad87 100644 (file)
@@ -200,6 +200,14 @@ table.pageEditor {
     margin: 0 2px;
 }
 
+.searchStat {
+    margin-bottom: 1.5em;
+}
+
+.searchResult {
+    margin-bottom: 1.5em;
+}
+
 /* color and text *************************************************************/
 * {
     font-family: sans-serif;
@@ -395,6 +403,24 @@ input[type="button"][disabled]:active {
     background-color: white;
 }
 
+.searchStat {
+    color: #888888;
+    font-size: 90%;
+}
+
+.searchResult a {
+    font-size: 120%;
+}
+.searchResult {
+    border-style: dotted;
+    border-width: 1px 0 0 0;
+    border-color: #aaaaaa;
+}
+
+.highlighted {
+    background-color: #ffefd5;
+}
+
 /* float **********************************************************************/
 h1, h2, h3, h4, h5, h6 {
     clear: both;
index 7063803ce53a914f8680f3a7150b585a899e6eb7..637f7d1c72ea45959237bbafc3d9518cd1f582ae 100644 (file)
@@ -12,6 +12,7 @@ SOURCES = \
        redirection.js \
        screen.js \
        search.js \
+       uri.js \
        $(NULL)
 
 COMPRESS = java -jar $(COMPRESSOR) --type js --charset UTF-8
index f2aa402fc91921426446e2c08ae6bf01711c11ce..a3dc7be69fc96c5c771b375f68e24c98dd118ef2 100644 (file)
@@ -4,3 +4,4 @@ var Rakka = {};
 Rakka.baseURI        = null;
 Rakka.isLocked       = false;
 Rakka.isGlobalLocked = false;
+Rakka.isSpecialPage  = false;
\ No newline at end of file
index 48a19b626fdd7e6e1caea341d6172a7b163887a6..291fa2987d8897f82dcea1051ac953359e0ccefb 100644 (file)
 
             $("input.newButton").attr({disabled: ""});
             
-            $("input.editButton").attr({disabled: ""});
+            $("input.editButton").attr({
+                disabled: (Rakka.isSpecialPage ? "disabled" : "")
+            });
         }
         else {
             /* ログインしてゐない */
             });
             
             $("input.editButton").attr({
-                disabled: (Rakka.isLocked || Rakka.isGlobalLocked ? "disabled" : "")
+                disabled: (Rakka.isLocked || Rakka.isGlobalLocked || Rakka.isSpecialPage ? "disabled" : "")
             });
         }
     };
index c1a90f84aa493a6c4691091bc3ca8ea293012616..3367804c97d0dd51facad3753446f8be13549b5d 100644 (file)
@@ -1,23 +1,34 @@
 (function () {
 
     $(document).ready(function () {
-        $("input.searchField")
-            .val("Search")
-            .removeClass("activeField")
-            .addClass("inactiveField")
-            .focus(function () {
-                if ($(this).attr("class").indexOf("inactiveField")) {
-                    $(this)
-                        .val("")
-                        .removeClass("inactiveField")
-                        .addClass("activeField");
-                }
-            })
-            .keypress(function (e) {
+        var $fld = $("input.searchField")
+
+        $fld.keypress(function (e) {
                 if (e.which == 10 || e.which == 13) {
                     window.location = Rakka.baseURI + "search.html?q=" + encodeURI($(this).val());
                 }
             });
+
+        /* 檢索 query が指定されてゐれば、それが最初から入力されてゐる
+         * 状態にする。
+         */
+        var form = Rakka.getQueryForm();
+        if (form["q"] == null) {
+            $fld.val("Search")
+                .removeClass("activeField")
+                .addClass("inactiveField")
+                .focus(function () {
+                    if ($(this).attr("class").indexOf("inactiveField")) {
+                        $(this)
+                            .val("")
+                            .removeClass("inactiveField")
+                            .addClass("activeField");
+                    }
+                });
+        }
+        else {
+            $fld.val(form["q"]);
+        }
     });
 
 })();
\ No newline at end of file
diff --git a/js/uri.js b/js/uri.js
new file mode 100644 (file)
index 0000000..abe7df4
--- /dev/null
+++ b/js/uri.js
@@ -0,0 +1,25 @@
+(function () {
+
+    Rakka.getQueryForm = function () {
+        var m = window.location.search.match(/^\?(.+)$/);
+        if (m) {
+            var ret = {};
+            
+            $.each(m[1].split(/[&;]/), function () {
+                var m = this.match(/^(.*?)=(.*)$/);
+                if (m) {
+                    var key = decodeURI(m[1]);
+                    var val = decodeURI(m[2]);
+                    
+                    ret[key] = val;
+                }
+            });
+
+            return ret;
+        }
+        else {
+            return {};
+        }
+    };
+    
+})();
\ No newline at end of file