update theme
This commit is contained in:
@@ -0,0 +1,2 @@
|
||||
vendor/
|
||||
composer.lock
|
||||
@@ -0,0 +1 @@
|
||||
{"version":1,"defects":{"ofc\\tests\\UtilTest::weCanSlugifyAString":3},"times":{"ofc\\tests\\UtilTest::weCanSlugifyAString":0.002}}
|
||||
21
wp/wp-content/themes/medicalalert/vendor/open-function-computers-llc/better-wordpress/LICENSE
vendored
Normal file
21
wp/wp-content/themes/medicalalert/vendor/open-function-computers-llc/better-wordpress/LICENSE
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2021 Open Function Computers, LLC
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
11
wp/wp-content/themes/medicalalert/vendor/open-function-computers-llc/better-wordpress/README.md
vendored
Normal file
11
wp/wp-content/themes/medicalalert/vendor/open-function-computers-llc/better-wordpress/README.md
vendored
Normal file
@@ -0,0 +1,11 @@
|
||||
<p align="center">
|
||||
<img src="https://avatars.githubusercontent.com/u/48373648?s=400&u=710b810ea6c2896a1ed8f67dc13e58fab1a5846d" alt="ofc-logo" style="max-width: 150px" />
|
||||
</p>
|
||||
|
||||
# better-wordpress
|
||||
A composer package to make WordPress theme development cleaner
|
||||
|
||||
## More info to come soon...
|
||||
I'll write more documentation about this package soon, but for now it's something that you can include and make your theme dev easier.
|
||||
|
||||
For now, I'll just describe the system's behavior.
|
||||
@@ -0,0 +1,23 @@
|
||||
{
|
||||
"name": "open-function-computers-llc/better-wordpress",
|
||||
"description": "A suite of classes to make WordPress theme development cleaner",
|
||||
"require": {
|
||||
"php": ">=7.4",
|
||||
"jjgrainger/posttypes": "^2.1",
|
||||
"salesforce/handlebars-php": "^2.3"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "^9.5"
|
||||
},
|
||||
"license": "MIT",
|
||||
"keywords": ["wordpress", "handlebars", "theme"],
|
||||
"minimum-stability": "stable",
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"ofc\\": "src/"
|
||||
}
|
||||
},
|
||||
"scripts": {
|
||||
"post-create-project-cmd": "ofc\\BetterWordpress::setup"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,93 @@
|
||||
<?php
|
||||
|
||||
return [
|
||||
/**
|
||||
* excerpt-length
|
||||
* how many words should the wordpress excerpt be
|
||||
*/
|
||||
"excerpt-length" => 100,
|
||||
|
||||
/**
|
||||
* guest-class
|
||||
* if you want wordpress to automatically append a class to the body_class
|
||||
* list when users are not authenticated, put that class name here. it
|
||||
* defaults to "guest"
|
||||
*
|
||||
* to disable, set this to null
|
||||
*/
|
||||
"guest-class" => "null",
|
||||
|
||||
/**
|
||||
* menu-locations
|
||||
* register your individual menu locations here
|
||||
*/
|
||||
"menu-locations" => [
|
||||
"main-nav" => "Main Navigation",
|
||||
"footer-nav" => "Footer Navigation",
|
||||
],
|
||||
|
||||
/**
|
||||
* custom-post-types
|
||||
* here is where you can define your custom post types easily
|
||||
*
|
||||
* icons are powered by dashicons, choose one from here:
|
||||
* https://developer.wordpress.org/resource/dashicons
|
||||
*
|
||||
* additional options are enabled in the cpt options key
|
||||
* if you override "supports", be sure to include 'title' and 'editor' in
|
||||
* the list for standard wordpress functionality
|
||||
*/
|
||||
"custom-post-types" => [
|
||||
[
|
||||
"slug" => "thing",
|
||||
"icon" => "dashicons-tide",
|
||||
"options" => [
|
||||
"supports" => ['title', 'editor', 'thumbnail', 'comments']
|
||||
]
|
||||
],
|
||||
],
|
||||
|
||||
/**
|
||||
* handlebars
|
||||
*
|
||||
* We use handlebars templating extensivly in this theme and code pattern.
|
||||
* You can adjust the defaults for many attributes here.
|
||||
*
|
||||
* Set this to `false` to disable handlebars functionality completely
|
||||
*/
|
||||
"handlebars" => [
|
||||
/**
|
||||
* additional-helpers
|
||||
* if you need to register additional Handlebars Helpers, register them here
|
||||
*
|
||||
* the key is the name that you will use in your templates, and the value is
|
||||
* the callback function that is run on the template side
|
||||
*/
|
||||
"additional-helpers" => [],
|
||||
|
||||
/**
|
||||
* template-extension
|
||||
*
|
||||
* The default extention for your templates is .tpl
|
||||
* If you'd like to change that, set the vaule here, without the dot
|
||||
*/
|
||||
// "template-extension" => "tpl",
|
||||
],
|
||||
|
||||
/**
|
||||
* enable
|
||||
* enable individual wordpress features here
|
||||
*/
|
||||
"enable" => [
|
||||
"post-thumbnails",
|
||||
"menus",
|
||||
],
|
||||
|
||||
/**
|
||||
* disable
|
||||
* disable individual wordpress features here
|
||||
*/
|
||||
"disable" => [
|
||||
"editor",
|
||||
],
|
||||
];
|
||||
@@ -0,0 +1,18 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:noNamespaceSchemaLocation="./vendor/phpunit/phpunit/phpunit.xsd"
|
||||
bootstrap="vendor/autoload.php"
|
||||
colors="true"
|
||||
stopOnFailure="false"
|
||||
>
|
||||
<testsuites>
|
||||
<testsuite name="Unit">
|
||||
<directory suffix="Test.php">./tests</directory>
|
||||
</testsuite>
|
||||
</testsuites>
|
||||
<coverage processUncoveredFiles="true">
|
||||
<include>
|
||||
<directory suffix=".php">./src</directory>
|
||||
</include>
|
||||
</coverage>
|
||||
</phpunit>
|
||||
907
wp/wp-content/themes/medicalalert/vendor/open-function-computers-llc/better-wordpress/src/Site.php
vendored
Normal file
907
wp/wp-content/themes/medicalalert/vendor/open-function-computers-llc/better-wordpress/src/Site.php
vendored
Normal file
@@ -0,0 +1,907 @@
|
||||
<?php
|
||||
|
||||
namespace ofc;
|
||||
|
||||
use PostTypes\PostType;
|
||||
use Handlebars\Handlebars;
|
||||
use Handlebars\Loader\FilesystemLoader;
|
||||
use PostTypes\Taxonomy;
|
||||
use WP_Post;
|
||||
|
||||
class Site
|
||||
{
|
||||
private $config;
|
||||
private $hb;
|
||||
private $partialsDir;
|
||||
private $fileExtension;
|
||||
private $templateDirectory;
|
||||
|
||||
public function __construct($config = [])
|
||||
{
|
||||
if ($config == [] && file_exists(TEMPLATEPATH . "/config.php")) {
|
||||
$config = include(TEMPLATEPATH . "/config.php");
|
||||
}
|
||||
|
||||
$this->config = $config;
|
||||
$this->bootstrap();
|
||||
}
|
||||
|
||||
private function bootstrap()
|
||||
{
|
||||
// disable various things
|
||||
if (isset($this->config["disable"])) {
|
||||
$this->disable($this->config["disable"]);
|
||||
}
|
||||
|
||||
// enable various things, starting with TinyMCE
|
||||
if (isset($this->config["tinyMCEAdditions"]) || isset($this->config["tiny-mce-additions"])) {
|
||||
$this->addEditorStyles();
|
||||
}
|
||||
if (isset($this->config["enable"])) {
|
||||
$this->enable($this->config["enable"]);
|
||||
}
|
||||
|
||||
// adjust wordpress filters
|
||||
$this->processFilters();
|
||||
|
||||
// create wordpress menu locations
|
||||
$this->registerMenuLocations();
|
||||
|
||||
// initialize handlebars
|
||||
$this->setUpHandlebars();
|
||||
|
||||
// register custom post types
|
||||
$this->registerCPTs();
|
||||
|
||||
// add mix static assets
|
||||
$this->includeManifestFiles();
|
||||
|
||||
// register ACF options pages
|
||||
$this->addOptionsPages();
|
||||
}
|
||||
|
||||
private function addEditorStyles()
|
||||
{
|
||||
$formats = [];
|
||||
|
||||
if (isset($this->config["tinyMCEAdditions"])) {
|
||||
$formats = $this->config["tinyMCEAdditions"];
|
||||
}
|
||||
|
||||
if (isset($this->config["tiny-mce-additions"])) {
|
||||
$formats = $this->config["tiny-mce-additions"];
|
||||
}
|
||||
|
||||
$defaults = [
|
||||
[
|
||||
'title' => 'Headings',
|
||||
'items' => [
|
||||
[
|
||||
'title' => 'Heading 1',
|
||||
'format' => 'h1',
|
||||
],
|
||||
[
|
||||
'title' => 'Heading 2',
|
||||
'format' => 'h2',
|
||||
],
|
||||
[
|
||||
'title' => 'Heading 3',
|
||||
'format' => 'h3',
|
||||
],
|
||||
[
|
||||
'title' => 'Heading 4',
|
||||
'format' => 'h4',
|
||||
],
|
||||
[
|
||||
'title' => 'Heading 5',
|
||||
'format' => 'h5',
|
||||
],
|
||||
[
|
||||
'title' => 'Heading 6',
|
||||
'format' => 'h6',
|
||||
],
|
||||
],
|
||||
],
|
||||
[
|
||||
'title' => 'Inline',
|
||||
'items' => [
|
||||
[
|
||||
'title' => 'Bold',
|
||||
'format' => 'bold',
|
||||
'icon' => 'bold',
|
||||
],
|
||||
[
|
||||
'title' => 'Italic',
|
||||
'format' => 'italic',
|
||||
'icon' => 'italic',
|
||||
],
|
||||
[
|
||||
'title' => 'Underline',
|
||||
'format' => 'underline',
|
||||
'icon' => 'underline',
|
||||
],
|
||||
[
|
||||
'title' => 'Strikethrough',
|
||||
'format' => 'strikethrough',
|
||||
'icon' => 'strikethrough',
|
||||
],
|
||||
[
|
||||
'title' => 'Superscript',
|
||||
'format' => 'superscript',
|
||||
'icon' => 'superscript',
|
||||
],
|
||||
[
|
||||
'title' => 'Subscript',
|
||||
'format' => 'subscript',
|
||||
'icon' => 'subscript',
|
||||
],
|
||||
[
|
||||
'title' => 'Code',
|
||||
'format' => 'code',
|
||||
'icon' => 'code',
|
||||
],
|
||||
],
|
||||
],
|
||||
[
|
||||
'title' => 'Blocks',
|
||||
'items' => [
|
||||
[
|
||||
'title' => 'Paragraph',
|
||||
'format' => 'p',
|
||||
],
|
||||
[
|
||||
'title' => 'Blockquote',
|
||||
'format' => 'blockquote',
|
||||
],
|
||||
[
|
||||
'title' => 'Div',
|
||||
'format' => 'div',
|
||||
],
|
||||
[
|
||||
'title' => 'Pre',
|
||||
'format' => 'pre',
|
||||
],
|
||||
],
|
||||
],
|
||||
[
|
||||
'title' => 'Alignment',
|
||||
'items' => [
|
||||
[
|
||||
'title' => 'Left',
|
||||
'format' => 'alignleft',
|
||||
'icon' => 'alignleft',
|
||||
],
|
||||
[
|
||||
'title' => 'Center',
|
||||
'format' => 'aligncenter',
|
||||
'icon' => 'aligncenter',
|
||||
],
|
||||
[
|
||||
'title' => 'Right',
|
||||
'format' => 'alignright',
|
||||
'icon' => 'alignright',
|
||||
],
|
||||
[
|
||||
'title' => 'Justify',
|
||||
'format' => 'alignjustify',
|
||||
'icon' => 'alignjustify',
|
||||
],
|
||||
],
|
||||
],
|
||||
];
|
||||
|
||||
add_filter('tiny_mce_before_init', function ($settings) use ($formats, $defaults) {
|
||||
$settings['style_formats'] = json_encode(array_merge($defaults, [
|
||||
[
|
||||
"title" => "Custom",
|
||||
"items" => $formats
|
||||
]
|
||||
]));
|
||||
return $settings;
|
||||
});
|
||||
}
|
||||
|
||||
private function includeManifestFiles()
|
||||
{
|
||||
$manifestFile = get_template_directory() . "/dist/mix-manifest.json";
|
||||
if (!file_exists($manifestFile)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$items = json_decode(file_get_contents($manifestFile), true);
|
||||
foreach ($items as $file => $version) {
|
||||
$extension = end(explode(".", $file));
|
||||
$tag = $this->stringify($file);
|
||||
if ($extension === "js") {
|
||||
add_action('wp_enqueue_scripts', function () use ($file, $version, $tag) {
|
||||
wp_register_script($tag, get_template_directory_uri() . '/dist/' . $version, [], '', false);
|
||||
wp_enqueue_script($tag);
|
||||
});
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($extension === "css") {
|
||||
add_action('wp_enqueue_scripts', function () use ($version, $tag) {
|
||||
wp_enqueue_style($tag, get_template_directory_uri() . '/dist/' . $version);
|
||||
});
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private function registerCPTs()
|
||||
{
|
||||
if (!array_key_exists('custom-post-types', $this->config)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$cptTaxonomies = [];
|
||||
foreach ($this->config['custom-post-types'] as $cpt) {
|
||||
if (!isset($cpt['slug'])) {
|
||||
$this->adminError("To register a new custom post type, you must set the `slug` key.");
|
||||
continue;
|
||||
}
|
||||
$options = $cpt['options'] ?? [];
|
||||
$names = $this->generateLabels($cpt['slug']);
|
||||
$newCpt = new PostType($cpt['slug'], $options, $names);
|
||||
|
||||
if (isset($cpt['icon'])) {
|
||||
$newCpt->icon($cpt['icon']);
|
||||
}
|
||||
|
||||
if (isset($cpt["taxonomies"])) {
|
||||
foreach ($cpt["taxonomies"] as $customTaxonomy) {
|
||||
$cptTaxonomies[] = $customTaxonomy;
|
||||
$newCpt->taxonomy($customTaxonomy);
|
||||
}
|
||||
}
|
||||
$newCpt->register();
|
||||
|
||||
// disable post type things here
|
||||
if (isset($cpt["disable"]) && is_array($cpt["disable"])) {
|
||||
foreach ($cpt["disable"] as $feature) {
|
||||
if (strtolower($feature) === "yoast") {
|
||||
add_action('add_meta_boxes', fn () => remove_meta_box('wpseo_meta', $cpt['slug'], 'normal'), 100);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// set up any ACF CPT options pages here
|
||||
if (isset($cpt["options-pages"])) {
|
||||
if (!function_exists("acf_add_options_page")) {
|
||||
$this->adminError("You can't register options pages without the Pro version of Advanced Custom Fields.");
|
||||
continue;
|
||||
}
|
||||
foreach ($cpt["options-pages"] as $optionsPageTitle) {
|
||||
acf_add_options_page([
|
||||
"page_title" => $optionsPageTitle,
|
||||
"menu_title" => $optionsPageTitle,
|
||||
"menu_slug" => $this->stringify($optionsPageTitle),
|
||||
'capability' => 'edit_posts',
|
||||
"position" => 100,
|
||||
"parent_slug" => "edit.php?post_type=" . $cpt["slug"]
|
||||
]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (count($cptTaxonomies)) {
|
||||
foreach ($cptTaxonomies as $customTaxonomy) {
|
||||
$tax = new Taxonomy($customTaxonomy);
|
||||
$tax->options([
|
||||
'hierarchical' => false,
|
||||
]);
|
||||
$tax->register();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private function disable(array $keys)
|
||||
{
|
||||
foreach ($keys as $key) {
|
||||
if ($key === "editor") {
|
||||
define('DISALLOW_FILE_EDIT', true);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private function addOptionsPages()
|
||||
{
|
||||
if (!array_key_exists('options-pages', $this->config)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!function_exists("acf_add_options_page")) {
|
||||
$this->adminError("You can't register options pages without the Pro version of Advanced Custom Fields.");
|
||||
}
|
||||
|
||||
$i = 100;
|
||||
foreach ($this->config["options-pages"] as $pageTitle) {
|
||||
acf_add_options_page([
|
||||
"page_title" => $pageTitle,
|
||||
"menu_title" => $pageTitle,
|
||||
"menu_slug" => $this->stringify($pageTitle),
|
||||
'capability' => 'edit_posts',
|
||||
"position" => $i,
|
||||
]);
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
|
||||
private function enable(array $keys)
|
||||
{
|
||||
foreach ($keys as $key) {
|
||||
if ($key === "post-thumbnails") {
|
||||
add_theme_support('post-thumbnails');
|
||||
continue;
|
||||
}
|
||||
if ($key === "menus") {
|
||||
add_theme_support('menus');
|
||||
continue;
|
||||
}
|
||||
if ($key === "styleselect") {
|
||||
add_filter('mce_buttons_2', function ($buttons) {
|
||||
return array_merge(['styleselect'], $buttons);
|
||||
});
|
||||
continue;
|
||||
}
|
||||
|
||||
$this->adminError("Couldn't enable feature `$key`");
|
||||
}
|
||||
}
|
||||
|
||||
private function processFilters()
|
||||
{
|
||||
// handle "guest" html body class
|
||||
$guestClass = "guest";
|
||||
if (array_key_exists("guest-class", $this->config)) {
|
||||
$guestClass = $this->config["guest-class"];
|
||||
}
|
||||
if (!is_null($guestClass)) {
|
||||
add_filter('body_class', function ($classes) use ($guestClass) {
|
||||
return in_array('logged-in', $classes) ? $classes : [$guestClass, ...$classes];
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private function registerMenuLocations()
|
||||
{
|
||||
if (!array_key_exists("menu-locations", $this->config)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!is_array($this->config["menu-locations"])) {
|
||||
// TODO: show a helpful error message that notifies the developer this is set up wrong
|
||||
return;
|
||||
}
|
||||
|
||||
$menus = $this->config["menu-locations"];
|
||||
add_action('after_setup_theme', function () use ($menus) {
|
||||
register_nav_menus($menus);
|
||||
});
|
||||
}
|
||||
|
||||
private function setUpHandlebars()
|
||||
{
|
||||
if ($this->config["handlebars"] === false) {
|
||||
return;
|
||||
}
|
||||
|
||||
$this->fileExtension = "tpl";
|
||||
if (is_array($this->config["handlebars"]) &&
|
||||
array_key_exists("template-extension", $this->config["handlebars"])
|
||||
) {
|
||||
$this->fileExtension = $this->config["handlebars"]["template-extension"];
|
||||
}
|
||||
|
||||
$this->templateDirectory = "tpl";
|
||||
if (is_array($this->config["handlebars"]) &&
|
||||
array_key_exists("template-directory", $this->config["handlebars"])
|
||||
) {
|
||||
$this->templateDirectory = $this->config["handlebars"]["template-directory"];
|
||||
}
|
||||
|
||||
$this->partialsDir = get_template_directory()."/".$this->templateDirectory;
|
||||
if (!file_exists($this->partialsDir) && !is_dir($this->partialsDir)) {
|
||||
$this->adminError("Your Handlebars directory is not setup correctly or doesn't exist.");
|
||||
return;
|
||||
}
|
||||
$partialsLoader = new FilesystemLoader($this->partialsDir, ["extension" => $this->fileExtension]);
|
||||
|
||||
$this->hb = new Handlebars([
|
||||
"loader" => $partialsLoader,
|
||||
"partials_loader" => $partialsLoader,
|
||||
"enableDataVariables" => true,
|
||||
]);
|
||||
|
||||
if (isset($this->config["handlebars"]["additional-helpers"])) {
|
||||
foreach ($this->config["handlebars"]["additional-helpers"] as $name => $callback) {
|
||||
$this->hb->addHelper($name, $callback);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* render
|
||||
* See $this->view()
|
||||
*
|
||||
* @param string $fileName
|
||||
* @param array $data
|
||||
* @return string
|
||||
*/
|
||||
public function render(string $fileName, array $data = []) : string
|
||||
{
|
||||
return $this->view($fileName, $data);
|
||||
}
|
||||
|
||||
/**
|
||||
* view
|
||||
* Invoke handlebar rendering engine for a given template file and data array
|
||||
*
|
||||
* @param string $fileName
|
||||
* @param array $data
|
||||
* @return string
|
||||
*/
|
||||
public function view(string $fileName, array $data = []) : string
|
||||
{
|
||||
$filePath = $this->partialsDir."/".$fileName.".".$this->fileExtension;
|
||||
if (!file_exists($filePath)) {
|
||||
if ($this->config["debug"] === true) {
|
||||
return "<pre>View {$fileName}.{$this->fileExtension} does not exist.\nData:\n"
|
||||
.print_r($data, true)
|
||||
."</pre>";
|
||||
}
|
||||
return "";
|
||||
}
|
||||
return $this->hb->render($fileName, $data);
|
||||
}
|
||||
|
||||
public function getPost($idOrPost, $fields = [])
|
||||
{
|
||||
if (is_numeric($idOrPost)) {
|
||||
$p = get_post($idOrPost);
|
||||
} elseif ($idOrPost instanceof WP_Post) {
|
||||
$p = $idOrPost;
|
||||
} else {
|
||||
return [
|
||||
"error" => "You must pass an ID or WP_Post to this method"
|
||||
];
|
||||
}
|
||||
|
||||
if ($fields == []) {
|
||||
return [
|
||||
'post' => $p,
|
||||
'meta' => get_post_meta($p->ID),
|
||||
];
|
||||
}
|
||||
|
||||
$output = [];
|
||||
$categories = [];
|
||||
$taxonomies = [];
|
||||
foreach ($fields as $key) {
|
||||
// handle url/permalink
|
||||
if ($key === "url" || $key === "permalink") {
|
||||
$output[$key] = get_permalink($p->ID);
|
||||
continue;
|
||||
}
|
||||
|
||||
// handle post content
|
||||
if ($key === "content") {
|
||||
$output["content"] = apply_filters('the_content', get_the_content($p->ID));
|
||||
continue;
|
||||
}
|
||||
|
||||
// handle post excerpt
|
||||
if ($key === "excerpt") {
|
||||
$output["excerpt"] = get_the_excerpt($p->ID);
|
||||
continue;
|
||||
}
|
||||
|
||||
// handle meta keys
|
||||
if (substr($key, 0, 5) === "meta.") {
|
||||
$output[substr($key, 5)] = get_post_meta($p->ID, substr($key, 5), true);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (substr($key, 0, 4) === "acf.") {
|
||||
$output[substr($key, 4)] = get_field(substr($key, 4), $p->ID);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (substr($key, 0, 11) === "categories.") {
|
||||
if (count($categories) == 0) {
|
||||
$categories = wp_get_post_categories($p->ID, ["fields" => "all"]);
|
||||
$attrs = explode(",", substr($key, 11));
|
||||
|
||||
foreach ($categories as $cat) {
|
||||
$dataToAppend = [];
|
||||
foreach ($attrs as $key) {
|
||||
$oldKey = $key;
|
||||
if ($key == "id") {
|
||||
$key = "term_id";
|
||||
}
|
||||
if (isset($cat->$key)) {
|
||||
$dataToAppend[$oldKey] = $cat->$key;
|
||||
}
|
||||
}
|
||||
$output["categories"][] = $dataToAppend;
|
||||
}
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
if (substr($key, 0, 9) === "taxonomy.") {
|
||||
$taxonomyKey = $this->parseTaxKey($key);
|
||||
$values = explode(",", $this->parseTaxValues($key));
|
||||
if (!isset($taxonomies[$taxonomyKey])) {
|
||||
$taxonomies[$taxonomyKey] = $this->getPostTaxonomy($p, $taxonomyKey);
|
||||
$output[$taxonomyKey] = [];
|
||||
}
|
||||
|
||||
if (!is_array($taxonomies[$taxonomyKey])) {
|
||||
continue;
|
||||
}
|
||||
|
||||
foreach ($taxonomies[$taxonomyKey] as $tax) {
|
||||
$taxonomyDTO = [];
|
||||
foreach ($values as $val) {
|
||||
if ($val === "id" || $val === "term_id") {
|
||||
$taxonomyDTO["id"] = $tax->term_id;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($val === "link") {
|
||||
$taxonomyDTO["link"] = get_term_link($tax);
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($val === "name") {
|
||||
$taxonomyDTO["name"] = $tax->name;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($val === "title") {
|
||||
$taxonomyDTO["title"] = $tax->name;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($val === "slug") {
|
||||
$taxonomyDTO["slug"] = $tax->slug;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($val === "description") {
|
||||
$taxonomyDTO["description"] = $tax->description;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
$output[$taxonomyKey][] = $taxonomyDTO;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
// let's keep our sanity here...
|
||||
// the following keys are here for convienance. WP names things so weirdly!
|
||||
if ($key === "id") {
|
||||
$output[$key] = $p->ID;
|
||||
continue;
|
||||
}
|
||||
if ($key === "title" || $key === "name") {
|
||||
$output[$key] = $p->post_title;
|
||||
continue;
|
||||
}
|
||||
if ($key === "thumbnail") {
|
||||
$output[$key] = get_the_post_thumbnail_url($p->ID);
|
||||
continue;
|
||||
}
|
||||
|
||||
$output[$key] = $p->$key;
|
||||
}
|
||||
return $output;
|
||||
}
|
||||
|
||||
public function getPosts($args = [], $fields = [])
|
||||
{
|
||||
$args = $this->processArgs($args);
|
||||
$posts = get_posts($args);
|
||||
|
||||
if ($fields == []) {
|
||||
return [
|
||||
'posts' => $posts,
|
||||
];
|
||||
}
|
||||
|
||||
$output = [];
|
||||
foreach ($posts as $p) {
|
||||
$output[] = $this->getPost($p, $fields);
|
||||
}
|
||||
return $output;
|
||||
}
|
||||
|
||||
/**
|
||||
* getCurrentPosts
|
||||
* see getDefaultPosts
|
||||
*
|
||||
* @deprecated 1.0.15
|
||||
*
|
||||
* @param array $fields
|
||||
* @return array
|
||||
*/
|
||||
public function getCurrentPosts($fields = []) : array
|
||||
{
|
||||
return $this->getDefaultPosts($fields);
|
||||
}
|
||||
|
||||
/**
|
||||
* getDefaultPosts
|
||||
* get all the posts for the current page as defined by wordpress' weird rules for archive pages
|
||||
*
|
||||
* @param array $fields
|
||||
* @return array
|
||||
*/
|
||||
public function getDefaultPosts($fields = []) : array
|
||||
{
|
||||
$output = [];
|
||||
if (!have_posts()) {
|
||||
return $output;
|
||||
}
|
||||
while (have_posts()) {
|
||||
the_post();
|
||||
global $post;
|
||||
$output[] = $this->getPost($post, $fields);
|
||||
}
|
||||
return $output;
|
||||
}
|
||||
|
||||
public function getTerm($slug, $fields = [])
|
||||
{
|
||||
$args = [
|
||||
'taxonomy' => $slug,
|
||||
'hide_empty' => false,
|
||||
'suppress_filter' => true,
|
||||
];
|
||||
$results = get_terms($args);
|
||||
|
||||
if ($fields == []) {
|
||||
return $results;
|
||||
}
|
||||
|
||||
$output = [];
|
||||
foreach ($results as $term) {
|
||||
$append = [];
|
||||
foreach ($fields as $key) {
|
||||
$oldKey = $key;
|
||||
if ($key == "id") {
|
||||
$key = "term_id";
|
||||
}
|
||||
if ($key == "title") {
|
||||
$key = "name";
|
||||
}
|
||||
|
||||
if ($oldKey != $key) {
|
||||
$append[$oldKey] = $term->$key;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($key === "url" || $key === "permalink") {
|
||||
$append[$key] = get_term_link($term);
|
||||
continue;
|
||||
}
|
||||
$append[$key] = $term->$key;
|
||||
}
|
||||
$output[] = $append;
|
||||
}
|
||||
return $output;
|
||||
}
|
||||
|
||||
private function processArgs(array $args) : array
|
||||
{
|
||||
// wordpress default
|
||||
$args = array_merge(
|
||||
[
|
||||
'numberposts' => 5,
|
||||
'category' => 0,
|
||||
'orderby' => 'date',
|
||||
'order' => 'DESC',
|
||||
'include' => array(),
|
||||
'exclude' => array(),
|
||||
'meta_key' => '',
|
||||
'meta_value' => '',
|
||||
'post_type' => 'post',
|
||||
'suppress_filters' => true,
|
||||
],
|
||||
$args
|
||||
);
|
||||
|
||||
if (isset($args["type"])) {
|
||||
$args["post_type"] = $args["type"];
|
||||
}
|
||||
|
||||
if (isset($args["title"])) {
|
||||
$args["title"] = urldecode($args["title"]);
|
||||
}
|
||||
|
||||
if (isset($args["s"])) {
|
||||
$args["s"] = urldecode($args["s"]);
|
||||
}
|
||||
|
||||
// process custom taxonomy
|
||||
$taxQuery = [];
|
||||
foreach ($args as $paramKey => $paramValue) {
|
||||
if (!(substr($paramKey, 0, 4) === "tax." || substr($paramKey, 0, 9) === "taxonomy.")) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (substr($paramKey, 0, 4) === "tax.") {
|
||||
$tax = substr($paramKey, 4);
|
||||
}
|
||||
|
||||
if (substr($paramKey, 0, 9) === "taxonomy.") {
|
||||
$tax = substr($paramKey, 9);
|
||||
}
|
||||
|
||||
$field = "slug";
|
||||
$values = explode(",", $paramValue);
|
||||
$allValuesAreNumeric = false;
|
||||
foreach ($values as $v) {
|
||||
if (is_numeric($v)) {
|
||||
$allValuesAreNumeric = true;
|
||||
}
|
||||
}
|
||||
|
||||
if ($allValuesAreNumeric) {
|
||||
$field = "term_id";
|
||||
}
|
||||
|
||||
$taxQuery[] = [
|
||||
"taxonomy" => $tax,
|
||||
"field" => $field,
|
||||
"terms" => $values,
|
||||
];
|
||||
}
|
||||
if ($taxQuery != []) {
|
||||
$args['tax_query'] = $taxQuery;
|
||||
}
|
||||
|
||||
return $args;
|
||||
}
|
||||
|
||||
private function parseTaxKey(string $paramater) : string
|
||||
{
|
||||
$parts = explode(".", $paramater);
|
||||
if (count($parts) != 3) {
|
||||
return $paramater;
|
||||
}
|
||||
return $parts[1];
|
||||
}
|
||||
|
||||
private function parseTaxValues(string $paramater) : string
|
||||
{
|
||||
$parts = explode(".", $paramater);
|
||||
if (count($parts) != 3) {
|
||||
return $paramater;
|
||||
}
|
||||
return $parts[2];
|
||||
}
|
||||
|
||||
public function getPostTaxonomy($post, $taxonomyKey)
|
||||
{
|
||||
return get_the_terms($post->ID, $taxonomyKey);
|
||||
}
|
||||
|
||||
public function setPostMeta($postID, $data)
|
||||
{
|
||||
foreach ($data as $metaKey => $metaValue) {
|
||||
update_post_meta($postID, $metaKey, $metaValue);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* add an error to the wordpress backend
|
||||
*
|
||||
* @param string $message
|
||||
*/
|
||||
private function adminError(string $message)
|
||||
{
|
||||
$key = $this->stringify($message);
|
||||
add_action('admin_notices', function ($messages) use ($message, $key) {
|
||||
add_settings_error($key, '', "OFC Site Error: $message", 'error');
|
||||
settings_errors($key);
|
||||
return $messages;
|
||||
});
|
||||
}
|
||||
|
||||
public function renderMenu($menuLocation)
|
||||
{
|
||||
return wp_nav_menu([
|
||||
"theme_location" => $menuLocation,
|
||||
"echo" => false,
|
||||
]);
|
||||
}
|
||||
|
||||
private function stringify(string $thing) : string
|
||||
{
|
||||
$bad = [" ", "/"];
|
||||
$good = ["_", ""];
|
||||
return strtolower(str_replace($bad, $good, $thing));
|
||||
}
|
||||
|
||||
public function getAssetURL(string $filename) : string
|
||||
{
|
||||
if (!file_exists(get_template_directory()."/assets/$filename")) {
|
||||
$this->adminError("Requested asset $filename doesn't exist.");
|
||||
return "";
|
||||
}
|
||||
|
||||
return get_template_directory_uri()."/assets/$filename";
|
||||
}
|
||||
|
||||
private function generateLabels(string $slug) : array
|
||||
{
|
||||
return [
|
||||
'name' => $this->humanize($slug, true),
|
||||
'singular_name' => $this->humanize($slug, false),
|
||||
'menu_name' => $this->humanize($slug, true),
|
||||
'all_items' => "All " . $this->humanize($slug, true),
|
||||
'add_new' => "Add New {$this->humanize($slug, false)}",
|
||||
'add_new_item' => "Add New {$this->humanize($slug, false)}",
|
||||
'edit_item' => "Edit {$this->humanize($slug, false)}",
|
||||
'new_item' => "New {$this->humanize($slug, false)}",
|
||||
'view_item' => "View {$this->humanize($slug, false)}",
|
||||
'search_items' => "Search {$this->humanize($slug, true)}",
|
||||
'not_found' => "No {$this->humanize($slug, true)} found",
|
||||
'not_found_in_trash' => "No {$this->humanize($slug, true)} found in Trash",
|
||||
'parent_item_colon' => "Parent {$this->humanize($slug, false)}:",
|
||||
];
|
||||
}
|
||||
|
||||
private function humanize(string $word, bool $makePlural = false) : string
|
||||
{
|
||||
$humanized = ucwords(strtolower(str_replace(['-', '_'], ' ', $word)));
|
||||
|
||||
if (!$makePlural) {
|
||||
return $humanized;
|
||||
}
|
||||
|
||||
if (strtolower(substr($humanized, strlen($humanized)-1, 1)) == "s") {
|
||||
return $humanized . "es";
|
||||
}
|
||||
if (strtolower(substr($humanized, strlen($humanized)-1, 1)) == "y") {
|
||||
return substr($humanized, 0, strlen($humanized)-1) . "ies";
|
||||
}
|
||||
return $humanized . "s";
|
||||
}
|
||||
|
||||
public function getPaginationLinks() : array
|
||||
{
|
||||
global $wp_query;
|
||||
|
||||
$output = [
|
||||
"older" => false,
|
||||
"newer" => false,
|
||||
"totalPages" => 0,
|
||||
"currentPage" => 0,
|
||||
];
|
||||
|
||||
if (is_singular()) {
|
||||
return $output;
|
||||
}
|
||||
|
||||
$max_num_pages = (int) $wp_query->max_num_pages;
|
||||
$paged = get_query_var('paged');
|
||||
if (($paged + 1) < $max_num_pages) {
|
||||
$output["older"] = next_posts(0, false);
|
||||
}
|
||||
|
||||
if ($max_num_pages > 1 && $paged <= $max_num_pages && $paged > 0) {
|
||||
$output["newer"] = previous_posts(false);
|
||||
}
|
||||
|
||||
$output["totalPages"] = $max_num_pages;
|
||||
$output["currentPage"] = $paged;
|
||||
|
||||
return $output;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
<?php
|
||||
|
||||
namespace ofc;
|
||||
|
||||
class Util
|
||||
{
|
||||
/**
|
||||
* slugify
|
||||
* modified from https://lucidar.me/en/web-dev/how-to-slugify-a-string-in-php/
|
||||
*
|
||||
* @param string $str
|
||||
* @return string
|
||||
*/
|
||||
public static function slugify(string $str) : string
|
||||
{
|
||||
$text = strip_tags($str);
|
||||
$text = str_replace(" & ", " and ", $text);
|
||||
$text = preg_replace('~[^\pL\d]+~u', '-', $text);
|
||||
setlocale(LC_ALL, 'en_US.utf8');
|
||||
$text = iconv('utf-8', 'us-ascii//TRANSLIT', $text);
|
||||
$text = preg_replace('~[^-\w]+~', '', $text);
|
||||
$text = trim(strtolower($text), '-');
|
||||
$text = preg_replace('~-+~', '-', $text);
|
||||
if (empty($text)) {
|
||||
return 'n-a';
|
||||
}
|
||||
return $text;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
<?php
|
||||
|
||||
namespace ofc\tests;
|
||||
|
||||
use ofc\Util;
|
||||
use PHPUnit\Framework\TestCase;
|
||||
|
||||
class UtilTest extends TestCase
|
||||
{
|
||||
/** @test */
|
||||
public function weCanSlugifyAString()
|
||||
{
|
||||
$cases = [
|
||||
"This is a string" => "this-is-a-string",
|
||||
"String with nÓn ASCII chars & stuff!" => "string-with-non-ascii-chars-and-stuff",
|
||||
];
|
||||
|
||||
foreach ($cases as $input => $expected) {
|
||||
$this->assertEquals($expected, Util::slugify($input));
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user