<commit_before><?php
/*
 * This file is part of the cookbook/core package.
 *
 * (c) <NAME> <<EMAIL>>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Cookbook\Core\Bus;

use Closure;
use Exception;
use Illuminate\Http\Response;
use Cookbook\Core\Exceptions\Exception as CookbookException;

/**
 * ApiCommandDispatcher class
 * 
 * Cookbook API Command Dispatcher
 * 
 * @uses  		Cookbook\Core\Bus\CommandDispatcher
 * 
 * @author  	<NAME> <<EMAIL>>
 * @copyright  	<NAME> <<EMAIL>>
 * @package 	cookbook/core
 * @since 		0.1.0-alpha
 * @version  	0.1.0-alpha
 */
class ApiCommandDispatcher
{

	protected $dispatcher;


	public function __construct(CommandDispatcher $dispatcher)
	{
		$this->dispatcher = $dispatcher;
	}

	/**
	 * Dispatch a command to its appropriate handler.
	 * And handle the result as JSON response for API
	 *
	 * @param  mixed  $command
	 * @param  Closure|null  $afterResolving
	 * 
	 * @return mixed
	 */
	public function dispatch($command, Closure $afterResolving = null)
	{
		try
		{
			// dispatch the command
			$result = $this->dispatcher->dispatch($command, $afterResolving);
		}
		catch(Exception $e)
		{
			return $this->handleException($e);
		}

		// return the handler result
		return $this->createResponse($result);
	}

	protected function handleException(Exception $e)
	{
		// if it's a cookbook exception, 
		// use it's toArray function to ger all errors
		if( $e instanceOf CookbookException )
		{
			return $this->handleCookbookException($e);
		}

		// if it's some other exception return 500 error from exception
		return $this->handleGenericException($e);
	}

	protected function handleCookbookException(CookbookException $e)
	{
		$errors = $e->toArray();

		$responseCode = $this->getResponseCodeFromErrors($errors);

		return $this->createResponse(['errors' => $errors], $responseCode);
	}

	protected function handleGenericException(Exception $e)
	{
		$message = $e->getMessage();
		$code = $e->getCode();
		$status = 500;

		$error = [
			'status' 	=> $status,
			'code'	 	=> $code,
			'message' 	=> $message,
			'pinter' 	=> '/'
		];

		$errors = [$error];

		return $this->createResponse(['errors' => $errors], $status);
	}

	protected function getResponseCodeFromErrors(array $errors)
	{
		$statusDetail = 0;
		$statusGeneral = 0;
		foreach ($errors as $error) {
			
			// if it's first error set values and move on
			if($statusDetail = 0)
			{
				$statusGeneral = $statusDetail = $error['status'];
				continue;
			}

			// get http status code group
			$statusGroup = floor($error['status'], -2);

			// check if group is lower then previous error
			// if it is break
			if($statusGroup < floor($statusGeneral, -2))
			{
				break;
			}
			// check if errors are different
			// if they are return general http code (400, 500...)
			if($statusDetail != $error['status'])
			{
				$statusGeneral = $statusGroup;
			}
		}

		return $statusGeneral;
	}

	public function createResponse($data = [], $code = 200, $headers = [])
	{
		$response = new Response(json_encode($data), $code);

		$response->header('Content-Type', 'application/cookbook.api+json');

		if( ! empty($headers) && is_array($headers) )
		{
			foreach ($headers as $key => $value) {
				$response->header($key, $value, true);
			}
		}

		return $response;
	}

}<commit_msg>small fix<commit_after><?php
/*
 * This file is part of the cookbook/core package.
 *
 * (c) <NAME> <<EMAIL>>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Cookbook\Core\Bus;

use Closure;
use Exception;
use Illuminate\Http\Response;
use Cookbook\Core\Exceptions\Exception as CookbookException;

/**
 * ApiCommandDispatcher class
 * 
 * Cookbook API Command Dispatcher
 * 
 * @uses  		Cookbook\Core\Bus\CommandDispatcher
 * 
 * @author  	<NAME> <<EMAIL>>
 * @copyright  	<NAME> <<EMAIL>>
 * @package 	cookbook/core
 * @since 		0.1.0-alpha
 * @version  	0.1.0-alpha
 */
class ApiCommandDispatcher
{

	protected $dispatcher;


	public function __construct(CommandDispatcher $dispatcher)
	{
		$this->dispatcher = $dispatcher;
	}

	/**
	 * Dispatch a command to its appropriate handler.
	 * And handle the result as JSON response for API
	 *
	 * @param  mixed  $command
	 * @param  Closure|null  $afterResolving
	 * 
	 * @return mixed
	 */
	public function dispatch($command, Closure $afterResolving = null)
	{
		try
		{
			// dispatch the command
			$result = $this->dispatcher->dispatch($command, $afterResolving);
		}
		catch(Exception $e)
		{
			return $this->handleException($e);
		}

		// return the handler result
		return $this->createResponse($result);
	}

	protected function handleException(Exception $e)
	{
		// if it's a cookbook exception, 
		// use it's toArray function to ger all errors
		if( $e instanceOf CookbookException )
		{
			return $this->handleCookbookException($e);
		}

		// if it's some other exception return 500 error from exception
		return $this->handleGenericException($e);
	}

	protected function handleCookbookException(CookbookException $e)
	{
		$errors = $e->toArray();

		$responseCode = $this->getResponseCodeFromErrors($errors);

		return $this->createResponse(['errors' => $errors], $responseCode);
	}

	protected function handleGenericException(Exception $e)
	{
		$message = $e->getMessage();
		$code = $e->getCode();
		$status = 500;

		$error = [
			'status' 	=> $status,
			'code'	 	=> $code,
			'message' 	=> $message,
			'pinter' 	=> '/'
		];

		$errors = [$error];

		return $this->createResponse(['errors' => $errors], $status);
	}

	protected function getResponseCodeFromErrors(array $errors)
	{
		$statusDetail = 0;
		$statusGeneral = 0;
		foreach ($errors as $error) {
			
			// if it's first error set values and move on
			if($statusDetail = 0)
			{
				$statusGeneral = $statusDetail = $error['status'];
				continue;
			}

			// get http status code group
			$statusGroup = floor($error['status'] / 100) * 100;

			// check if group is lower then previous error
			// if it is break
			if($statusGroup < floor($statusGeneral / 100) * 100)
			{
				break;
			}
			// check if errors are different
			// if they are return general http code (400, 500...)
			if($statusDetail != $error['status'])
			{
				$statusGeneral = $statusGroup;
			}
		}

		return $statusGeneral;
	}

	public function createResponse($data = [], $code = 200, $headers = [])
	{
		$response = new Response(json_encode($data), $code);

		$response->header('Content-Type', 'application/cookbook.api+json');

		if( ! empty($headers) && is_array($headers) )
		{
			foreach ($headers as $key => $value) {
				$response->header($key, $value, true);
			}
		}

		return $response;
	}

}
{'fraction_non_alphanumeric': 0.1411314083677077, 'fraction_numerical': 0.009133765468473777, 'mean_word_length': 3.448885976408912, 'pattern_counts': {'":': 0, '<': 25, '<?xml version=': 0, '>': 65, 'https://': 0, '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': '637098', 'n_tokens_mistral': 2491, 'n_tokens_neox': 2137, 'n_words': 577}