Skip to content
Snippets Groups Projects
FeatureContainer.php 6.68 KiB
Newer Older
  • Learn to ignore specific revisions
  • Josh Pollock's avatar
    Josh Pollock committed
    <?php
    
    
    namespace calderawp\CalderaFormsQuery\Features;
    
    use calderawp\CalderaContainers\Container;
    use calderawp\CalderaContainers\Interfaces\ServiceContainer;
    
    
    use calderawp\CalderaFormsQuery\Delete\DeleteQueryBuilder;
    use calderawp\CalderaFormsQuery\Delete\DoesDeleteQuery;
    
    Josh Pollock's avatar
    Josh Pollock committed
    use calderawp\CalderaFormsQuery\DeleteQueries;
    use calderawp\CalderaFormsQuery\MySqlBuilder;
    use calderawp\CalderaFormsQuery\Delete\Entry as EntryDelete;
    use \calderawp\CalderaFormsQuery\Delete\EntryValues as EntryValuesDelete;
    
    use calderawp\CalderaFormsQuery\Select\DoesSelectQuery;
    
    Josh Pollock's avatar
    Josh Pollock committed
    use \calderawp\CalderaFormsQuery\Select\Entry as EntrySelect;
    use \calderawp\CalderaFormsQuery\Select\EntryValues as EntryValueSelect;
    
    use calderawp\CalderaFormsQuery\Select\SelectQueryBuilder;
    
    Josh Pollock's avatar
    Josh Pollock committed
    use calderawp\CalderaFormsQuery\SelectQueries;
    
    class FeatureContainer extends Container
    {
    	/**
    	 * @var ServiceContainer
    	 */
    	protected $serviceContainer;
    	/**
    	 * @var \wpdb
    	 */
    	protected $wpdb;
    
    	/**
    	 * FeatureContainer constructor.
    	 * @param ServiceContainer $serviceContainer
    	 * @param \wpdb $wpdb
    	 */
    
    	public function __construct(ServiceContainer $serviceContainer, \wpdb $wpdb)
    
    Josh Pollock's avatar
    Josh Pollock committed
    	{
    		$this->serviceContainer = $serviceContainer;
    		$this->wpdb = $wpdb;
    		$this->bindServices();
    	}
    
    	/**
    	 * Bind services to service container
    	 */
    	protected function bindServices()
    	{
    
    		//@TODO move these to service provider classes
    
    		$this->serviceContainer->singleton(MySqlBuilder::class, function () {
    
    Josh Pollock's avatar
    Josh Pollock committed
    			return new MySqlBuilder();
    		});
    
    
    		$this->serviceContainer->bind(SelectQueries::class, function () {
    
    			//@TODO Factory
    
    Josh Pollock's avatar
    Josh Pollock committed
    			return new SelectQueries(
    				new EntrySelect(
    					$this->getBuilder(),
    					$this->entryTableName()
    				),
    				new EntryValueSelect(
    					$this->getBuilder(),
    
    					$this->entryValueTableName()
    
    Josh Pollock's avatar
    Josh Pollock committed
    				),
    				$this->wpdb
    			);
    		});
    
    
    		$this->serviceContainer->bind(DeleteQueries::class, function () {
    
    			//@TODO Factory
    
    Josh Pollock's avatar
    Josh Pollock committed
    			return new DeleteQueries(
    				new EntryDelete(
    					$this->getBuilder(),
    					$this->entryTableName()
    				),
    				new EntryValuesDelete(
    					$this->getBuilder(),
    
    					$this->entryValueTableName()
    
    Josh Pollock's avatar
    Josh Pollock committed
    				),
    				$this->wpdb
    			);
    		});
    
    
    		$this->serviceContainer->singleton(Queries::class, function () {
    
    Josh Pollock's avatar
    Josh Pollock committed
    			return new Queries(
    				$this
    					->serviceContainer
    
    					->make(SelectQueries::class),
    
    Josh Pollock's avatar
    Josh Pollock committed
    				$this
    					->serviceContainer
    
    					->make(DeleteQueries::class)
    
    Josh Pollock's avatar
    Josh Pollock committed
    			);
    		});
    	}
    
    	/**
    	 * Get MySQL builder
    	 *
    	 * @return MySqlBuilder
    	 */
    	public function getBuilder()
    	{
    		return $this
    			->serviceContainer
    
    			->make(MySqlBuilder::class);
    
    Josh Pollock's avatar
    Josh Pollock committed
    	}
    
    	/**
    	 * Get query runner
    	 *
    	 * @return Queries
    	 */
    	public function getQueries()
    	{
    		return $this
    			->serviceContainer
    
    	/**
    	 * Select all entries and entry values by user ID
    	 *
    	 * @param int $userId
    	 * @return array
    	 */
    	public function selectByUserId($userId)
    	{
    		$query = $this
    			->getQueries()
    			->entrySelect()
    			->queryByUserId($userId);
    
    		return $this->collectResults($this->select($query));
    
    Josh Pollock's avatar
    Josh Pollock committed
    
    
    	/**
    	 * Find all entries that have or do not have field with a slug and value
    	 *
    	 * @param string $fieldSlug Field slug
    	 * @param string $fieldValue Field value
    	 * @param bool $have Optional. Default: true. If true query is for fields with this value
    	 *
    	 * @return array
    	 */
    
    	public function selectByFieldValue($fieldSlug, $fieldValue, $have = true)
    
    	{
    		$type = $have ? 'equals' : 'notEquals';
    		$queryForEntryValues = $this
    			->getQueries()
    			->entryValuesSelect()
    			->queryByFieldValue($fieldSlug, $fieldValue, $type, 'AND', [
    				'entry_id'
    
    			]);
    		$results = $this->select($queryForEntryValues);
    		if (empty($results) || 0 >= count($results)) {
    
    		$results = $this->reduceResultsToEntryId($results);
    
    
    		$queryForValues = $this
    			->getQueries()
    			->entrySelect()
    			->queryByEntryIds($results);
    
    
    		return $this->collectResults($this->select($queryForValues));
    
    	/**
    	 * Delete all entry data, including field values for a collection of entries
    	 *
    	 * @param array $entryIds Entry Ids to delete
    	 * @return $this
    	 */
    
    	public function deleteByEntryIds(array $entryIds)
    
    	{
    		$this->delete(
    			$this
    
    				->getQueries()
    				->entryDelete()
    				->deleteByEntryIds($entryIds)
    
    		);
    		$this->delete(
    			$this->getQueries()
    				->entryValueDelete()
    				->deleteByEntryIds($entryIds)
    		);
    
    		return $this;
    	}
    
    
    	/**
    	 * Delete all entries and entry values by user ID
    	 *
    	 * @param int $userId
    	 */
    	public function deleteByUserId($userId)
    	{
    		$entries = $this->select(
    			$this
    			->getQueries()
    			->entrySelect()
    			->queryByUserId($userId)
    		);
    		if (!empty($entries)) {
    			$ids = $this->reduceResultsToEntryId($entries, 'id');
    			$this->delete(
    				$this
    					->getQueries()
    					->entryDelete()
    					->deleteByEntryIds($ids)
    			);
    			$this->delete(
    				$this
    					->getQueries()
    					->entryValueDelete()
    					->deleteByEntryIds($ids)
    			);
    		}
    	}
    
    
    Josh Pollock's avatar
    Josh Pollock committed
    	/**
    	 * @return string
    	 */
    
    	protected function entryValueTableName()
    
    Josh Pollock's avatar
    Josh Pollock committed
    	{
    		return "{$this->wpdb->prefix}cf_form_entry_values";
    	}
    
    	/**
    	 * @return string
    	 */
    
    	protected function entryTableName()
    
    Josh Pollock's avatar
    Josh Pollock committed
    	{
    		return "{$this->wpdb->prefix}cf_form_entries";
    	}
    
    
    	/**
    	 * Collect results using  Caldera_Forms_Entry_Entry and Caldera_Forms_Entry_Field to represent values
    	 *
    	 * @param \stdClass[] $entriesValues
    	 * @return array
    	 */
    	private function collectResults($entriesValues)
    	{
    		$results = [];
    		foreach ($entriesValues as $entry) {
    			$entry = new \Caldera_Forms_Entry_Entry($entry);
    			$query = $this
    				->getQueries()
    				->entryValuesSelect()
    				->queryByEntryId($entry->id);
    			$entriesValues = $this->select($query);
    
    			$entryValuesPrepared = $this->collectEntryValues($entriesValues);
    			$results[] = [
    				'entry' => $entry,
    				'values' => $entryValuesPrepared
    			];
    		}
    		return $results;
    	}
    
    	/**
    	 * Collect entry values as Caldera_Forms_Entry_Field objects
    	 *
    	 * @param \stdClass[] $entriesValues
    	 * @return array
    	 */
    	private function collectEntryValues($entriesValues): array
    	{
    		$entryValuesPrepared = [];
    		if (!empty($entriesValues)) {
    			foreach ($entriesValues as $entryValue) {
    				$entryValuesPrepared[] = new \Caldera_Forms_Entry_Field($entryValue);
    			}
    		}
    		return $entryValuesPrepared;
    	}
    
    	/**
    	 * Do a select query
    	 *
    	 * @param SelectQueryBuilder $query
    	 * @return \stdClass[]
    	 */
    	private function select(SelectQueryBuilder $query)
    	{
    		return $this
    
    			->getQueries()
    			->select($query);
    
    	}
    
    	/**
    	 * Do a delete query
    	 *
    	 * @param DeleteQueryBuilder $query
    	 * @return \stdClass[]
    	 */
    	private function delete(DeleteQueryBuilder $query)
    	{
    		return $this->
    
    Josh Pollock's avatar
    Josh Pollock committed
    			getQueries()
    
    			->delete($query);
    	}
    
    
    	/**
    	 * @param $results
    	 * @return array
    	 */
    
    Josh Pollock's avatar
    Josh Pollock committed
    	private function reduceResultsToEntryId($results, $colum = 'entry_id')
    
    	{
    		foreach ($results as &$result) {
    			$result = $result->$colum;
    		}
    		return $results;
    	}
    }