Tribe__Tickets_Plus__Commerce__WooCommerce__Main::generate_tickets( int $order_id )

Generates the tickets.

This happens only once, as soon as an order reaches a suitable status (which is set in the WooCommerce-specific ticket settings).


Parameters

$order_id

(int) (Required)


Top ↑

Source

File: src/Tribe/Commerce/WooCommerce/Main.php

	public function generate_tickets( $order_id ) {
		/**
		 * Hook before WooCommerce Tickets are generated in Event Tickets Plus.
		 *
		 * @since 4.10.4
		 *
		 * @param int $order_id The order ID.
		 */
		do_action( 'tribe_tickets_plus_woo_before_generate_tickets', $order_id );

		$order_status = get_post_status( $order_id );

		$generation_statuses = (array) tribe_get_option(
			'tickets-woo-generation-status',
			$this->settings->get_default_ticket_generation_statuses()
		);

		$dispatch_statuses = (array) tribe_get_option(
			'tickets-woo-dispatch-status',
			$this->settings->get_default_ticket_dispatch_statuses()
		);

		/**
		 * Filters the list of ticket order stati that should trigger the ticket generation.
		 *
		 * By default the WooCommerced default ones that will affect the ticket stock.
		 *
		 * @since 4.2
		 *
		 * @param array $generation_statuses
		 */
		$generation_statuses = (array) apply_filters( 'event_tickets_woo_ticket_generating_order_stati', $generation_statuses );

		/**
		 * Controls the list of order post statuses used to trigger dispatch of ticket emails.
		 *
		 * @since 4.2
		 *
		 * @param array $trigger_statuses order post statuses
		 */
		$dispatch_statuses = apply_filters( 'event_tickets_woo_complete_order_stati', $dispatch_statuses );

		$should_generate    = in_array( $order_status, $generation_statuses ) || in_array( 'immediate', $generation_statuses );
		$should_dispatch    = in_array( $order_status, $dispatch_statuses ) || in_array( 'immediate', $dispatch_statuses );
		$already_generated  = get_post_meta( $order_id, $this->order_has_tickets, true );
		$already_dispatched = get_post_meta( $order_id, $this->mail_sent_meta_key, true );

		$has_tickets = false;

		// Get the items purchased in this order
		$order       = new WC_Order( $order_id );
		$order_items = $order->get_items();

		// Bail if the order is empty
		if ( empty( $order_items ) ) {
			return;
		}

		// Iterate over each product
		foreach ( (array) $order_items as $item_id => $item ) {
			// order attendee IDs in the meta are per ticket type
			$order_attendee_id = 0;

			$product = $this->get_product_from_item( $order, $item );

			if ( empty( $product ) ) {
				continue;
			}

			$product_id = $this->get_product_id( $product );

			// Check if the order item contains attendee optout information
			$optout_data = isset( $item['item_meta'][ $this->attendee_optout_key ] )
				? $item['item_meta'][ $this->attendee_optout_key ]
				: false;

			$optout = is_array( $optout_data )
				? (bool) reset( $optout_data ) // WC 2.x
				: (bool) $optout_data;         // WC 3.x

			// Get the event this ticket is for
			$post_id = (int) get_post_meta( $product_id, $this->event_key, true );

			$quantity = empty( $item['qty'] ) ? 0 : intval( $item['qty'] );

			if ( ! empty( $post_id ) ) {

				$has_tickets = true;

				if ( $already_generated || ! $should_generate ) {
					break;
				}

				// Iterate over all the amount of tickets purchased (for this product)
				$quantity = (int) $item['qty'];

				/** @var Tribe__Tickets__Commerce__Currency $currency */
				$currency        = tribe( 'tickets.commerce.currency' );
				$currency_symbol = $currency->get_currency_symbol( $product_id, true );

				for ( $i = 0; $i < $quantity; $i++ ) {

					$attendee = array(
						'post_status' => 'publish',
						'post_title'  => $order_id . ' | ' . $item['name'] . ' | ' . ( $i + 1 ),
						'post_type'   => $this->attendee_object,
						'ping_status' => 'closed',
					);

					// Insert individual ticket purchased
					$attendee = apply_filters( 'wootickets_attendee_insert_args', $attendee, $order_id, $product_id, $post_id );

					if ( $attendee_id = wp_insert_post( $attendee ) ) {
						update_post_meta( $attendee_id, self::ATTENDEE_PRODUCT_KEY, $product_id );
						update_post_meta( $attendee_id, self::ATTENDEE_ORDER_KEY, $order_id );
						update_post_meta( $attendee_id, $this->attendee_order_item_key, $item_id );
						update_post_meta( $attendee_id, self::ATTENDEE_EVENT_KEY, $post_id );
						update_post_meta( $attendee_id, self::ATTENDEE_OPTOUT_KEY, $optout );
						update_post_meta( $attendee_id, $this->security_code, $this->generate_security_code( $order_id, $attendee_id ) );
						update_post_meta( $attendee_id, '_paid_price', $this->get_price_value( $product_id ) );
						update_post_meta( $attendee_id, '_price_currency_symbol', $currency_symbol );

						/**
						 * WooCommerce-specific action fired when a WooCommerce-driven attendee ticket for an event is generated
						 *
						 * @param $attendee_id ID of attendee ticket
						 * @param $post_id    ID of event
						 * @param $order       WooCommerce order
						 * @param $product_id  WooCommerce product ID
						 */
						do_action( 'event_ticket_woo_attendee_created', $attendee_id, $post_id, $order, $product_id );

						/**
						 * Action fired when an attendee ticket is generated
						 *
						 * @param int $attendee_id       ID of attendee ticket
						 * @param int $order_id          WooCommerce order ID
						 * @param int $product_id        Product ID attendee is "purchasing"
						 * @param int $order_attendee_id Attendee # for order
						 */
						do_action( 'event_tickets_woocommerce_ticket_created', $attendee_id, $order_id, $product_id, $order_attendee_id );

						$customer_id = method_exists( $order, 'get_customer_id' )
							? $order->get_customer_id()  // WC 3.x
							: $order->customer_user; // WC 2.2.x

						$this->record_attendee_user_id( $attendee_id, $customer_id );
						$order_attendee_id++;
					}
				}
			}

			if ( ! $already_generated && $should_generate ) {
				if ( ! isset( $quantity ) ) {
					$quantity = null;
				}
				/**
				 * Action fired when a WooCommerce has had attendee tickets generated for it
				 *
				 * @param int $product_id RSVP ticket post ID
				 * @param int $order_id   ID of the WooCommerce order
				 * @param int $quantity   Quantity ordered
				 * @param int $post_id    ID of event
				 */
				do_action( 'event_tickets_woocommerce_tickets_generated_for_product', $product_id, $order_id, $quantity, $post_id );

				update_post_meta( $order_id, $this->order_has_tickets, '1' );
			}
		}

		// Disallow the dispatch of emails before attendees have been created
		$attendees_generated = $already_generated || $order_attendee_id;

		if ( $has_tickets && $attendees_generated && ! $already_dispatched && $should_dispatch ) {
			$this->complete_order( $order_id );
		}

		if ( ! $already_generated && $should_generate ) {
			/**
			 * Action fired when a WooCommerce attendee tickets have been generated
			 *
			 * @param $order_id ID of the WooCommerce order
			 */
			do_action( 'event_tickets_woocommerce_tickets_generated', $order_id );
		}
	}