Including libraries from node_modules in Wordpress Plugin - php

I am creating a ReactJs and wordpress plugin. I have created the standalone Reactjs control and I now want to include my reactJS libraries in the node_modules folder in my wordpress php file like so. Is this the right way to do it? Wordpress is able to find the node_modules folder and the libraries that I have enqueued but not the libraries that the enqueued files depend on(which are present in the node_modules folder).
add_action( 'wp_enqueue_scripts', 'FacebookAlbums_enqueue_scripts' );
function FacebookAlbums_enqueue_scripts() {
wp_enqueue_script( 'react', plugin_dir_url( __FILE__ ) . 'node_modules/react/umd/react.production.min.js' );
wp_enqueue_script( 'react-dom', plugin_dir_url( __FILE__ ) . 'node_modules/react-dom/umd/react-dom.production.min.js' );
wp_enqueue_script( 'react-slick', plugin_dir_url( __FILE__ ) . 'node_modules/react-slick/lib/slider.js' );
wp_enqueue_script( 'react-image-lightbox', plugin_dir_url( __FILE__ ) . 'node_modules/react-image-lightbox/dist/main.js' );
wp_enqueue_script( 'babel', 'https://npmcdn.com/babel-core#5.8.38/browser.min.js', '', null, false );
wp_enqueue_script( 'FacebookAlbums', plugin_dir_url( __FILE__ ) . 'FacebookAlbums.js' );
wp_enqueue_style( 'FacebookAlbums', plugin_dir_url( __FILE__ ) . 'FacebookAlbums.css' );
}

Place this file in the same folder as your package.json that contains your dependencies:
<?php
// the generic wp node_modules loader
$package = file_get_contents(__DIR__ . '/package.json');
$package = json_decode($package, true);
foreach ($package['dependencies'] as $dep => $version) {
$subpackage = file_get_contents(__DIR__ . "/node_modules/$dep/package.json");
$subpackage = json_decode($subpackage, true);
$use = 'main';
if (isset($subpackage['browser'])) {
$use = 'browser';
}
if (isset($subpackage[$use])) {
$deps = array();
if (strpos($dep, 'jquery') !== false) {
$deps[] = 'jquery';
}
wp_enqueue_script("node_module-$dep", plugin_dir_url(__FILE__) . "node_modules/$dep/" . $subpackage[$use], $deps, $subpackage['version']);
}
if (isset($subpackage['style'])) {
wp_enqueue_style("node_module-$dep", plugin_dir_url(__FILE__) . "node_modules/$dep/" . $subpackage['style']);
}
}
You'll need to require this file somewhere in your plugin. (This will not work with 100% of packages, modify it according to your project - this is a work in progress).

Related

How to fix fatal PHP error on Wordpress login page?

I'm trying load my websites Wordpress page but get the error
Warning: require(__DIR__/wp-load.php) [function.require]: failed to open stream: No such file or directory in /home/content/39/4124639/html/wp-login.php on line 12
Fatal error: require() [function.require]: Failed opening required '__DIR__/wp-load.php' (include_path='.:/usr/local/php5/lib/php') in /home/content/39/4124639/html/wp-login.php on line 12
Inside the wp-login.php file on line 12 is: require __DIR__ . '/wp-load.php';
I confirmed the file wp-load.php is there. Can someone help?
I haven't changed my wp-blog-header.php file it is:
<?php
/**
* Loads the WordPress environment and template.
*
* #package WordPress
*/
if ( ! isset( $wp_did_header ) ) {
$wp_did_header = true;
// Load the WordPress library.
require_once __DIR__ . '/wp-load.php';
// Set up the WordPress query.
wp();
// Load the theme template.
require_once ABSPATH . WPINC . '/template-loader.php';
}
The wp-load.php file is (I haven't messed around with it either):
<?php
/**
* Bootstrap file for setting the ABSPATH constant
* and loading the wp-config.php file. The wp-config.php
* file will then load the wp-settings.php file, which
* will then set up the WordPress environment.
*
* If the wp-config.php file is not found then an error
* will be displayed asking the visitor to set up the
* wp-config.php file.
*
* Will also search for wp-config.php in WordPress' parent
* directory to allow the WordPress directory to remain
* untouched.
*
* #package WordPress
*/
/** Define ABSPATH as this file's directory */
if ( ! defined( 'ABSPATH' ) ) {
define( 'ABSPATH', __DIR__ . '/' );
}
error_reporting( E_CORE_ERROR | E_CORE_WARNING | E_COMPILE_ERROR | E_ERROR | E_WARNING | E_PARSE | E_USER_ERROR | E_USER_WARNING | E_RECOVERABLE_ERROR );
/*
* If wp-config.php exists in the WordPress root, or if it exists in the root and wp-settings.php
* doesn't, load wp-config.php. The secondary check for wp-settings.php has the added benefit
* of avoiding cases where the current directory is a nested installation, e.g. / is WordPress(a)
* and /blog/ is WordPress(b).
*
* If neither set of conditions is true, initiate loading the setup process.
*/
if ( file_exists( ABSPATH . 'wp-config.php' ) ) {
/** The config file resides in ABSPATH */
require_once ABSPATH . 'wp-config.php';
} elseif ( #file_exists( dirname( ABSPATH ) . '/wp-config.php' ) && ! #file_exists( dirname( ABSPATH ) . '/wp-settings.php' ) ) {
/** The config file resides one level above ABSPATH but is not part of another installation */
require_once dirname( ABSPATH ) . '/wp-config.php';
} else {
// A config file doesn't exist.
define( 'WPINC', 'wp-includes' );
require_once ABSPATH . WPINC . '/load.php';
// Standardize $_SERVER variables across setups.
wp_fix_server_vars();
require_once ABSPATH . WPINC . '/functions.php';
$path = wp_guess_url() . '/wp-admin/setup-config.php';
/*
* We're going to redirect to setup-config.php. While this shouldn't result
* in an infinite loop, that's a silly thing to assume, don't you think? If
* we're traveling in circles, our last-ditch effort is "Need more help?"
*/
if ( false === strpos( $_SERVER['REQUEST_URI'], 'setup-config' ) ) {
header( 'Location: ' . $path );
exit;
}
define( 'WP_CONTENT_DIR', ABSPATH . 'wp-content' );
require_once ABSPATH . WPINC . '/version.php';
wp_check_php_mysql_versions();
wp_load_translations_early();
// Die with an error message
$die = sprintf(
/* translators: %s: wp-config.php */
__( "There doesn't seem to be a %s file. I need this before we can get started." ),
'<code>wp-config.php</code>'
) . '</p>';
$die .= '<p>' . sprintf(
/* translators: %s: Documentation URL. */
__( "Need more help? <a href='%s'>We got it</a>." ),
__( 'https://wordpress.org/support/article/editing-wp-config-php/' )
) . '</p>';
$die .= '<p>' . sprintf(
/* translators: %s: wp-config.php */
__( "You can create a %s file through a web interface, but this doesn't work for all server setups. The safest way is to manually create the file." ),
'<code>wp-config.php</code>'
) . '</p>';
$die .= '<p>' . __( 'Create a Configuration File' ) . '';
wp_die( $die, __( 'WordPress › Error' ) );
}

wordpress get url of registered script

If I register a script or style (using wp_register_script() or wp_register_style()), is there a way I can get the URL of that script/style?
(If you must know why, I'm trying to put those URL's into another function that generates prefetch link tags so I can prefetch certain scripts/styles for a performance boost in my site.)
Just in case someone is still looking for this:
<?php
function invdr_get_script_uri_by_handler( $handler ){
//Get an instance of WP_Scripts or create new;
$wp_scripts = wp_scripts();
//Get the script by registered handler name
$script = $wp_scripts->registered[ $handler ];
if ( file_exists( ABSPATH . $script->src ) ){
return ABSPATH . $script->src;
}
return false;
}
add_action( 'wp_enqueue_scripts', 'invdr_get_script_uri_by_handler', PHP_INT_MAX );
Tested in wordpress 5.0
You can use wp_scripts() to get the instance of the WP_Scripts class which contains the registered scripts (this class extends WP_Dependencies).
Basically, try looking in:
$wp_scripts = wp_scripts();
var_dump( $wp_scripts->registered );
var_dump( $wp_scripts );
Here's how I've accomplished this in a self-authored plugin to help me enhance dependencies within WordPress:
// Convert relative URL to absolute?
$absolute = true;
$handle = 'your_stylesheet_handle';
$helper = wp_styles();
$object = $helper->registered[ $handle ];
$src = $object->src;
if (
$absolute
&& $helper->in_default_dir( $src )
) {
$src = $helper->base_url . $src;
}
$ver = $object->ver;
if ( ! is_null( $ver ) && empty( $ver ) ) {
$ver = $helper->default_version;
}
if ( isset( $helper->args[ $handle ] ) ) {
$ver = $ver ? $ver . '&' : '';
$ver .= $helper->args[ $handle ];
}
$src = add_query_arg( 'ver', $ver, $src );
$stylesheet_url = urldecode_deep( $src );
Note that the absolute URL conversion is directed towards handling assets registered by WordPress core, as they're typically relative URLs.

How Can I Get the Current Logged-In User with WordPress SHORTINIT

I'm running a PHP script called by an AJAX function. I do not want to use the built-in WordPress AJAX API because it would take way too long, since I'm uploading a lot of images. I'm using SHORTINIT to do a partial WordPress load like this: https://wordpress.stackexchange.com/questions/173002/how-declare-ajax-functions-ussing-shortinit
I need to check the username of the current logged-in user. Can someone list the files I need to include/require in my custom PHP file and the order they should be in? Thanks!
As I cant comment (new user). The final soultion (single WP install) I use for making is_user_logged_in() and current_user_can() work, is as follow below. We require('wp-load.php') first (to skip wp() in load-blog-header.php), and get ABSPATH constant then, manually includes exactly all the stuff needed.
Using define('SHORTINIT', true) + require('wp-load.php') + manually includes:
Pageload: 1.05 sek - included files: 43 files
Comparing: Using ONLY require('wp-load.php'):
Pageload: 1.35 sek - included files: 419 files
The time difference (0.3 sek) might differ from installs and PHP engines, but while validating many requests on one pageload -things adds up!
Remember to use relative call to WP installed dir. From a Wordpress custom plugin dir, inside one subdir level, normal install, a path should be like:
$wordpress = '../../../../wp-load.php';
Then:
define('SHORTINIT', true);
include_once $wordpress;
require_once ( ABSPATH . WPINC . '/class-wp-user.php' );
require_once ( ABSPATH . WPINC . '/class-wp-roles.php' );
require_once ( ABSPATH . WPINC . '/class-wp-role.php' );
require_once ( ABSPATH . WPINC . '/class-wp-session-tokens.php' );
require_once ( ABSPATH . WPINC . '/class-wp-user-meta-session-tokens.php' );
require_once ( ABSPATH . WPINC . '/formatting.php' );
require_once ( ABSPATH . WPINC . '/capabilities.php' );
//require_once ( ABSPATH . WPINC . '/query.php' ); // - might be useful
require_once ( ABSPATH . WPINC . '/user.php' );
require_once ( ABSPATH . WPINC . '/meta.php' );
wp_cookie_constants();
require_once ( ABSPATH . WPINC . '/vars.php' );
require_once ( ABSPATH . WPINC . '/kses.php' );
require_once ( ABSPATH . WPINC . '/rest-api.php' );
require_once ( ABSPATH . WPINC . '/pluggable.php' );
After this, user validation is accessable. For other task, running on one or two requests, tracking down other needed files is not worth 0.3 sek. Skip the SHORTINIT constant and manually clutter.
Maybe a bit late but I will post it here so it might be useful to other people.
I needed a quick light weight way to load the minimum of Wordpress to figure out the user in a separate API next to the Wordpress install. For me this code works with Wordpress 4.8
NOTE: it is only used in this way. It can be that if you need to do more Wordpress things, you are missing some includes.
// load minimum wordpress to load the user
define('SHORTINIT', true);
/** Define ABSPATH as this files directory */
define( 'ABSPATH', dirname(__FILE__) . '/' );
//WP config file
require ('wp-config.php');
// Run the installer if WordPress is not installed.
wp_not_installed();
require( ABSPATH . WPINC . '/class-wp-user.php' );
require( ABSPATH . WPINC . '/class-wp-roles.php' );
require( ABSPATH . WPINC . '/class-wp-role.php' );
require( ABSPATH . WPINC . '/class-wp-session-tokens.php' );
require( ABSPATH . WPINC . '/class-wp-user-meta-session-tokens.php' );
require( ABSPATH . WPINC . '/formatting.php' );
require( ABSPATH . WPINC . '/capabilities.php' );
require( ABSPATH . WPINC . '/query.php' );
require( ABSPATH . WPINC . '/user.php' );
require( ABSPATH . WPINC . '/meta.php' );
// Define constants after multisite is loaded. Cookie-related constants may be overridden in ms_network_cookies().
wp_cookie_constants( );
// Create common globals.
require( ABSPATH . WPINC . '/vars.php' );
require( ABSPATH . WPINC . '/kses.php' );
require( ABSPATH . WPINC . '/rest-api.php' );
require( ABSPATH . WPINC . '/pluggable.php' );
require('wp-load.php');
$user = wp_get_current_user();
var_dump($user);
I used the code here as a starting point but that didn't work under the current Wordpress version for me:
https://wordpress.stackexchange.com/questions/28342/is-there-a-way-to-use-the-wordpress-users-but-without-loading-the-entire-wordpre

Enqueueing scripts if a file exists

I work with wordpress on my child theme.
My site is installed into mydomain.xx/install, but runs from mydomain.xx.
My functions.php works and looks like this:
<?php
/* Script in head */
function carica_scripts() {
/* Common scripts */
// insert scripts here, if some
/* Page-based script */
$pageId = get_the_ID();
$pageType = get_post_type();
$myBaseURL = get_stylesheet_directory_uri() . '/js/';
/* Page-type scripts */
if($pageType == "product") {
wp_enqueue_script('CondAll', $myBaseURL . 'CondAll.js', array('jquery'));
wp_enqueue_script('CondShipping', $myBaseURL . 'CondShipping.js', array('jquery'));
}
/* Page-id scripts */
if($pageId == "1") {
wp_enqueue_script('Cond1', $myBaseURL . 'Cond1.js', array('jquery'));
}
if($pageId == "294") {
wp_enqueue_script('Cond294', $myBaseURL . 'Cond294.js', array('jquery'));
}
if($pageId == "318") {
wp_enqueue_script('Cond318', $myBaseURL . 'Cond318.js', array('jquery'));
}
if($pageId == "232") {
wp_enqueue_script('Cond232', $myBaseURL . 'Cond232.js', array('jquery'));
}
/* END of page-based script */
}
add_action( 'wp_enqueue_scripts', 'carica_scripts' );
?>
What I want to achieve is avoiding all the ifs on $pageId, and to auto-enqueue jQuery script CodXXX.js on page id XXX if the relative file exists in the subdirectory /js/ of my child theme.
file_exists() expects an absolute path to a file rather than a URL.
Use get_stylesheet_directory() to get the path you need. Also get_the_ID() shouldn't be used outside of the loop.
Example:
/*
* Enqueue CondXXX.js on page XXX if file CondXXX.js exists
*/
function carica_scripts() {
global $post;
// Check we're on a page.
if ( ! is_page() ) {
return false;
}
// Build the filename to check.
$handle = 'Cond' . $post->ID;
$relpath = '/js/' . $handle . '.js';
// Get path + url to file.
$file_path = get_stylesheet_directory() . $relpath;
$file_url = get_stylesheet_directory_uri() . $relpath;
if ( file_exists( $file_path ) ) {
wp_enqueue_script( $handle, $file_url, array( 'jquery' ) );
}
}
add_action( 'wp_enqueue_scripts', 'carica_scripts' );
The answer given by Nathan Dawson does not work in my case, I had to do some workarounds. I ended up with the following code:
/* Load scripts in head */
function carica_scripts() {
/* Common scripts */
/* END of common scripts */
/* Page-based script */
$pageId = get_the_ID();
$pageType = get_post_type();
$handle = 'Cond' . $pageId;
$file = $handle .'.js';
$relPath = '/js/';
$styleSheet_path = get_stylesheet_directory();
$domain_base = 'mydomain.it/public_html/';
$start_pos = strpos ( $styleSheet_path, $domain_base) + strlen ($domain_base);
$basePath = substr ( $styleSheet_path, $start_pos); // I need everything after 'mydomain.it/public_html/'
$file_path = $basePath. $relPath . $file;
$enqueue_path = get_stylesheet_directory_uri() . $relPath;
$enqueue_file = $enqueue_path . $file;
/* if page-type is ... (product, in this case) */
if($pageType == "product") {
wp_enqueue_script('CondAll', $enqueue_path . 'CondAll.js', array('jquery'));
wp_enqueue_script('CondShipping', $enqueue_path . 'CondShipping.js', array('jquery'));
}
/* If page id is... (1, in this case - because page 1 is not product but I want CondAll here too) */
if($pageId == "1") {
wp_enqueue_script('CondAll', $enqueue_path . 'CondAll.js', array('jquery'));
}
/* auto load script CondXXX.js from subdir js/ if file exists */
if ( file_exists( $file_path ) ) {
wp_enqueue_script( $handle, $enqueue_file, array( 'jquery' ) );
}
/* END of page-based script */
}
add_action( 'wp_enqueue_scripts', 'carica_scripts' );
Now the the scripts load.

How does wordpress do to make functions.php available withouut includes?

It may be a silly question, but I cant understand how I can access every function (from functions.php for example) in WordPress without any include or require calls, I know if I want to create a new script I can simply require wp-load.php from that particular script, just dont understand why this is isn't needed in other template files.
WordPress does that automatically. Whenever there is a functions.php file for the active theme, WP will load it for you. The magic happens in wp-settings.php, specifically among the following lines:
if ( ! defined( 'WP_INSTALLING' ) || 'wp-activate.php' === $pagenow ) {
if ( TEMPLATEPATH !== STYLESHEETPATH && file_exists( STYLESHEETPATH . '/functions.php' ) )
include( STYLESHEETPATH . '/functions.php' );
if ( file_exists( TEMPLATEPATH . '/functions.php' ) )
include( TEMPLATEPATH . '/functions.php' );
}

Categories