/** * Redirects to the Neos backend on the given site, passing a one-time login token * * @param Site $site * @return void */ public function switchSiteAction($site) { $token = Algorithms::generateRandomToken(32); $this->loginTokenCache->set($token, $this->currentSession->getId()); $siteUri = $this->linkingService->createSiteUri($this->controllerContext, $site); $loginUri = $this->controllerContext->getUriBuilder()->reset()->uriFor('tokenLogin', ['token' => $token], 'Login', 'Neos.Neos'); $this->redirectToUri($siteUri . $loginUri); }
/** * Before advice for all methods annotated with "@Flow\Session(autoStart=true)". * Those methods will trigger a session initialization if a session does not exist * yet. * * @param JoinPointInterface $joinPoint The current join point * @return void * @fixme The pointcut expression below does not consider the options of the session annotation – needs adjustments in the AOP framework * @Flow\Before("methodAnnotatedWith(Neos\Flow\Annotations\Session)") */ public function initializeSession(JoinPointInterface $joinPoint) { if ($this->session->isStarted() === true) { return; } $objectName = $this->objectManager->getObjectNameByClassName(get_class($joinPoint->getProxy())); $methodName = $joinPoint->getMethodName(); $this->systemLogger->log(sprintf('Session initialization triggered by %s->%s.', $objectName, $methodName), LOG_DEBUG); $this->session->start(); }
/** * Returns the specified session. If no session with the given identifier exists, * NULL is returned. * * @param string $sessionIdentifier The session identifier * @return SessionInterface * @api */ public function getSession($sessionIdentifier) { if ($this->currentSession !== null && $this->currentSession->isStarted() && $this->currentSession->getId() === $sessionIdentifier) { return $this->currentSession; } if (isset($this->remoteSessions[$sessionIdentifier])) { return $this->remoteSessions[$sessionIdentifier]; } if ($this->metaDataCache->has($sessionIdentifier)) { $sessionInfo = $this->metaDataCache->get($sessionIdentifier); $this->remoteSessions[$sessionIdentifier] = new Session($sessionIdentifier, $sessionInfo['storageIdentifier'], $sessionInfo['lastActivityTimestamp'], $sessionInfo['tags']); return $this->remoteSessions[$sessionIdentifier]; } }
/** * Shows the specified node and takes visibility and access restrictions into * account. * * @param NodeInterface $node * @return string View output for the specified node * @Flow\SkipCsrfProtection We need to skip CSRF protection here because this action could be called with unsafe requests from widgets or plugins that are rendered on the node - For those the CSRF token is validated on the sub-request, so it is safe to be skipped here * @Flow\IgnoreValidation("node") * @throws NodeNotFoundException */ public function showAction(NodeInterface $node = null) { if ($node === null) { throw new NodeNotFoundException('The requested node does not exist or isn\'t accessible to the current user', 1430218623); } $inBackend = $node->getContext()->isInBackend(); if ($node->getNodeType()->isOfType('Neos.Neos:Shortcut') && !$inBackend) { $this->handleShortcutNode($node); } $this->view->assign('value', $node); if ($inBackend) { $this->overrideViewVariablesFromInternalArguments(); /** @var UserInterfaceMode $renderingMode */ $renderingMode = $node->getContext()->getCurrentRenderingMode(); $this->response->setHeader('Cache-Control', 'no-cache'); if ($renderingMode !== null) { // Deprecated TypoScript context variable from version 2.0. $this->view->assign('editPreviewMode', $renderingMode->getTypoScriptPath()); } if (!$this->view->canRenderWithNodeAndPath()) { $this->view->setTypoScriptPath('rawContent'); } } if ($this->session->isStarted() && $inBackend) { $this->session->putData('lastVisitedNode', $node->getContextPath()); } }
/** * @test */ public function logoutRefreshesTokensInSecurityContext() { $this->authenticationProviderManager = $this->getAccessibleMock(AuthenticationProviderManager::class, ['emitLoggedOut'], [], '', false); $this->inject($this->authenticationProviderManager, 'securityContext', $this->mockSecurityContext); $this->inject($this->authenticationProviderManager, 'session', $this->mockSession); $this->mockSession->expects($this->any())->method('canBeResumed')->will($this->returnValue(true)); $this->mockSession->expects($this->any())->method('isStarted')->will($this->returnValue(true)); $token = $this->getMockBuilder(TokenInterface::class)->disableOriginalConstructor()->getMock(); $token->expects($this->any())->method('isAuthenticated')->will($this->returnValue(true)); $this->mockSecurityContext->expects($this->any())->method('getAuthenticationTokens')->will($this->returnValue([$token])); $this->mockSecurityContext->expects($this->once())->method('refreshTokens'); $this->authenticationProviderManager->logout(); }
/** * * @param string $workspaceName * @return NodeInterface */ protected function getLastVisitedNode($workspaceName) { if (!$this->session->isStarted() || !$this->session->hasKey('lastVisitedNode')) { return null; } try { $lastVisitedNode = $this->propertyMapper->convert($this->session->getData('lastVisitedNode'), NodeInterface::class); $q = new FlowQuery([$lastVisitedNode]); $lastVisitedNodeUserWorkspace = $q->context(['workspaceName' => $workspaceName])->get(0); return $lastVisitedNodeUserWorkspace; } catch (\Exception $exception) { return null; } }
/** * Is called if authentication was successful. * * @param ActionRequest $originalRequest The request that was intercepted by the security framework, NULL if there was none * @return void */ protected function onAuthenticationSuccess(ActionRequest $originalRequest = null) { if ($this->view instanceof JsonView) { $this->view->assign('value', array('success' => $this->authenticationManager->isAuthenticated(), 'csrfToken' => $this->securityContext->getCsrfProtectionToken())); } else { if ($this->request->hasArgument('lastVisitedNode') && strlen($this->request->getArgument('lastVisitedNode')) > 0) { $this->session->putData('lastVisitedNode', $this->request->getArgument('lastVisitedNode')); } if ($originalRequest !== null) { // Redirect to the location that redirected to the login form because the user was nog logged in $this->redirectToRequest($originalRequest); } $this->redirect('index', 'Backend\\Backend'); } }
/** * Logout all active authentication tokens * * @return void */ public function logout() { if ($this->isAuthenticated() !== true) { return; } $this->isAuthenticated = null; /** @var $token TokenInterface */ foreach ($this->securityContext->getAuthenticationTokens() as $token) { $token->setAuthenticationStatus(TokenInterface::NO_CREDENTIALS_GIVEN); } $this->emitLoggedOut(); if ($this->session->isStarted()) { $this->session->destroy('Logout through AuthenticationProviderManager'); } $this->securityContext->refreshTokens(); }
/** * @Flow\Session(autoStart = true) * @return string */ public function sessionStartAction() { return 'this action started session ' . $this->session->getId(); }
/** * @param string $actionName Name of the action to forward to * @param string $controllerName Unqualified object name of the controller to forward to. If not specified, the current controller is used. * @param string $packageKey Key of the package containing the controller to forward to. If not specified, the current package is assumed. * @param array $arguments Array of arguments for the target action * @param integer $delay (optional) The delay in seconds. Default is no delay. * @param integer $statusCode (optional) The HTTP status code for the redirect. Default is "303 See Other" * @param string $format The format to use for the redirect URI * @return void */ protected function unsetLastVisitedNodeAndRedirect($actionName, $controllerName = null, $packageKey = null, array $arguments = null, $delay = 0, $statusCode = 303, $format = null) { $this->session->putData('lastVisitedNode', null); parent::redirect($actionName, $controllerName, $packageKey, $arguments, $delay, $statusCode, $format); }