Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 12 additions & 10 deletions docs/calendar-block.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@ The Calendar block renders a Carousel List of events with progressive enhancemen

## Server Templates & Helpers

- `event-item.php`, `date-group.php`, `navigation.php`, `pagination.php`, `results-counter.php`, `no-events.php`, `filter-bar.php`, `time-gap-separator.php`, and `modal/taxonomy-filter.php` live under `inc/Blocks/Calendar/templates` and are orchestrated by `inc/Core/Template_Loader`.
- `inc/Core/Taxonomy_Helper` builds hierarchical term data and counts for each template, while `Taxonomy_Badges` renders badge markup that respects `data_machine_events_badge_wrapper_classes`, `data_machine_events_badge_classes`, and `data_machine_events_more_info_button_classes` filters.
- `event-item.php`, `date-group.php`, `navigation.php`, `pagination.php`, `results-counter.php`, `no-events.php`, `filter-bar.php`, `time-gap-separator.php`, and `modal/taxonomy-filter.php` live under `inc/Blocks/Calendar/templates` and are orchestrated by `inc/Blocks/Calendar/Template_Loader.php`.
- `inc/Blocks/Calendar/Taxonomy_Helper.php` builds hierarchical term data and counts for each template, while `Taxonomy_Badges` renders badge markup that respects `data_machine_events_badge_wrapper_classes`, `data_machine_events_badge_classes`, and `data_machine_events_more_info_button_classes` filters.
- The filter modal uses taxonomy helpers to surface dynamic dependencies, counts, and active state indicators before handing control to the filter modal module.

## REST API Support
Expand All @@ -23,14 +23,16 @@ The Calendar block renders a Carousel List of events with progressive enhancemen

## JavaScript Modules

- `inc/Blocks/Calendar/src/frontend.js` bootstraps each `.data-machine-events-calendar`, wiring the following modules:
- `modules/api-client.js` handles REST requests and swaps fragments.
- `modules/carousel.js` detects overflow, updates dots, and powers chevrons (with click-and-hold support).
- `modules/date-picker.js` integrates Flatpickr for date range filters.
- `modules/filter-modal.js` keeps the taxonomy modal accessible and debounced when filters change.
- `modules/filter-state.js` centralizes filter state management across URL params, localStorage, and DOM with regex support for both indexed (`tax_filter[taxonomy][0]`) and non-indexed (`tax_filter[taxonomy][]`) array syntax.
- `modules/navigation.js` powers past/upcoming toggles, calendar navigation, and pagination link handling.
- `modules/state.js` serializes query parameters, manages history state, and debounces search input.
- `inc/Blocks/Calendar/src/frontend.ts` bootstraps each `.data-machine-events-calendar`, wiring the following modules:
- `modules/api-client.ts` handles REST requests and swaps fragments.
- `modules/carousel.ts` detects overflow, updates dots, and powers chevrons (with click-and-hold support).
- `modules/date-picker.ts` integrates Flatpickr for date range filters.
- `modules/day-loader.ts` loads events for a specific date, used by the carousel for on-demand day rendering.
- `modules/filter-modal.ts` keeps the taxonomy modal accessible and debounced when filters change.
- `modules/filter-state.ts` centralizes filter state management across URL params, localStorage, and DOM with regex support for both indexed (`tax_filter[taxonomy][0]`) and non-indexed (`tax_filter[taxonomy][]`) array syntax.
- `modules/geo-sync.ts` handles browser geolocation for nearest-event sorting and the blue dot indicator.
- `modules/lazy-render.ts` defers calendar rendering until the block scrolls into view.
- `modules/navigation.ts` powers past/upcoming toggles, calendar navigation, and pagination link handling.

## Filter Modal & Taxonomy Helpers

Expand Down
103 changes: 16 additions & 87 deletions docs/eventbrite-handler.md
Original file line number Diff line number Diff line change
@@ -1,105 +1,34 @@
# Eventbrite Handler
# Eventbrite Handler (Deprecated)

Import events from public Eventbrite organizer pages via Schema.org JSON-LD extraction.
This handler has been consolidated into the Universal Web Scraper as the `EventbriteExtractor`.

## Overview
Previously the handler lived at `inc/Steps/EventImport/Handlers/Eventbrite/Eventbrite.php` with `EventbriteSettings`. That standalone handler and its settings were removed; existing flows should migrate to the scraper-based extractor by reconfiguring the fetch step to use the `UniversalWebScraper` handler, which auto-detects Eventbrite organizer and event pages.

The Eventbrite handler parses public Eventbrite organizer pages to extract events from embedded JSON-LD structured data. No API key or authentication is required - events are extracted directly from the public HTML page.
See `docs/universal-web-scraper-handler.md` for extraction behavior and `inc/Steps/EventImport/Handlers/WebScraper/Extractors/EventbriteExtractor.php` for the implementation.

## Features
## Migration

### JSON-LD Extraction
- **Schema.org Parsing**: Extracts Event schema from `<script type="application/ld+json">` tags
- **ItemList Support**: Handles both individual Event objects and ItemList containers
- **Complete Metadata**: Extracts venue, pricing, performer, and image data
The `EventbriteExtractor` (since v0.15.5) parses Eventbrite pages by:

### Configuration Options
- **organizer_url**: Full Eventbrite organizer page URL (required)
- **date_range**: Number of days into the future to import (default: 90)
1. Detecting `eventbrite.com/o/` or `eventbrite.com/e/` URLs (or `evbuc.com` short links) in the page HTML.
2. Extracting **all** events from `ItemList` JSON-LD on organizer pages (not just the first event).
3. Handling individual event pages with a direct `Event` JSON-LD object.

## Usage

### Configuration
```php
$config = [
'organizer_url' => 'https://www.eventbrite.com/o/lo-fi-brewing-14959647606',
'date_range' => 90
];
```

### Example Organizer URLs
- `https://www.eventbrite.com/o/lo-fi-brewing-14959647606`
- `https://www.eventbrite.com/o/your-organizer-name-12345678`
No configuration changes are needed — the extractor auto-detects Eventbrite pages from the `source_url`.

## Data Mapping

### Eventbrite Schema.org to Event Details Block
The extractor preserves the same Schema.org field mapping:

| Eventbrite Field | Event Details Attribute |
|------------------|------------------------|
| Eventbrite JSON-LD Field | Event Details Attribute |
|--------------------------|------------------------|
| `name` | title |
| `startDate` | startDate, startTime |
| `endDate` | endDate, endTime |
| `startDate` / `endDate` | date/time fields |
| `description` | description |
| `location.name` | venue |
| `location.address.streetAddress` | venueAddress |
| `location.address.addressLocality` | venueCity |
| `location.address.addressRegion` | venueState |
| `location.address.postalCode` | venueZip |
| `location.address.addressCountry` | venueCountry |
| `location.geo` | venueCoordinates |
| `location.address.*` | venue address components |
| `location.geo` | venue coordinates |
| `offers.lowPrice` / `offers.highPrice` | price |
| `url` | ticketUrl |
| `performer.name` | artist |
| `image` | imageUrl |

## Integration

### EventIdentifierGenerator
Uses `EventIdentifierGenerator::generate()` for consistent event identity:
```php
$event_identifier = EventIdentifierGenerator::generate(
$standardized_event['title'],
$standardized_event['startDate'],
$standardized_event['venue']
);
```

### Single-Item Processing
Processes one event per job execution with duplicate prevention via ProcessedItems tracking.

### Venue Metadata
Complete venue metadata extraction including:
- Address components (street, city, state, zip, country)
- Geographic coordinates
- Phone and website (when available)

## Handler Registration

Uses `HandlerRegistrationTrait` for self-registration:
```php
self::registerHandler(
'eventbrite',
'event_import',
self::class,
__('Eventbrite Events', 'data-machine-events'),
__('Import events from any public Eventbrite organizer page via JSON-LD extraction', 'data-machine-events'),
false,
null,
EventbriteSettings::class,
null
);
```

## Advantages

- **No API Key Required**: Works with public organizer pages only
- **Schema.org Standard**: Leverages structured data that Eventbrite maintains for SEO
- **Complete Data**: Extracts venue, pricing, performer, and image information
- **Date Range Filtering**: Configurable future date window for imports

## Limitations

- Only works with public organizer pages
- Depends on Eventbrite's JSON-LD structure (standard Schema.org format)
- Cannot access private or draft events
173 changes: 23 additions & 150 deletions docs/ics-calendar-handler.md
Original file line number Diff line number Diff line change
@@ -1,162 +1,35 @@
# ICS Calendar Handler
# ICS Calendar Handler (Deprecated)

Generic ICS/iCal feed integration for importing events from any calendar feed supporting the ICS format.
This handler has been consolidated into the Universal Web Scraper as the `IcsExtractor`.

## Overview
Previously the handler lived at `inc/Steps/EventImport/Handlers/IcsCalendar/IcsCalendar.php` with `IcsCalendarSettings.php`. That standalone handler and its settings were removed; existing flows should migrate to the scraper-based extractor by reconfiguring the fetch step to use the `UniversalWebScraper` handler.

The ICS Calendar handler provides comprehensive support for importing events from any ICS (iCalendar) feed, including popular platforms like Tockify, Outlook, Apple Calendar, and Google Calendar ICS exports. Features automatic protocol conversion, venue override options, and keyword filtering.
See `docs/universal-web-scraper-handler.md` for extraction behavior and `inc/Steps/EventImport/Handlers/WebScraper/Extractors/IcsExtractor.php` for the implementation.

## Features
## Migration

### Calendar Feed Support
- **Universal ICS Support**: Works with any ICS/iCal feed URL
- **Protocol Conversion**: Automatic `webcal://` to `https://` conversion
- **Multiple Platforms**: Supports Tockify, Outlook, Apple Calendar, Google Calendar exports, and custom ICS feeds
The `IcsExtractor` handles ICS/iCal feeds within the Universal Web Scraper:

### Venue Management
- **Venue Override**: Optional venue name override for consistent venue assignment
- **Address Override**: Venue address override for accurate location data
- **Automatic Venue Creation**: Creates venues with complete metadata when overrides are provided

### Event Filtering
- **Keyword Filtering**: Include/exclude keywords to filter relevant events
- **Case-Insensitive Matching**: Flexible keyword matching in event titles and descriptions
- **Multiple Keywords**: Support for comma-separated keyword lists

### Technical Features
- **Single-Item Processing**: Processes one event per job execution with duplicate prevention
- **Event Identifier Generation**: Uses EventIdentifierGenerator for consistent event identity
- **Processed Items Tracking**: Prevents duplicate imports using Data Machine's processed items system
1. Detects ICS feeds by URL extension (`.ics`) or `webcal://` protocol.
2. Converts `webcal://` to `https://` automatically.
3. Parses VEVENT components using the `johngrogg/ics-parser` library.
4. Applies keyword filtering and venue overrides via standard handler settings.
5. Supports RRULE recurring events, EXDATE exception dates, and RDATE additional dates.

## Configuration

### Required Settings
- **ICS URL**: The URL of the ICS feed to import from
- **Venue Name Override** (optional): Override venue names for consistent assignment
- **Venue Address Override** (optional): Override venue addresses for accurate geocoding

### Optional Settings
- **Include Keywords**: Comma-separated keywords to include (events must contain at least one)
- **Exclude Keywords**: Comma-separated keywords to exclude (events containing these are skipped)

## Usage Examples

### Basic ICS Import
```php
$config = [
'ics_url' => 'https://example.com/calendar.ics',
'venue_name_override' => 'Custom Venue Name',
'venue_address_override' => '123 Main St, City, State 12345'
];
```

### Filtered Import
```php
$config = [
'ics_url' => 'https://calendar.google.com/calendar/ical/.../basic.ics',
'search' => 'concert,music,jazz',
'exclude_keywords' => 'cancelled,postponed'
];
```

### WebCal Protocol
```php
$config = [
'ics_url' => 'webcal://example.com/calendar.ics' // Automatically converted to https://
];
```

## Event Processing

### Data Mapping
- **Title**: Event summary from ICS VEVENT
- **Start/End Dates**: DTSTART/DTEND from ICS event
- **Description**: Event description from ICS DESCRIPTION
- **Location**: Venue information from ICS LOCATION (overridden if configured)
- **Time Zone**: Respects ICS timezone information

### Duplicate Prevention
```php
use DataMachineEvents\Utilities\EventIdentifierGenerator;

// Generate consistent identifier
$event_identifier = EventIdentifierGenerator::generate($title, $startDate, $venue);

// Check if already processed
if (apply_filters('datamachine_is_item_processed', false, $flow_step_id, 'ics_calendar', $event_identifier)) {
continue;
}

// Mark as processed
do_action('datamachine_mark_item_processed', $flow_step_id, 'ics_calendar', $event_identifier, $job_id);
```

## Integration Architecture

### Handler Structure
- **IcsCalendar.php**: Main import handler with ICS parsing and event processing
- **IcsCalendarSettings.php**: Admin interface and configuration forms
- **johngrogg/ics-parser**: PHP library for reliable ICS parsing

### Data Flow
1. **Feed Retrieval**: Downloads ICS feed from configured URL
2. **Protocol Conversion**: Converts webcal:// to https:// if needed
3. **ICS Parsing**: Parses VEVENT components using ics-parser library
4. **Event Filtering**: Applies include/exclude keyword filtering
5. **Venue Processing**: Applies venue overrides or extracts from event location
6. **Event Mapping**: Converts ICS data to Data Machine event structure
7. **Duplicate Check**: Uses EventIdentifierGenerator for identity verification
8. **Event Upsert**: Creates/updates events using EventUpsert handler

## Supported ICS Features

### Event Properties
- **SUMMARY**: Event title
- **DESCRIPTION**: Event description
- **DTSTART/DTEND**: Event start and end times
- **LOCATION**: Venue information
- **TZID**: Timezone information

### Recurring Events
- **RRULE**: Recurrence rules (expanded to individual events)
- **EXDATE**: Exception dates
- **RDATE**: Additional recurrence dates

## Error Handling

### Feed Errors
- **Invalid URL**: Clear error messages for malformed URLs
- **Network Errors**: Timeout and connection error handling
- **Parse Errors**: Malformed ICS file detection

### Configuration Errors
- **Missing URL**: Validation for required ICS URL
- **Invalid Keywords**: Warning for malformed keyword lists

## Performance Considerations

### Feed Size Limits
- **Memory Usage**: Efficient parsing of large ICS feeds
- **Processing Limits**: Single-item processing prevents timeouts
- **Batch Handling**: Handles feeds with hundreds of events

### Optimization Features
- **Incremental Processing**: Only processes new/changed events
- **Caching**: Feed content caching for repeated imports
- **Error Recovery**: Continues processing after individual event errors

## Troubleshooting
When using the Universal Web Scraper with an ICS feed:

### Common Issues
- **WebCal Links**: Ensure webcal:// URLs are accessible (may need manual conversion)
- **Timezone Issues**: Verify ICS feed timezone settings
- **Large Feeds**: Consider date range limiting for very large calendars
- **Encoding Problems**: Check ICS file encoding (UTF-8 recommended)
- **`source_url`**: The ICS feed URL (`.ics` or `webcal://` links)
- **`search` / `exclude_keywords`**: Comma-separated filters applied before normalization
- **Venue override fields**: Available via `VenueFieldsTrait` in handler settings

### Debug Information
- **Feed Validation**: Test ICS URL accessibility
- **Event Parsing**: Review parsed event data structure
- **Filter Matching**: Verify keyword filtering logic
- **Venue Assignment**: Check venue override application
## Data Mapping

The ICS Calendar handler provides flexible, reliable event import from any ICS-compatible calendar feed with comprehensive filtering and venue management capabilities.
| ICS Property | Event Details Attribute |
|--------------|------------------------|
| `SUMMARY` | title |
| `DESCRIPTION` | description |
| `DTSTART` / `DTEND` | start/end dates and times |
| `LOCATION` | venue |
| `TZID` | timezone |
Loading
Loading