jekyll_ranked_search 0.0.2 → 0.0.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/search.js +62 -13
  3. metadata +4 -4
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 4a717e9e1526e49b484e6b84067aa22daef311e21160e80a5c87a5a18fd6aeeb
4
- data.tar.gz: 5f6403859df289ecd20971ecb775d08bcc88487616df544ebacc1c2e74805fe6
3
+ metadata.gz: aa336a48a9eb94c3a0e7e395dee1a9c4a7938339cfa800e528db49b3c2876953
4
+ data.tar.gz: ced1e0e9cd3919a5a5fc28848c80523a81987698c11b0be0b4ea487f5f3ca3a7
5
5
  SHA512:
6
- metadata.gz: 7c268065e1ffe5dbd646feca161ed346dfc649c52d2b4f7269e1cab98e17a3a6180cb70c81a82a8c9b081b4b3a4aa7a6d5dd4d7d9b3ea10610a20210610e0f46
7
- data.tar.gz: 73822909d296b0d24a711cbffe27ceb906d6319bc419932ce5dc8be94774d1840339aba7eb58634c126c75a836bc4b4279275eab8ae431d47b17ffc9df0127d4
6
+ metadata.gz: f87c796fa346ac49d87bb939ee85ed37cfbe4083954a2963e2fb04e95963b87e0b95d2b5b03356364a1ce84f59d366fc74477e65fd532f1808ed272b810cda22
7
+ data.tar.gz: 811a1bebdcbef011282022bfe7083d2284d0c690132aad7a79431fd01fd0548144540f8499c61e04458e6f93ab1b29f4a61a3d05c220e5fede490ce7c05d5861
data/lib/search.js CHANGED
@@ -4,16 +4,44 @@ import 'https://cdn.jsdelivr.net/npm/@github/relative-time-element';
4
4
 
5
5
  class SearchBox extends LitElement {
6
6
  static properties = {
7
- _data: {state: true, type: Array},
7
+ _isLoading: {state: true, type: Boolean},
8
+ _data: {state: false, type: Array},
8
9
  _results : {state: true, type: Array},
9
10
  _open: {state: true, type: Boolean},
11
+ _placeholder: {state: true, type: String},
12
+
13
+ // Lazy loading
14
+ lazy: {type: Boolean, attribute: true},
15
+
16
+ // Maximum number of results to show
17
+ maxResults: {type: Number, attribute: "max-results"},
10
18
  };
11
19
 
20
+ /**
21
+ * Constructor. Sets up default values.
22
+ */
12
23
  constructor() {
13
24
  super();
25
+
26
+ // No data initially loaded
14
27
  this._data = [];
28
+
29
+ // Results are initially empty
15
30
  this._results = [];
31
+
32
+ // Start in closed state, show no results
16
33
  this._open = false;
34
+
35
+ // Default to not loading
36
+ this._isLoading = false;
37
+
38
+ // Disable lazy loading by default
39
+ this.lazy = false;
40
+
41
+ // Default to maximum of 8 results
42
+ this.maxResults = 8;
43
+
44
+ this._placeholder = "Search...";
17
45
  }
18
46
 
19
47
  static styles = css`
@@ -40,6 +68,7 @@ class SearchBox extends LitElement {
40
68
  margin-top: 4px;
41
69
  z-index: 10;
42
70
  background-color: #F6F6F6;
71
+ overflow: hidden;
43
72
  border-radius: 4px;
44
73
  box-shadow: 1px 1px 2px #888;
45
74
  }
@@ -77,16 +106,17 @@ class SearchBox extends LitElement {
77
106
 
78
107
  connectedCallback() {
79
108
  super.connectedCallback();
80
- this.loadData();
109
+
110
+ // Load data if lazy loading is disabled
111
+ if (!this.lazy) {
112
+ this.loadData();
113
+ }
81
114
 
82
115
  document.addEventListener('click', (event) => {
83
116
  if (!event.composedPath().includes(this) && this._open) {
84
117
  this.toggle();
85
118
  }
86
- });
87
-
88
- // Register arrow keys
89
-
119
+ });
90
120
  }
91
121
 
92
122
  toggle() {
@@ -104,12 +134,20 @@ class SearchBox extends LitElement {
104
134
  }
105
135
 
106
136
  async loadData() {
137
+ // Set state during loading
138
+ this._isLoading = true;
139
+ this.updatePlaceholder();
140
+
107
141
  const response = await fetch("/search.json");
108
142
  const jsonData = await response.json();
109
143
  jsonData.word2doc = new Map(Object.entries(jsonData.word2doc));
110
144
  jsonData.bow = new Map(Object.entries(jsonData.bow));
111
145
  jsonData.tfidf = new Map(Object.entries(jsonData.tfidf));
112
146
  this._data = jsonData;
147
+
148
+ // Cleanup state
149
+ this._isLoading = false;
150
+ this.updatePlaceholder();
113
151
  }
114
152
 
115
153
  disconnectedCallback() {
@@ -158,7 +196,6 @@ class SearchBox extends LitElement {
158
196
  for (const tokenId of tokenIds.slice(1)) {
159
197
  // Find document candidates
160
198
  const docCandidates = new Set(this._data.word2doc.get(tokenId.toString()));
161
- // console.log("intersection", docCandidates, docs);
162
199
  docs = new Set([...docs].filter((x) => docCandidates.has(x)));
163
200
  }
164
201
 
@@ -178,25 +215,37 @@ class SearchBox extends LitElement {
178
215
  const candidates = [...results.entries()].sort((a, b) => b[1] - a[1]).map((a) => a[0]);
179
216
 
180
217
  // Get top n results
181
- this._results = candidates.map((idx) => this._data.docs[idx]).slice(0, 8);
218
+ this._results = candidates.map((idx) => this._data.docs[idx]).slice(0, this.maxResults);
182
219
  this._open = true;
183
220
  }
184
221
 
185
- placeholder() {
222
+ updatePlaceholder() {
223
+ if (this._isLoading) {
224
+ this._placeholder = "Loading...";
225
+ return;
226
+ }
186
227
  if (this._data && this._data.docs && this._data.docs.length > 0) {
187
228
  let plural = "";
188
229
  if (this._data.docs.length !== 1) {
189
230
  plural = "s";
190
231
  }
191
- return "Search in " + this._data.docs.length + ` post${plural}...`;
192
- } else {
193
- return "Loading...";
232
+ this._placeholder = "Search in " + this._data.docs.length + ` post${plural}...`;
233
+ return;
234
+ }
235
+ }
236
+
237
+ /**
238
+ * Event triggered on search box focus.
239
+ */
240
+ focus(_) {
241
+ if (this.lazy && this._data.length === 0 && !this._isLoading) {
242
+ this.loadData();
194
243
  }
195
244
  }
196
245
 
197
246
  render() {
198
247
  return html`<div>
199
- <input id="q" type="text" placeholder="${this.placeholder()}" @keyup="${this.search}" @click=${this.openIfResults}>
248
+ <input id="q" type="text" placeholder="${this._placeholder}" @keyup="${this.search}" @click=${this.openIfResults} @focus=${this.focus}>
200
249
  ${this._open ? html`
201
250
  <div id="results">
202
251
  ${this._results.map((result) => html`
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: jekyll_ranked_search
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.2
4
+ version: 0.0.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Friedrich Ewald
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-06-24 00:00:00.000000000 Z
11
+ date: 2023-07-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: redcarpet
@@ -46,7 +46,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
46
46
  requirements:
47
47
  - - ">="
48
48
  - !ruby/object:Gem::Version
49
- version: '0'
49
+ version: 2.5.0
50
50
  required_rubygems_version: !ruby/object:Gem::Requirement
51
51
  requirements:
52
52
  - - ">="
@@ -56,5 +56,5 @@ requirements: []
56
56
  rubygems_version: 3.4.13
57
57
  signing_key:
58
58
  specification_version: 4
59
- summary: TF-IDF search for Jekyll posts
59
+ summary: TF-IDF offline search for Jekyll posts
60
60
  test_files: []