<commit_before><?php

namespace Lagan;

/**
 * Search controller for Lagan.
 *
 * We use "*" as the seperator, since "-" is in the slug, and "+" is filtered out of the $_GET variable name by PHP.
 *
 * Syntax:
 * Value from: *min
 * Value to: *max
 * Contains: *has
 * Equal to: *is
 * Sort: sort
 * Limit: length
 * Offset: start
 *
 * start only works if length is defined too
 *
 * Query structure examples:
 * [model]?*has=[search string] :				Searches all searchable properties of a model
 * [model]?[property]*has=[search string] :		Searches single property of a model
 * [model]?[property]*min=[number]
 * sort=[property]*asc
 * [model]?description*title*has=[search string]&title*has=[search string]&sort=title*asc&start=10&length=100
 *
 * To be used with Lagan: https://github.com/lutsen/lagan
 */

class Search {

	protected $type;
	protected $criteria;
	protected $sequences;
	protected $model;

	/**
	 * Construct function
	 *
	 * @param string $type The Bean type to search
	 */
	function __construct($type) {

		$this->type = $type;

		$this->criteria = array(
			'*min',
			'*max',
			'*has',
			'*is'
		);

		// Sorting order
		$this->sequences = array(
			'*asc',
			'*desc'
		);

		$model_name = '\Lagan\Model\\' . ucfirst($type);
		$this->model = new $model_name;

	}

	/**
	 * Search function
	 *
	 * @param array[] $params Request parameters array
	 *
	 * @return bean[] Array of Redbean beans matching the search criteria
	 */
	public function find($params) {

		// Search
		$loop = 0; // To create different name for all search values
		$q = [];
		$s= [];
		$values = [];
		foreach ($params as $left => $right) {

			$lhs = $this->lefthandside($left);

			// Sort
			if ( $lhs == 'sort' ) {

				$rhs = $this->righthandside($right);

				$glue = ' '.strtoupper($rhs['order']).', ';
				$s[] = implode( $glue, $rhs['properties'] ) . ' ' . strtoupper($rhs['order']); // Add latest order

			} else if ($lhs === 'start') {

				// Limit
				$start = true;
				$values[ ':start' ] = floatval($right);
			
			} elseif ($lhs === 'length') {

				// Limit
				$length = true;
				$values[ ':length' ] = floatval($right);

			// Find
			} else if ( $lhs ) {

				$p = [];
				foreach ($lhs['properties'] as $k => $v) {

					if ( $this->isSearchable($v) ) {

						if ($lhs['criterion'] === '*min') {

							// Create '>=' query
							$p[] = ' '.$v.' >= :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = floatval($right);

						} elseif ($lhs['criterion'] === '*max') {

							// Create '<=' query
							$p[] = ' '.$v.' <= :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = floatval($right);

						} elseif ($lhs['criterion'] === '*has') {

							// Create 'LIKE' query
							$p[] = ' '.$v.' LIKE :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = '%'.$right.'%';

						} elseif ($lhs['criterion'] === '*is') {

							// Create '=' query
							$p[] = ' '.$v.' = :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = $right;

						}

					} // End isSearchable($v)

				} // End foreach $lhs['properties']


				// Implode array to create nice 'OR' query
				$q[] = implode('OR', $p);

				$loop++;

			} // End if else

		} // End foreach $params

		// Query

		// Implode array to create nice '( #query ) AND ( #query )'
		if (count($q) > 1) {
			$query = '(' . implode(') AND (', $q) . ')';
		} else if (count($q) > 0) {
			$query = $q[0];
		} else {
			return false;
		}

		// Implode different sort arrays
		$sort = '';
		if (count($s) > 0) {
			$sort = ' ORDER BY ' . implode(', ', $s);
		}

		if ( isset($length) ) {
			$limit .= ' LIMIT :length';
			if ( isset($start) ) {
				$limit .= ' OFFSET :start';<commit_msg>Removed to allow pagination or sorting without searching.<commit_after><?php

namespace Lagan;

/**
 * Search controller for Lagan.
 *
 * We use "*" as the seperator, since "-" is in the slug, and "+" is filtered out of the $_GET variable name by PHP.
 *
 * Syntax:
 * Value from: *min
 * Value to: *max
 * Contains: *has
 * Equal to: *is
 * Sort: sort
 * Limit: length
 * Offset: start
 *
 * start only works if length is defined too
 *
 * Query structure examples:
 * [model]?*has=[search string] :				Searches all searchable properties of a model
 * [model]?[property]*has=[search string] :		Searches single property of a model
 * [model]?[property]*min=[number]
 * sort=[property]*asc
 * [model]?description*title*has=[search string]&title*has=[search string]&sort=title*asc&start=10&length=100
 *
 * To be used with Lagan: https://github.com/lutsen/lagan
 */

class Search {

	protected $type;
	protected $criteria;
	protected $sequences;
	protected $model;

	/**
	 * Construct function
	 *
	 * @param string $type The Bean type to search
	 */
	function __construct($type) {

		$this->type = $type;

		$this->criteria = array(
			'*min',
			'*max',
			'*has',
			'*is'
		);

		// Sorting order
		$this->sequences = array(
			'*asc',
			'*desc'
		);

		$model_name = '\Lagan\Model\\' . ucfirst($type);
		$this->model = new $model_name;

	}

	/**
	 * Search function
	 *
	 * @param array[] $params Request parameters array
	 *
	 * @return bean[] Array of Redbean beans matching the search criteria
	 */
	public function find($params) {

		// Search
		$loop = 0; // To create different name for all search values
		$q = [];
		$s= [];
		$values = [];
		foreach ($params as $left => $right) {

			$lhs = $this->lefthandside($left);

			// Sort
			if ( $lhs == 'sort' ) {

				$rhs = $this->righthandside($right);

				$glue = ' '.strtoupper($rhs['order']).', ';
				$s[] = implode( $glue, $rhs['properties'] ) . ' ' . strtoupper($rhs['order']); // Add latest order

			} else if ($lhs === 'start') {

				// Limit
				$start = true;
				$values[ ':start' ] = floatval($right);
			
			} elseif ($lhs === 'length') {

				// Limit
				$length = true;
				$values[ ':length' ] = floatval($right);

			// Find
			} else if ( $lhs ) {

				$p = [];
				foreach ($lhs['properties'] as $k => $v) {

					if ( $this->isSearchable($v) ) {

						if ($lhs['criterion'] === '*min') {

							// Create '>=' query
							$p[] = ' '.$v.' >= :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = floatval($right);

						} elseif ($lhs['criterion'] === '*max') {

							// Create '<=' query
							$p[] = ' '.$v.' <= :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = floatval($right);

						} elseif ($lhs['criterion'] === '*has') {

							// Create 'LIKE' query
							$p[] = ' '.$v.' LIKE :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = '%'.$right.'%';

						} elseif ($lhs['criterion'] === '*is') {

							// Create '=' query
							$p[] = ' '.$v.' = :value'.$loop.' ';
							// Add value to Redbean named search values array
							$values[ ':value'.$loop ] = $right;

						}

					} // End isSearchable($v)

				} // End foreach $lhs['properties']


				// Implode array to create nice 'OR' query
				$q[] = implode('OR', $p);

				$loop++;

			} // End if else

		} // End foreach $params

		// Query

		// Implode array to create nice '( #query ) AND ( #query )'
		if (count($q) > 1) {
			$query = '(' . implode(') AND (', $q) . ')';
		} else if (count($q) > 0) {
			$query = $q[0];
		}

		// Implode different sort arrays
		$sort = '';
		if (count($s) > 0) {
			$sort = ' ORDER BY ' . implode(', ', $s);
		}

		if ( isset($length) ) {
			$limit .= ' LIMIT :length';
			if ( isset($start) ) {
				$limit .= ' OFFSET :start';
{'fraction_non_alphanumeric': 0.20143700282268412, 'fraction_numerical': 0.0025660764690787785, 'mean_word_length': 2.528746038931643, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 31, 'https://': 2, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '454287', 'n_tokens_mistral': 3268, 'n_tokens_neox': 2687, 'n_words': 731}