package com.braintree.controllers.pages;

import com.braintree.controllers.BraintreeaddonControllerConstants;
import com.braintree.facade.BrainTreeUserFacade;
import de.hybris.platform.acceleratorstorefrontcommons.controllers.pages.AbstractLoginPageController;
import de.hybris.platform.acceleratorstorefrontcommons.controllers.util.GlobalMessages;
import de.hybris.platform.acceleratorstorefrontcommons.forms.GuestForm;
import de.hybris.platform.acceleratorstorefrontcommons.forms.LoginForm;
import de.hybris.platform.acceleratorstorefrontcommons.forms.RegisterForm;
import de.hybris.platform.cms2.exceptions.CMSItemNotFoundException;
import de.hybris.platform.cms2.model.pages.AbstractPageModel;
import org.apache.log4j.Logger;
import org.springframework.security.web.savedrequest.HttpSessionRequestCache;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.RequestHeader;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@Controller
@RequestMapping(value = "/login")
public class BrainTreeLoginPageController extends AbstractLoginPageController {
    private static final Logger LOGGER = Logger.getLogger(BrainTreeLoginPageController.class);
    private static final String FORM_GLOBAL_ERROR = "form.global.error";
    private static final String REGISTRATION_ERROR = "paypal.connect.registration.global.error";

    private HttpSessionRequestCache httpSessionRequestCache;

    @Resource(name = "userFacade")
    private BrainTreeUserFacade brainTreeUserFacade;

    @RequestMapping(value = "/customerRegistration", method = RequestMethod.POST)
    public String doRegister(@RequestHeader(value = "referer", required = false) final String referer,
                             final RegisterForm form, final BindingResult bindingResult, final Model model,
                             final HttpServletRequest request, final HttpServletResponse response,
                             final RedirectAttributes redirectModel) throws CMSItemNotFoundException {
        getRegistrationValidator().validate(form, bindingResult);
        if (!bindingResult.hasErrors() && brainTreeUserFacade.isUserExisting(form.getEmail().toLowerCase())) {
            LOGGER.debug("registration failed.");
            form.setTermsCheck(false);
            model.addAttribute(form);
            model.addAttribute(new LoginForm());
            model.addAttribute(new GuestForm());
            if (brainTreeUserFacade.isPayerIdInCustomer(form.getEmail().toLowerCase())) {
                bindingResult.rejectValue("email", REGISTRATION_ERROR);
            } else {
                bindingResult.rejectValue("email", "registration.error.account.exists.title");
            }
            GlobalMessages.addErrorMessage(model, FORM_GLOBAL_ERROR);
            return handleRegistrationError(model);
        }
        return processRegisterUserRequest(referer, form, bindingResult, model, request, response, redirectModel);
    }

    @Override
    protected AbstractPageModel getCmsPage() throws CMSItemNotFoundException {
        return getContentPageForLabelOrId("login");
    }

    @Override
    protected String getSuccessRedirect(HttpServletRequest request, HttpServletResponse response) {
        if (httpSessionRequestCache.getRequest(request, response) != null)
        {
            return httpSessionRequestCache.getRequest(request, response).getRedirectUrl();
        }
        return "/";
    }

    @Override
    protected String getView() {
        return BraintreeaddonControllerConstants.Views.Pages.Account.AccountLoginPage;
    }

    @Resource(name = "httpSessionRequestCache")
    public void setHttpSessionRequestCache(final HttpSessionRequestCache accHttpSessionRequestCache) {
        this.httpSessionRequestCache = accHttpSessionRequestCache;
    }
}
