added project start and end date (#1303)

* added sortable js library
* activity in invoice is optional
* added javascript widget for paginated boxes
* fix activity dropdown for globals only
* added timesheet service to reduce code duplication
* use repository to query for teams in dropdowns
* added project validator
* validate project start and end against timesheet
* include begin and end in dynamic form requests for projects
* added timezone and language option to import flag, improve timesheet import speed
* deactivate cross-timezone filter
* add virtual fields to field order list
* composer update
* added param to ignore dates
* position loader icon fixed - fixes #1330
* permission problem when creating a new project - fixes #1340
* remove dev dependencies webserver and thanks bundle
* stop information leak (begin and end date) in duration mode - fixes #1307
* unify timesheet edit dialog for user and admins
* fix security issue, own rates exposed to unauthorized users in multi-update dialog
This commit is contained in:
Kevin Papst
2020-01-05 02:49:01 +01:00
committed by GitHub
parent 50383673ca
commit d6798eed1e
121 changed files with 2465 additions and 1439 deletions

View File

@@ -20,6 +20,7 @@ use App\Repository\Query\TimesheetQuery;
use App\Repository\TagRepository;
use App\Repository\TimesheetRepository;
use App\Timesheet\RoundingService;
use App\Timesheet\TimesheetService;
use App\Timesheet\TrackingMode\TrackingModeInterface;
use App\Timesheet\TrackingModeService;
use App\Timesheet\UserDateTimeFactory;
@@ -81,6 +82,10 @@ class TimesheetController extends BaseApiController
* @var RoundingService
*/
private $roundingService;
/**
* @var TimesheetService
*/
private $service;
public function __construct(
ViewHandlerInterface $viewHandler,
@@ -90,7 +95,8 @@ class TimesheetController extends BaseApiController
TagRepository $tagRepository,
TrackingModeService $trackingModeService,
EventDispatcherInterface $dispatcher,
RoundingService $roundingService
RoundingService $roundingService,
TimesheetService $service
) {
$this->viewHandler = $viewHandler;
$this->repository = $repository;
@@ -100,6 +106,7 @@ class TimesheetController extends BaseApiController
$this->trackingModeService = $trackingModeService;
$this->dispatcher = $dispatcher;
$this->roundingService = $roundingService;
$this->service = $service;
}
protected function getTrackingMode(): TrackingModeInterface
@@ -295,14 +302,9 @@ class TimesheetController extends BaseApiController
*/
public function postAction(Request $request): Response
{
$timesheet = new Timesheet();
$timesheet->setUser($this->getUser());
$event = new TimesheetMetaDefinitionEvent($timesheet);
$this->dispatcher->dispatch($event);
$timesheet = $this->service->createNewTimesheet($this->getUser(), $request);
$mode = $this->getTrackingMode();
$mode->create($timesheet, $request);
$form = $this->createForm(TimesheetApiEditForm::class, $timesheet, [
'include_rate' => $this->isGranted('edit_rate', $timesheet),
@@ -316,18 +318,16 @@ class TimesheetController extends BaseApiController
$form->submit($request->request->all(), false);
if ($form->isValid()) {
if (null === $timesheet->getEnd()) {
if (!$this->isGranted('start', $timesheet)) {
throw new AccessDeniedHttpException('You are not allowed to start this timesheet record');
try {
$this->service->saveNewTimesheet($timesheet);
} catch (\Exception $ex) {
if ($ex->getMessage() === 'timesheet.start.exceeded_limit') {
throw new BadRequestHttpException('Too many active timesheets');
} else {
throw $ex;
}
$this->repository->stopActiveEntries(
$timesheet->getUser(),
$this->configuration->getActiveEntriesHardLimit()
);
}
$this->repository->save($timesheet);
$view = new View($timesheet, 200);
$view->getContext()->setGroups(['Default', 'Entity', 'Timesheet']);
@@ -559,7 +559,7 @@ class TimesheetController extends BaseApiController
throw new AccessDeniedHttpException('You are not allowed to stop this timesheet');
}
$this->repository->stopRecording($timesheet);
$this->service->stopTimesheet($timesheet);
$view = new View($timesheet, 200);
$view->getContext()->setGroups(['Default', 'Entity', 'Timesheet']);
@@ -600,13 +600,10 @@ class TimesheetController extends BaseApiController
throw new AccessDeniedHttpException('You are not allowed to re-start this timesheet');
}
/** @var User $user */
$user = $this->getUser();
$copyTimesheet = $this->service->createNewTimesheet($this->getUser());
$copyTimesheet = new Timesheet();
$copyTimesheet
->setBegin($this->dateTime->createDateTime())
->setUser($user)
->setActivity($timesheet->getActivity())
->setProject($timesheet->getProject())
;
@@ -642,12 +639,7 @@ class TimesheetController extends BaseApiController
throw new BadRequestHttpException($errors[0]->getPropertyPath() . ' = ' . $errors[0]->getMessage());
}
$this->repository->stopActiveEntries(
$user,
$this->configuration->getActiveEntriesHardLimit()
);
$this->repository->save($copyTimesheet);
$this->service->saveNewTimesheet($copyTimesheet);
$view = new View($copyTimesheet, 200);
$view->getContext()->setGroups(['Default', 'Entity', 'Timesheet']);