'', 'class' => '', ]; } /** * Don't manage stock for licensed products */ public function managing_stock(): bool { return false; } /** * Check if variation is purchasable * Override to handle custom parent product type */ public function is_purchasable(): bool { // Check if variation exists if (!$this->exists()) { return false; } // Check parent product status $parentId = $this->get_parent_id(); $parentStatus = get_post_status($parentId); if ($parentStatus !== 'publish' && !current_user_can('edit_post', $parentId)) { return false; } // Check if variation has a price $price = $this->get_price(); if ($price === '' || $price === null) { return false; } return apply_filters('woocommerce_variation_is_purchasable', true, $this); } /** * Get max activations for this variation * Falls back to parent product, then to default settings */ public function get_max_activations(): int { // Check variation-specific setting first $value = $this->get_meta('_licensed_max_activations', true); if ($value !== '' && $value !== null) { return max(1, (int) $value); } // Fall back to parent product $parent = wc_get_product($this->get_parent_id()); if ($parent && method_exists($parent, 'get_max_activations')) { return $parent->get_max_activations(); } return SettingsController::getDefaultMaxActivations(); } /** * Check if variation has custom max activations set */ public function has_custom_max_activations(): bool { $value = $this->get_meta('_licensed_max_activations', true); return $value !== '' && $value !== null; } /** * Get validity days for this variation * This is the primary license setting that varies per variation * Falls back to parent product, then to default settings */ public function get_validity_days(): ?int { // Check variation-specific setting first $value = $this->get_meta('_licensed_validity_days', true); if ($value !== '' && $value !== null) { $days = (int) $value; // 0 means lifetime return $days > 0 ? $days : null; } // Fall back to parent product $parent = wc_get_product($this->get_parent_id()); if ($parent && method_exists($parent, 'get_validity_days')) { return $parent->get_validity_days(); } return SettingsController::getDefaultValidityDays(); } /** * Check if variation has custom validity days set */ public function has_custom_validity_days(): bool { $value = $this->get_meta('_licensed_validity_days', true); return $value !== '' && $value !== null; } /** * Check if license should be bound to major version * Falls back to parent product, then to default settings */ public function is_bound_to_version(): bool { // Check variation-specific setting first $value = $this->get_meta('_licensed_bind_to_version', true); if ($value !== '' && $value !== null) { return $value === 'yes'; } // Fall back to parent product $parent = wc_get_product($this->get_parent_id()); if ($parent && method_exists($parent, 'is_bound_to_version')) { return $parent->is_bound_to_version(); } return SettingsController::getDefaultBindToVersion(); } /** * Check if variation has custom bind to version setting */ public function has_custom_bind_to_version(): bool { $value = $this->get_meta('_licensed_bind_to_version', true); return $value !== '' && $value !== null; } /** * Get the license duration label for display */ public function get_license_duration_label(): string { $days = $this->get_validity_days(); if ($days === null) { return __('Lifetime', 'wc-licensed-product'); } if ($days === 30) { return __('Monthly', 'wc-licensed-product'); } if ($days === 90) { return __('Quarterly', 'wc-licensed-product'); } if ($days === 365) { return __('Yearly', 'wc-licensed-product'); } return sprintf( /* translators: %d: number of days */ _n('%d day', '%d days', $days, 'wc-licensed-product'), $days ); } /** * Get current software version from parent product */ public function get_current_version(): string { $parent = wc_get_product($this->get_parent_id()); if ($parent && method_exists($parent, 'get_current_version')) { return $parent->get_current_version(); } $versionManager = new VersionManager(); $latestVersion = $versionManager->getLatestVersion($this->get_parent_id()); return $latestVersion ? $latestVersion->getVersion() : ''; } /** * Get major version number from parent product */ public function get_major_version(): int { $parent = wc_get_product($this->get_parent_id()); if ($parent && method_exists($parent, 'get_major_version')) { return $parent->get_major_version(); } $versionManager = new VersionManager(); $latestVersion = $versionManager->getLatestVersion($this->get_parent_id()); if ($latestVersion) { return $latestVersion->getMajorVersion(); } return 1; } }