Appearance
Advanced Topics
This guide covers advanced features and integrations in LamaPress, including Bunny.net, custom integrations, and advanced patterns.
Table of Contents
- Bunny.net Integration
- Custom Integrations
- Advanced ACF Patterns
- Custom Post Types
- Advanced JavaScript Patterns
- WordPress Hooks
Bunny.net Integration
Overview
LamaPress includes integration with Bunny.net for video hosting and CDN services.
Configuration
Set up Bunny.net constants in wp-config.php:
php
define('LL_BUNNY_API_KEY', 'your-api-key');
define('LL_BUNNY_LIBRARY_ID', 'your-library-id');
define('LL_BUNNY_PULL_ZONE', 'your-pull-zone');Video Library
Access Bunny.net video library:
php
<?php
// Get video library helper
$bunnyHelper = new BunnyHelpers();
// Upload video
$video = $bunnyHelper->uploadVideo($file, $title);
// Get video URL
$videoUrl = $bunnyHelper->getVideoUrl($videoId);
?>Video Components
Use Bunny.net videos in components:
php
<?php
$video = llField('bunny_video', $key);
if ($video) {
llBlock('video/bunny', ['fields' => ['video' => $video]]);
}
?>ACF Field Integration
Bunny.net provides ACF field integration:
php
<?php
// In component acf.php
$groupFields = [
[
'key' => $name . '_01',
'label' => 'Bunny Video',
'name' => 'bunny_video',
'type' => 'bunny_video', // Custom field type
],
];
?>Custom Integrations
Adding Custom Integrations
Create integration files in functions/:
php
<?php
// functions/custom-integration.php
function llCustomIntegration() {
// Integration logic
}
add_action('init', 'llCustomIntegration');Include in functions/bootstrap.php:
php
include_once $templateDirectory.'/functions/custom-integration.php';Third-Party APIs
Example: Integrating with external API:
php
<?php
function llFetchExternalData($endpoint) {
$response = wp_remote_get($endpoint, [
'timeout' => 30,
'headers' => [
'Authorization' => 'Bearer ' . get_option('api_token'),
],
]);
if (is_wp_error($response)) {
return false;
}
return json_decode(wp_remote_retrieve_body($response), true);
}
?>Advanced ACF Patterns
Dynamic Field Options
Populate field options dynamically:
php
<?php
function acf_populate_dynamic_options($field) {
$choices = [];
// Get options from database, API, etc.
$items = get_posts(['post_type' => 'custom_type']);
foreach ($items as $item) {
$choices[$item->ID] = $item->post_title;
}
$field['choices'] = $choices;
return $field;
}
add_filter('acf/load_field/name=dynamic_select', 'acf_populate_dynamic_options');Conditional Field Groups
Show/hide field groups based on conditions:
php
<?php
function acf_conditional_field_group($field_group) {
// Only show on specific post types
if (!in_array(get_post_type(), ['page', 'post'])) {
return false;
}
return $field_group;
}
add_filter('acf/get_field_groups', 'acf_conditional_field_group');Field Validation
Add custom field validation:
php
<?php
function acf_validate_custom_field($valid, $value, $field, $input) {
if (!$valid) {
return $valid;
}
// Custom validation logic
if ($field['name'] === 'email' && !is_email($value)) {
$valid = 'Please enter a valid email address';
}
return $valid;
}
add_filter('acf/validate_value/name=email', 'acf_validate_custom_field', 10, 4);Custom Post Types
Creating Post Types
Define post types in config/post-types.php:
php
<?php
return [
[
'name' => 'employee',
'label' => 'Employees',
'public' => true,
'has_archive' => true,
'supports' => ['title', 'editor', 'thumbnail'],
'menu_icon' => 'dashicons-groups',
],
];
?>Post Type Fields
Create fields in config/fields/:
php
<?php
// config/fields/employee.php
$key = 'employee_fields';
return [
'key' => $key,
'title' => 'Employee Information',
'type' => [
'post_type' => 'employee'
],
'fields' => [
// Field definitions
],
];
?>Querying Post Types
Query custom post types:
php
<?php
$employees = get_posts([
'post_type' => 'employee',
'posts_per_page' => -1,
'meta_query' => [
[
'key' => 'department',
'value' => 'engineering',
],
],
]);
?>Advanced JavaScript Patterns
Custom Event System
Create custom events:
javascript
import { app } from '@src/js/core/app'
export default class CustomComponent {
triggerCustomEvent = (data) => {
app.instances.get('eventManager').trigger('customEvent', {
component: this,
data: data
})
}
listenToEvent = () => {
app.instances.get('eventManager').on('customEvent', (eventData) => {
// Handle event
})
}
}Async Component Loading
Load components asynchronously:
javascript
export default class AsyncComponent {
constructor(element) {
this.element = element
this.loaded = false
this.init()
}
init = async () => {
await this.loadData()
this.render()
}
loadData = async () => {
const response = await fetch('/api/data')
this.data = await response.json()
this.loaded = true
}
render = () => {
if (this.loaded) {
// Render component
}
}
}Intersection Observer
Use Intersection Observer for performance:
javascript
export default class ObserverComponent {
constructor(element) {
this.element = element
this.observer = null
this.init()
}
init = () => {
this.createObserver()
}
createObserver = () => {
this.observer = new IntersectionObserver((entries) => {
entries.forEach(entry => {
if (entry.isIntersecting) {
this.handleIntersect()
}
})
}, {
threshold: 0.5
})
this.observer.observe(this.element)
}
handleIntersect = () => {
// Component is visible
}
destroy = () => {
if (this.observer) {
this.observer.disconnect()
}
}
}WordPress Hooks
Action Hooks
Use WordPress action hooks:
php
<?php
// In functions/custom.php
// Add custom action
function llCustomAction() {
// Custom logic
}
add_action('wp_head', 'llCustomAction');
// Modify existing action
function llModifyAction() {
// Modification logic
}
add_action('wp_footer', 'llModifyAction', 20); // Priority 20
?>Filter Hooks
Use WordPress filter hooks:
php
<?php
// Filter post content
function llFilterContent($content) {
// Modify content
return $content;
}
add_filter('the_content', 'llFilterContent');
// Filter ACF field value
function llFilterAcfField($value, $post_id, $field) {
// Modify field value
return $value;
}
add_filter('acf/load_value/name=my_field', 'llFilterAcfField', 10, 3);
?>Custom Hooks
Create custom hooks:
php
<?php
// Trigger custom action
do_action('ll_custom_action', $data);
// Apply custom filter
$filtered = apply_filters('ll_custom_filter', $data);
?>Best Practices
1. Error Handling
Always handle errors gracefully:
php
<?php
try {
$result = riskyOperation();
} catch (Exception $e) {
error_log($e->getMessage());
$result = false;
}
?>2. Caching
Cache expensive operations:
php
<?php
$cacheKey = 'expensive_operation_' . $id;
$result = wp_cache_get($cacheKey);
if (false === $result) {
$result = expensiveOperation();
wp_cache_set($cacheKey, $result, '', 3600);
}
?>3. Security
Always sanitize and validate:
php
<?php
// Sanitize input
$input = sanitize_text_field($_POST['input']);
// Validate
if (empty($input)) {
return false;
}
// Escape output
echo esc_html($output);
?>4. Performance
Optimize for performance:
- Use efficient queries
- Cache expensive operations
- Minimize database calls
- Use object caching
Related Documentation
- ACF Integration - ACF patterns
- JavaScript Architecture - JS patterns
- Performance Optimization - Performance
Next Steps:
- Review Common Patterns for patterns
- Check Examples & Recipes for examples
- Learn about Performance Optimization