เพิ่มปุ่ม Search ให้กับ Static Website + แชร์วิธีการทำ

Published on
Web Development
2017/01/add-lunr-search-with-middleman
Discord

จริงๆแล้วบทความนี้แค่จะมาอัพเดทเพื่อบอกว่าตอนนี DevAhoy สามารถทำการค้นหาบทความได้แล้วนะครับ :)

เนื่องมาจากหลายๆคนสอบถามเข้ามาว่า ทำไมบล็อกไม่ทำปุ่ม search ละ? เวลาจะค้นหาอะไรก็ต้องเข้า google แล้วพิมพ์ "devahoy + keyword" ซึ่งมันไม่สะดวกเท่าไหร่

เมื่อพิจารณาดูแล้ว เนื่องจากว่าบล็อกนี้ เป็น Static Website ไม่มีฐานข้อมูล ฉะนั้น ทางเลือกที่เป็นไปได้ในการเพิ่มปุ่ม Search ก็มี 2 ทางเลือก คือ

  1. Middleman Search + lunr.js
  2. Google Custom Search
  3. Algolia Search

แต่ว่าเลือกใช้ข้อ 1 และตัด Google Custom Search ออกเนื่องจากว่ามันเหมือน google ทั่วไป ไปค้นหาใน google น่าจะดูดีกว่า ส่วนข้อ 3 Algolia Search ดูน่าสนใจดีแต่ว่าไม่มี plugin สำหรับ Middleman มีแต่ Jekyll ก็เลยเลือกใช้ middleman-search ดีกว่า

ซึ่งตอนนี้ก็มีปุ่มค้นหาแล้ว ต่อไปก็จะมาแชร์วิธีการทำ เผื่อว่าจะมีคนที่ใช้ static website แล้วอยากมีปุ่มค้นหาบ้าง

Installation

เปิด Gemfile และทำการเพิ่ม https://github.com/manastech/middleman-search ลงไป

gem 'middleman-search'

สั่ง install gem

bundle

จากนั้นแก้ไขไฟล์ config.rb โดยเพิ่มส่วนที่เราจะตั้งค่าตัว search

activate :search do |search|
  search.resources = ['posts/', 'index.html']
  search.index_path = 'search/index.json'
  search.fields = {
    title: { boost: 100, store: true, required: true },
    content: { boost: 60 },
    url: { boost: 80, index: false, store: true }
  }
end

อธิบายเพิ่มเพิม

  • resources คือ list ของ url ที่ต้องการจะให้มัน index
  • index_path คือ path สำหรับไฟล์ json ที่ตัว lunr มัน generate มาให้
  • fields คือ ค่าไหนบ้างที่ต้องให้เอาไปค้นหา

Implement Code

เพิ่มปุ้นค้นหาที่หน้าเว็บลงไป

<div class="search-input">
  <input type="text" id="search-box" placeholder="Search..." />
  <button id="btn-search">
    <i class="fa fa-search" aria-hidden="true"></i>
  </button>
</div>

ทีนี้เมื่อเราทำการค้นหา ก็จะไปทำการค้นหาข้อมูลจากไฟล์ json ที่ lunr มันทำ index ไว้ให้

//= require lunr.min

var lunrIndex = null;
var lunrData = null;
var results = '';

$('#btn-search').on('click', function () {
  var query = $('#search-box').val();

  $.ajax({
    url: '/search/index.json',
    cache: true,
    method: 'GET',
    success: function (data) {
      lunrData = data;
      lunrIndex = lunr.Index.load(lunrData.index);

      results = lunrIndex.search(query);

      results.map(function (result) {
        var post = lunrData.docs[result.ref];
        var title = post.title;
        var url = post.url;

        $('#search-list ul').append('<li><a href="' + url + '">' + title + '</a></li>');
      });
    }
  });
});

ตัวอย่างโค๊ดด้านบน ก็เป็นตัวอย่างง่ายๆ เมื่อเรากดคลิกปุ่ม Search ก็ใช้ jquery ajax ทำการยิง GET ไปที่ไฟล์ /search/index.json (ที่เดียวกับที่ตั้งค่าไว้ใน config.rb ) เพื่อทำการโหลด json มา จากนั้นตัว lunr จะ search query กับ index เพื่อหาค่าผลลัพธ์ที่ได้

พอได้ผลลัพธ์แล้ว ก็จะนำค่า result.ref ไปแมพกับ lunr.docs ซึ่งเป็น object ที่เก็บชื่อ title, url ของบทความเรานั่นเอง

สุดท้ายก็ได้หน้าตา search ง่ายๆ บนเว็บแล้ว

Search

สรุป

ถึงแม้ว่าจะมีปุ่มค้นหาแล้วก็ตาม แต่ว่ายังมีข้อจำกัดหลายๆด้าน ไม่ว่าจะเป็น เรื่องความเร็วในการค้นหา อาจจะสู้ Google Custom Search ไม่ได้ และตอนนี้ก็สามารถค้นหาได้แต่ภาษาอังกฤษเท่านั้น เนื่องจากว่า lunr.js i18n นั้นยังไม่รองรับภาษาไทยนั่นเอง

ส่วนตัว Google Custom Search นั้น implement ง่ายมาก และค้นหาได้เร็วกว่า แต่รู้สึกว่าขี้เกียจมานั่งปรับแต่ง style ซึ่งหากว่า middleman search ณ ตอนนี้ไม่เวิร์คเท่าไหร่ ก็อาจจะลองใช้ Google Custom Search ดูก็ได้

Buy Me A Coffee
Authors
Discord