wordpress-activitypub-event.../activitypub/object/class-event.php

250 lines
6.4 KiB
PHP
Raw Normal View History

<?php
/**
* ActivityPub Transformer for VS Event.
*
* This is a file doc comments.
*
* @package activity-event-transformers
*/
use function Activitypub\snake_to_camel_case;
/**
* Event is an implementation of one of the
* Activity Streams Event object type
*
* The Object is the primary base type for the Activity Streams
* vocabulary.
*
* @see https://www.w3.org/TR/activitystreams-vocabulary/#dfn-event
*/
class Event extends \Activitypub\Activity\Base_Object {
const REPLIES_MODERATION_OPTION_TYPES = [ 'allow_all', 'closed'];
const JOIN_MODE_TYPES = [ 'free', 'restricted', 'external'];
/**
* Event is an implementation of one of the
* Activity Streams
*
* @var string
*/
protected $type = 'Event';
/**
* Extension invented by PeerTube whether comments/replies are <enabled>
* Mobilizon also implemented this as a fallback to their own
* repliesModerationOption.
*
* @context https://joinpeertube.org/commentsEnabled
* @see https://docs.joinpeertube.org/api/activitypub#video
* @see https://docs.joinmobilizon.org/contribute/activity_pub/
* @var bool
*/
protected $comments_enabled;
/**
* @context https://joinmobilizon.org/timezone
* @var string
*/
protected $timezone;
/**
* @context https://joinmobilizon.org/repliesModerationOption
* @see https://docs.joinmobilizon.org/contribute/activity_pub/#repliesmoderation
* @var string
*/
protected $replies_moderation_option;
/**
* @context https://joinmobilizon/anonymousParticipationEnabled
* @see https://docs.joinmobilizon.org/contribute/activity_pub/#anonymousparticipationenabled
* @var bool
*/
protected $anonymous_participation_enabled;
/**
* @context https://schema.org/category
* @var enum
*/
protected $category;
/**
* @context https://schema.org/inLanguage
* @var
*/
protected $in_language;
/**
* @context https://joinmobilizon.org/isOnline
* @var bool
*/
protected $is_online;
/**
* @context http://www.w3.org/2002/12/cal/ical#
* @var enum
*/
protected $ical_status;
/**
* @context https://joinmobilizon.org/externalParticipationUrl
* @var string
*/
protected $external_participation_url;
/**
* @context https://joinmobilizon.org/joinMode
* @see https://docs.joinmobilizon.org/contribute/activity_pub/#joinmode
* @var
*/
protected $join_mode;
/**
* @context https://joinmobilizon.org/participantCount
* @var int
*/
protected $participant_count;
/**
* @context https://schema.org/maximumAttendeeCapacity
* @see https://docs.joinmobilizon.org/contribute/activity_pub/#maximumattendeecapacity
* @var int
*/
protected $maximum_attendee_capacity;
/**
* Setter function that makes sure, we only set valid replies moderation options.
* @param string $value
*/
public function set_replies_moderation_option( $value ) {
if ( in_array( $value, self::REPLIES_MODERATION_OPTION_TYPES, true ) ) {
$this->replies_moderation_option = $value;
}
return $this;
}
/**
* @param array $array The array version of an object of this class.
*/
private function rename_ical_status_key( $array ) {
$array[ 'ical:status' ] = $array[ 'icalStatus' ];
unset( $array[ 'icalStatus' ] );
}
/**
* @param array $array The array version of an object of this class.
*/
public function rename_array_keys( $array ) {
if ( isset( $array[ 'icalStatus' ] ) ) {
$array = rename_ical_status_key( $array );
}
return $array;
}
/**
* Get the context information for a property.
*
* @param string $property
*
* @return array|null
*/
private function get_property_context( string $property ) {
$reflection_class = new ReflectionClass( $this );
if ( $reflection_class->hasProperty( $property ) ) {
$reflection_property = $reflection_class->getProperty( $property );
$doc_omment = $reflection_property->getDocComment();
// Extract context information from the doc comment.
preg_match( '/@context\s+([^\s]+)/', $doc_omment, $matches );
if ( !empty( $matches[1] ) ) {
return $matches[1];
} else {
return 'https://www.w3.org/ns/activitystreams';
}
}
return null;
}
public function filter_context( $context ) {
if ( isset( $this->replies_moderation_option ) ) {
$replies_moderation_option_context = $this->get_property_context( 'replies_moderation_option' );
}
return $context;
}
private static function compact_context( $key_context, $namespace, $abbreviation ) {
$abbreviation_added = false;
foreach ( $key_context as $key => $value ) {
// Check if the key starts with "https://joinpeertube.org/"
if ( strpos( $value, $namespace ) === 0 ) {
// Replace the key
$key_context[ $key ] = $abbreviation . ':' . substr($value, strlen( $namespace ));
// Add "pt" element only once
if ( ! $abbreviation_added ) {
$key_context = [ $abbreviation => $namespace . '/ns#' ] + $key_context;
$abbreviation_added = true;
}
}
}
return $key_context;
}
public static function get_context() {
$class = self::class;
$transient = "activitypub_context_object_{$class}";
$context = get_transient($transient);
if ( $context ) {
return $context;
}
$reflection_class = new ReflectionClass( self::class );
$context = array(
'https://www.w3.org/ns/activitystreams',
'https://w3id.org/security/v1',
);
$key_context = [];
foreach ( $reflection_class->getProperties() as $property ) {
$doc_omment = $property->getDocComment();
// Extract context information from the doc comment.
preg_match( '/@context\s+([^\s]+)/', $doc_omment, $matches );
if ( !empty( $matches[1] ) ) {
$key_context[ snake_to_camel_case( $property->name ) ] = $matches[1];
}
}
$namespace_abbreviations = array(
'https://joinpeertube.org/' => 'pt',
'https://joinmobilizon.org/' => 'mz',
'https://schema.org/' => 'sc'
);
foreach ( $namespace_abbreviations as $namespace => $abbreviation ) {
$key_context = self::compact_context( $key_context, $namespace, $abbreviation );
}
$context[] = $key_context;
set_transient( $transient, $context );
return $context;
}
/**
* When using this class we need to add some filters.
*/
public function __construct() {
$class = get_class( $this );
$class = 'event';
add_filter( "activitypub_activity_{$class}_object_array", [ $this, 'rename_array_keys' ] );
add_filter( 'activitypub_json_context', [ $this, 'filter_context' ] );
}
}