Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save chriskyfung/b338a5f9bcfc5ef09968a602099607c2 to your computer and use it in GitHub Desktop.
Save chriskyfung/b338a5f9bcfc5ef09968a602099607c2 to your computer and use it in GitHub Desktop.
Custom Code Snippets for WordPress with WP Search with Algolia Plugin

Files

  1. custom-HTML-for-rendering-Algolia-search-results.html

  2. Exclude-specific-pages-from-Indexing-by-WP-Search-with-Algolia.php

  3. Rewrite-URLs-for-WP-Search-with-Algolia.php

<link rel="stylesheet" id="algolia-instantsearch-css" href="http://localhost/wp-content/plugins/wp-search-with-algolia/css/algolia-instantsearch.cssr=2.2.0" media="all">
<script src="http://localhost/wp-content/plugins/wp-search-with-algolia/js/instantsearch.js/dist/instantsearch.production.min.js?ver=2.2.0" id="algolia-instantsearch-js"></script>
<div id="ais-wrapper">
<main id="ais-main">
<div class="algolia-search-box-wrapper">
<div id="algolia-search-box"></div>
<svg class="search-icon" width="25" height="25" viewBox="0 0 40 40" xmlns="http://www.w3.org/2000/svg"><path d="M24.828 31.657a16.76 16.76 0 0 1-7.992 2.015C7.538 33.672 0 26.134 0 16.836 0 7.538 7.538 0 16.836 0c9.298 0 16.836 7.538 16.836 16.836 0 3.22-.905 6.23-2.475 8.79.288.18.56.395.81.645l5.985 5.986A4.54 4.54 0 0 1 38 38.673a4.535 4.535 0 0 1-6.417-.007l-5.986-5.986a4.545 4.545 0 0 1-.77-1.023zm-7.992-4.046c5.95 0 10.775-4.823 10.775-10.774 0-5.95-4.823-10.775-10.774-10.775-5.95 0-10.775 4.825-10.775 10.776 0 5.95 4.825 10.775 10.776 10.775z" fill-rule="evenodd"></path></svg>
<div id="algolia-stats"></div>
<div id="algolia-powered-by"></div>
</div>
<div id="algolia-hits"></div>
<div id="algolia-pagination"></div>
</main>
<aside id="ais-facets">
<div>
<h3 class="widgettitle">Post Types</h3>
<section class="ais-facets" id="facet-post-types"></section>
</div>
<div>
<h3 class="widgettitle">Languages</h3>
<section class="ais-facets" id="facet-languages"></section>
</div>
<div>
<h3 class="widgettitle">Categories</h3>
<section class="ais-facets" id="facet-categories"></section>
</div>
<div>
<h3 class="widgettitle">Tags</h3>
<section class="ais-facets" id="facet-tags"></section>
</div>
<div>
<h3 class="widgettitle">Authors</h3>
<section class="ais-facets" id="facet-users"></section>
</div>
</aside>
</div>
<script type="text/html" id="tmpl-instantsearch-hit">
<article itemtype="http://schema.org/Article">
<# if ( data.images.thumbnail ) { #>
<div class="ais-hits--thumbnail">
<a href="{{ data.permalink }}" title="{{ data.post_title }}" class="ais-hits--thumbnail-link">
<img src="{{ data.images.thumbnail.url }}" alt="{{ data.post_title }}" title="{{ data.post_title }}" itemprop="image" />
</a>
</div>
<# } #>
<div class="ais-hits--content">
<h2 itemprop="name headline"><a href="{{ data.permalink }}" title="{{ data.post_title }}" class="ais-hits--title-link" itemprop="url">{{{ data._highlightResult.post_title.value }}}</a></h2>
<div class="excerpt">
<p>
<# if ( data._snippetResult['content'] ) { #>
<span class="suggestion-post-content ais-hits--content-snippet">{{{ data._snippetResult['content'].value }}}</span>
<# } #>
</p>
</div>
</div>
<div class="ais-clearfix"></div>
</article>
</script>
<script type="text/javascript">
window.addEventListener('load', function() {
if ( document.getElementById("algolia-search-box") ) {
if ( algolia.indices.searchable_posts === undefined && document.getElementsByClassName("admin-bar").length > 0) {
alert('It looks like you haven\'t indexed the searchable posts index. Please head to the Indexing page of the Algolia Search plugin and index it.');
}
/* Instantiate instantsearch.js */
var search = instantsearch({
indexName: algolia.indices.searchable_posts.name,
searchClient: algoliasearch( algolia.application_id, algolia.search_api_key ),
routing: {
router: instantsearch.routers.history({ writeDelay: 1000 }),
stateMapping: {
stateToRoute( indexUiState ) {
return {
s: indexUiState[ algolia.indices.searchable_posts.name ].query,
page: indexUiState[ algolia.indices.searchable_posts.name ].page
}
},
routeToState( routeState ) {
const indexUiState = {};
indexUiState[ algolia.indices.searchable_posts.name ] = {
query: routeState.s,
page: routeState.page
};
return indexUiState;
}
}
}
});
search.addWidgets([
/* Search box widget */
instantsearch.widgets.searchBox({
container: '#algolia-search-box',
placeholder: 'Search for...',
showReset: false,
showSubmit: false,
showLoadingIndicator: false,
}),
/* Stats widget */
instantsearch.widgets.stats({
container: '#algolia-stats'
}),
/* Hits widget */
instantsearch.widgets.hits({
container: '#algolia-hits',
hitsPerPage: 10,
templates: {
empty: 'No results were found for "<strong>{{query}}</strong>".',
item: wp.template('instantsearch-hit')
},
transformData: {
item: function (hit) {
function replace_highlights_recursive (item) {
if (item instanceof Object && item.hasOwnProperty('value')) {
item.value = _.escape(item.value);
item.value = item.value.replace(/__ais-highlight__/g, '<em>').replace(/__\/ais-highlight__/g, '</em>');
} else {
for (var key in item) {
item[key] = replace_highlights_recursive(item[key]);
}
}
return item;
}
hit._highlightResult = replace_highlights_recursive(hit._highlightResult);
hit._snippetResult = replace_highlights_recursive(hit._snippetResult);
return hit;
}
}
}),
/* Pagination widget */
instantsearch.widgets.pagination({
container: '#algolia-pagination'
}),
/* Post types refinement widget */
instantsearch.widgets.menu({
container: '#facet-post-types',
attribute: 'post_type_label',
sortBy: ['isRefined:desc', 'count:desc', 'name:asc'],
limit: 10,
}),
/* Languages refinement widget */
instantsearch.widgets.menu({
container: '#facet-languages',
attribute: 'taxonomies.language',
sortBy: ['isRefined:desc', 'count:desc', 'name:asc'],
limit: 3,
}),
/* Categories refinement widget */
instantsearch.widgets.hierarchicalMenu({
container: '#facet-categories',
separator: ' > ',
sortBy: ['count'],
attributes: ['taxonomies_hierarchical.category.lvl0', 'taxonomies_hierarchical.category.lvl1', 'taxonomies_hierarchical.category.lvl2'],
}),
/* Tags refinement widget */
instantsearch.widgets.refinementList({
container: '#facet-tags',
attribute: 'taxonomies.post_tag',
operator: 'and',
limit: 15,
sortBy: ['isRefined:desc', 'count:desc', 'name:asc'],
}),
/* Users refinement widget */
instantsearch.widgets.menu({
container: '#facet-users',
attribute: 'post_author.display_name',
sortBy: ['isRefined:desc', 'count:desc', 'name:asc'],
limit: 10,
}),
/* Search powered-by widget */
instantsearch.widgets.poweredBy({
container: '#algolia-powered-by'
})
]);
/* Start */
search.start();
// This needs work
document.querySelector("#algolia-search-box input[type='search']").select()
}
});
</script>
<?php
// Alter both the posts index and the searchable_posts index for Algolia.
add_filter('algolia_should_index_post', 'custom_should_index_post', 10, 2);
add_filter('algolia_should_index_searchable_post', 'custom_should_index_post', 10, 2);
/**
* @param bool $should_index
* @param WP_Post $post
*
* @return bool
*/
function custom_should_index_post( $should_index, WP_Post $post ) {
// Replace these IDs with yours ;)
$posts_to_exclude = array( 12345, 23456, 34567 );
if ( false === $should_index ) {
// If the decision has already been taken to not index the post
// stick to that decision.
return $should_index;
}
if ( $post->post_type !== 'page' ) {
// We only want to alter the decision making for pages.
// We we are dealing with another post_type, return the $should_index as is.
return $should_index;
}
if (in_array($post->ID, $posts_to_exclude, TRUE)) {
// If the post is a page and belongs to an excluded posts,
// we return false to inform that we do not want to index the post.
return false;
}
return $should_index;
}
?>
<?php
/*
Rewrite URLs for WP Search with Algolia
*/
function deployment_url() {
return 'https://yoursite.com'; // Your production URL
}
/**
* Rewrite URLs in post_shared_attributes to deployment_url
*/
function replace_algolia_post_shared_attributes_url( $shared_attributes, $post ) {
$shared_attributes['permalink'] = str_replace(
site_url(),
deployment_url(),
$shared_attributes['permalink']
);
return $shared_attributes;
}
add_filter( 'algolia_post_shared_attributes', 'replace_algolia_post_shared_attributes_url', 10, 2 );
add_filter( 'algolia_searchable_post_shared_attributes', 'replace_algolia_post_shared_attributes_url', 10, 2 );
/**
* Rewrite URLs in term_record to deployment_url
*/
function replace_algolia_term_record_url( $record, $item ) {
$record['permalink'] = str_replace(
site_url(),
deployment_url(),
$record['permalink']
);
return $record;
}
add_filter( 'algolia_term_record', 'replace_algolia_term_record_url', 10, 2 );
/**
* Rewrite URLs in post_images to deployment_url
*/
function replace_algolia_post_images_url( array $images ) {
return array_map(
function($image) {
return array(
'url' => str_replace(
site_url(),
deployment_url(),
$image['url']
),
'width' => $image['width'],
'height' => $image['height'],
);
},
$images
);
}
add_filter( 'algolia_get_post_images', 'replace_algolia_post_images_url', 10, 1 );
?>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment