Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Behebe "Alle" Option verfügbar für CB Manager #1306

Draft
wants to merge 42 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
42 commits
Select commit Hold shift + click to select a range
736e291
Changed none to "all" option for Restrictions
hansmorb Jul 9, 2023
3376208
Merge branch 'master' into bugfix/issue-1273
hansmorb Jul 12, 2023
e27dcb9
added tests for option sanitization and getting "All" option key
hansmorb Jul 12, 2023
c9f0a9e
fixed unit tests run unnecessarily
hansmorb Jul 12, 2023
2611930
Simplify comment
datengraben Aug 20, 2023
d529725
Add restriction migration
datengraben Aug 20, 2023
de24f14
Merge branch 'master' into bugfix/issue-1273
hansmorb Sep 19, 2023
245aa0c
Revert "Add restriction migration"
hansmorb Sep 20, 2023
9fdac64
added proper migration function #1273 and re-wrote upgrade methods
hansmorb Sep 20, 2023
c001356
added restriction validation upon post-save
hansmorb Sep 25, 2023
40594fb
fixed wrong constant used in some unit tests
hansmorb Sep 25, 2023
4b7825d
fixed expected returns for meta value "all" in all places
hansmorb Sep 25, 2023
3b0852e
added unit test for getByTimerange
hansmorb Sep 24, 2023
ad3c1b6
removed stuff left-over from cherry-pick
hansmorb Sep 25, 2023
d5395b6
merge master
hansmorb Oct 2, 2023
8d0c20a
only allow administrators to set restrictions for all items / locations
hansmorb Oct 2, 2023
c928e3b
only run validation upon publication of post
hansmorb Oct 2, 2023
4ea15f5
Merge branch 'master' into bugfix/issue-1273
hansmorb Oct 19, 2023
b8c67b8
Merge branch 'master' into bugfix/issue-1273
hansmorb Oct 22, 2023
402cd6f
safe-remove unused function after merge
hansmorb Oct 22, 2023
6cc8fc8
Merge branch 'master' into bugfix/issue-1273
hansmorb Oct 22, 2023
9766209
fixed var name for test
hansmorb Oct 22, 2023
161b5f5
fixed annotation
hansmorb Oct 26, 2023
e38ed95
re-added tests
hansmorb Oct 26, 2023
4905afc
added more annotations
hansmorb Oct 26, 2023
8fc4ef5
refactored filterPosts (removed support for empty item / location field)
hansmorb Oct 26, 2023
960b8d3
re-wrote upgrade methods
hansmorb Sep 21, 2023
ee75aab
removed test for function that does not exist (yet)
hansmorb Oct 26, 2023
0de13d1
Merge branch 'refactoring/upgrade' into bugfix/issue-1273
hansmorb Oct 26, 2023
e974b3d
removed function that has been moved
hansmorb Oct 26, 2023
70c9b12
Merge branch 'refactoring/upgrade' into bugfix/issue-1273
hansmorb Oct 26, 2023
88fedba
added task that we missed
hansmorb Oct 26, 2023
f20ef13
added PHPdocs
hansmorb Oct 26, 2023
2c4fbd6
fixed syntax for new installations
hansmorb Oct 26, 2023
dbfe232
added more comments
hansmorb Oct 26, 2023
fed0699
Fix phpcs issues on new file
datengraben Oct 27, 2023
8204702
removes import and adds type annotation
datengraben Oct 27, 2023
04f5310
Add comments/phpdoc
datengraben Oct 27, 2023
d1ddb09
Merge branch 'refactoring/upgrade' into bugfix/issue-1273
hansmorb Oct 27, 2023
eaff0e9
Merge branch 'master' into bugfix/issue-1273
hansmorb Oct 30, 2023
e388287
clean up changelist
hansmorb Oct 30, 2023
b4d3932
Merge branch 'master' into bugfix/issue-1273
hansmorb Jan 4, 2024
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
10 changes: 10 additions & 0 deletions src/Exception/RestrictionInvalidException.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
<?php

namespace CommonsBooking\Exception;

class RestrictionInvalidException extends \Exception
{
public function __construct( $message ) {
parent::__construct( __('Invalid restriction settings: ','commonsbooking') . $message . __( ' Restriction is saved as draft.', 'commonsbooking' ) );
}
}
12 changes: 6 additions & 6 deletions src/Helper/Wordpress.php
Original file line number Diff line number Diff line change
Expand Up @@ -193,16 +193,16 @@ public static function getRelatedPostsIdsForRestriction($postId): array {
$relatedPostIds = [ $postId ];

// Item and related timeframes
if($itemId = $restriction->getItemId()) {
$timeframes = \CommonsBooking\Repository\Timeframe::get([], [$itemId]);
$relatedPostIds[] = $itemId;
if($itemIds = $restriction->getItemIds()) {
$timeframes = \CommonsBooking\Repository\Timeframe::get([], $itemIds);
$relatedPostIds = array_merge($relatedPostIds,$itemIds);
$relatedPostIds = array_merge($relatedPostIds, Wordpress::getPostIdArray($timeframes));
}

// Location and related timeframes
if($locationId = $restriction->getLocationId()) {
$timeframes = \CommonsBooking\Repository\Timeframe::get([$locationId]);
$relatedPostIds[] = $locationId;
if($locationIds = $restriction->getLocationIds()) {
$timeframes = \CommonsBooking\Repository\Timeframe::get($locationIds);
$relatedPostIds = array_merge($relatedPostIds,$locationIds);
$relatedPostIds = array_merge($relatedPostIds, Wordpress::getPostIdArray($timeframes));
}

Expand Down
2 changes: 2 additions & 0 deletions src/Model/Item.php
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,8 @@ public function getAdmins() {
* Returns all applicable restrictions for this item.
*
* This function is not used anywhere yet.
* WARNING: This function is partially broken, the \CommonsBooking\Repository\Restriction::get
* will only return restrictions that apply to all items, when the $locations or $items parameter is left empty.
* @return array
* @throws Exception
*/
Expand Down
3 changes: 3 additions & 0 deletions src/Model/Location.php
Original file line number Diff line number Diff line change
Expand Up @@ -246,6 +246,9 @@ public function getAdmins() {
/**
* Will get the currently applicable restrictions for the location.
*
* This function is not used anywhere yet.
* WARNING: This function is partially broken, the \CommonsBooking\Repository\Restriction::get
* will only return restrictions that apply to all items, when the $locations or $items parameter is left empty.
* @return Restriction[]
* @throws \Exception
*/
Expand Down
73 changes: 62 additions & 11 deletions src/Model/Restriction.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,11 @@

namespace CommonsBooking\Model;

use CommonsBooking\Exception\RestrictionInvalidException;
use CommonsBooking\Helper\Wordpress;
use CommonsBooking\Helper\Helper;
use CommonsBooking\Messages\RestrictionMessage;
use CommonsBooking\Wordpress\CustomPostType\CustomPostType;
use DateTime;

/**
Expand All @@ -20,6 +22,7 @@
*/
class Restriction extends CustomPost {

public const ERROR_TYPE = 'restrictionValidationFailed';
/**
* Referred to in the frontend as "total breakdown".
* This means, that the item is not available for booking and that all corresponding bookings will be cancelled.
Expand Down Expand Up @@ -235,50 +238,68 @@ public function getEndDateDateTime(): DateTime {

/**
* Returns item name for the item that is restricted.
*
* @deprecated: This is not used anywhere in the code. Besides, the function is broken since it does not consider the case where multiple items are selected.
*
* @return string
*/
public function getItemName(): string {
$itemName = esc_html__( 'Not set', 'commonsbooking' );
if ( $this->getItemId() ) {
$item = get_post( $this->getItemId() );
if ( $this->getItemIds() ) {
$item = get_post( $this->getItemIds() );
$itemName = $item->post_title;
}

return $itemName;
}

/**
* Returns itemId for the item that is restricted.
* Gets all of the itemIDs that this restriction applies to.
*
* @return mixed
* @return int[]
*/
public function getItemId() {
return $this->getMeta( self::META_ITEM_ID );
public function getItemIds(): array {
$metaField = $this->getMeta( self::META_ITEM_ID );
if ( is_numeric( $metaField ) ) {
return [ $metaField ];
} elseif ( $metaField == CustomPostType::SELECTION_ALL_POSTS ) {
return Wordpress::getPostIdArray( \CommonsBooking\Repository\Item::get());
} else {
return [];
}
}

/**
* Returns location name for the location that the restricted item is in.
*
* DEPRECATED: This is not used anywhere in the code. Besides, the function is broken since it does not consider the case where multiple locations are selected.
*
* @return string
*/
public function getLocationName(): string {
$locationName = esc_html__( 'Not set', 'commonsbooking' );
if ( $this->getLocationId() ) {
$location = get_post( $this->getLocationId() );
if ( $this->getLocationIds() ) {
$location = get_post( $this->getLocationIds() );
$locationName = $location->post_title;
}

return $locationName;
}

/**
* Returns location id for the location that the restricted item is in.
* Gets all of the locationIDs that this restriction applies to.
*
* @return mixed
*/
public function getLocationId() {
return $this->getMeta( self::META_LOCATION_ID );
public function getLocationIds() {
$metaField = $this->getMeta( self::META_LOCATION_ID );
if ( is_numeric( $metaField ) ) {
return [ $metaField ];
} elseif ( $metaField == CustomPostType::SELECTION_ALL_POSTS ) {
return Wordpress::getPostIdArray( \CommonsBooking\Repository\Location::get());
} else {
return [];
}
}

/**
Expand Down Expand Up @@ -310,6 +331,36 @@ public function apply() {
}
}

/**
* Returns true if restriction is valid.
* This is used to check if the restriction is valid before it will be published.
* Will throw an exception containing the error message if the restriction is not valid. The error message is expanded in the exception class.
* @return true
* @throws RestrictionInvalidException
*/
public function isValid(): bool {
if ($this->getItemIds() == [] ) {
throw new RestrictionInvalidException( __( 'No item selected.', 'commonsbooking' ) );
}

if ($this->getLocationIds() == [] ) {
throw new RestrictionInvalidException( __( 'No location selected.', 'commonsbooking' ) );
}

if ( $this->getStartDate() > $this->getEndDate() ) {
throw new RestrictionInvalidException( __( 'Start date is after end date.', 'commonsbooking' ) );
}

if (
( $this->getMeta(self::META_ITEM_ID) === CustomPostType::SELECTION_ALL_POSTS || $this->getMeta(self::META_LOCATION_ID) === CustomPostType::SELECTION_ALL_POSTS )
&& ! commonsbooking_isCurrentUserAdmin()
) {
throw new RestrictionInvalidException( __( 'Only admins are allowed to create a restriction for all items / locations.', 'commonsbooking' ) );
}

return true;
}

/**
* Returns restriction type.
* We currently have two types: hint and repair.
Expand Down
1 change: 1 addition & 0 deletions src/Plugin.php
Original file line number Diff line number Diff line change
Expand Up @@ -429,6 +429,7 @@ public static function registerLocationTaxonomy() {
public static function renderError() {
$errorTypes = [
Model\Timeframe::ERROR_TYPE,
Model\Restriction::ERROR_TYPE,
BookingCode::ERROR_TYPE,
OptionsTab::ERROR_TYPE,
Model\Booking::ERROR_TYPE,
Expand Down
35 changes: 18 additions & 17 deletions src/Repository/Booking.php
Original file line number Diff line number Diff line change
Expand Up @@ -209,21 +209,22 @@ function ( $post ) {
}

/**
* Will return all bookings that are in a specific timerange.
*
* @param $startDate int
* @param $endDate int
* @param $locationId
* @param $itemId
* @param array $customArgs
* @param array $postStatus
* @param array $locationIds
* @param array $itemIds
* @param array $customArgs
* @param array $postStatus
*
* @return \CommonsBooking\Model\Booking[]
* @throws Exception
*/
public static function getByTimerange(
int $startDate,
int $endDate,
$locationId,
$itemId,
$locationIds = [],
$itemIds = [],
array $customArgs = [],
array $postStatus = [ 'confirmed', 'unconfirmed' ]
): ?array {
Expand Down Expand Up @@ -254,19 +255,19 @@ public static function getByTimerange(
'nopaging' => true,
);

if ( $locationId ) {
if ( $locationIds !== [] ) {
$args['meta_query'][] = array(
'key' => 'location-id',
'value' => $locationId,
'compare' => '=',
'key' => \CommonsBooking\Model\Booking::META_LOCATION_ID,
'value' => $locationIds,
'compare' => 'IN',
);
}

if ( $itemId ) {
if ( $locationIds !== [] ) {
$args['meta_query'][] = array(
'key' => 'item-id',
'value' => $itemId,
'compare' => '=',
'key' => \CommonsBooking\Model\Booking::META_ITEM_ID,
'value' => $itemIds,
'compare' => 'IN',
);
}

Expand Down Expand Up @@ -427,8 +428,8 @@ public static function getByRestriction( \CommonsBooking\Model\Restriction $rest
return self::getByTimerange(
$restriction->getStartDate(),
$restriction->getEndDate(),
$restriction->getLocationId(),
$restriction->getItemId(),
$restriction->getLocationIds(),
$restriction->getItemIds(),
[],
[ 'confirmed' ]
);
Expand Down
74 changes: 34 additions & 40 deletions src/Repository/Restriction.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,27 @@

use CommonsBooking\Helper\Wordpress;
use CommonsBooking\Plugin;
use CommonsBooking\Wordpress\CustomPostType\CustomPostType;
use Exception;

class Restriction extends PostRepository {

/**
* Returns active restrictions.
*
* If both $locations and $items are empty, all restrictions will be returned.
*
* WARNING: When setting either $locations or $items, the query will be filtered by both.
* Meaning, that if $locations is not empty, but $items is, only restrictions that apply to all items will be returned.
* So, if a restriction is created that applies to the location but only to one item, it will not be returned if you just query for the location.
*
* @param array $locations Array of location ids
* @param array $items Array of item ids
* @param string|null $date
* @param bool $returnAsModel
* @param null $minTimestamp
* @param array $postStatus
*
* @return \CommonsBooking\Model\Restriction[]
* @throws Exception
*/
Expand Down Expand Up @@ -195,46 +210,25 @@ private static function getActiveQuery(): string {
*/
private static function filterPosts( array $posts, array $locations, array $items ): array {
hansmorb marked this conversation as resolved.
Show resolved Hide resolved
return array_filter( $posts, function ( $post ) use ( $locations, $items ) {
// Check if restriction is in relation to item and/or location
$location = intval( get_post_meta( $post->ID, \CommonsBooking\Model\Restriction::META_LOCATION_ID, true ) );
$restrictionHasLocation = $location !== 0;
$restrictedLocationInLocations = $restrictionHasLocation && in_array( $location, $locations );

$item = intval( get_post_meta( $post->ID, \CommonsBooking\Model\Restriction::META_ITEM_ID, true ) );
$restrictionHasItem = $item !== 0;
$restrictedItemInItems = $restrictionHasItem && in_array( $item, $items );

// No item or location for restriction set
$noLocationNoItem = ( ! $restrictionHasLocation && ! $restrictionHasItem );

// No location, item matching
$noLocationItemMatches = (
! $restrictionHasLocation &&
$restrictionHasItem &&
$restrictedItemInItems
);

// No item, location matching
$noItemLocationMatches = (
! $restrictionHasItem &&
$restrictionHasLocation &&
$restrictedLocationInLocations
);

// Item and location matching
$itemAndLocationMatches = (
$restrictionHasLocation &&
$restrictedLocationInLocations &&
$restrictionHasItem &&
$restrictedItemInItems
);

return
$noLocationNoItem ||
$noLocationItemMatches ||
$noItemLocationMatches ||
$itemAndLocationMatches;
} );
$item = intval( get_post_meta( $post->ID, \CommonsBooking\Model\Restriction::META_ITEM_ID, true ) );
$location = intval( get_post_meta( $post->ID, \CommonsBooking\Model\Restriction::META_LOCATION_ID, true ) );

//check, if the restriction has been set to apply to all items or all locations.
$appliedForAllItems = get_post_meta( $post->ID, \CommonsBooking\Model\Restriction::META_ITEM_ID, true ) === CustomPostType::SELECTION_ALL_POSTS;
$appliedForAllLocations = get_post_meta( $post->ID, \CommonsBooking\Model\Restriction::META_LOCATION_ID, true ) === CustomPostType::SELECTION_ALL_POSTS;

if ( $appliedForAllItems && $appliedForAllLocations ) {
return true;
} elseif ( $appliedForAllLocations && in_array( $item, $items ) ) {
return true;
} elseif ( $appliedForAllItems && in_array( $location, $locations ) ) {
return true;
} elseif ( in_array( $item, $items ) && in_array( $location, $locations ) ) {
return true;
} else {
return false;
}
});
}

/**
Expand Down
Loading
Loading